Compare commits
9 Commits
e48c516211
...
3a8a25d2e1
Author | SHA1 | Date | |
---|---|---|---|
3a8a25d2e1 | |||
fdfb9c0361 | |||
f220bbc63b | |||
520a5ca6d9 | |||
2c22cae07f | |||
550d79af28 | |||
57d6238ed6 | |||
4a28e22b82 | |||
257f0c833c |
3
.gitmodules
vendored
Normal file
3
.gitmodules
vendored
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
[submodule "android"]
|
||||||
|
path = android
|
||||||
|
url = https://git.adb.sh/adb/matrix-chat-android.git
|
1
android
Submodule
1
android
Submodule
@ -0,0 +1 @@
|
|||||||
|
Subproject commit df7bff7aadc07c585760f73fdb5fa287a63c8b95
|
14
capacitor.config.json
Normal file
14
capacitor.config.json
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
{
|
||||||
|
"appId": "sh.adb.matrixChat",
|
||||||
|
"appName": "matrix-chat",
|
||||||
|
"bundledWebRuntime": false,
|
||||||
|
"npmClient": "npm",
|
||||||
|
"webDir": "./dist",
|
||||||
|
"linuxAndroidStudioPath": "/home/alban/.local/share/JetBrains/Toolbox/apps/AndroidStudio/ch-0/201.7199119/bin/studio.sh",
|
||||||
|
"plugins": {
|
||||||
|
"SplashScreen": {
|
||||||
|
"launchShowDuration": 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cordova": {}
|
||||||
|
}
|
@ -8,6 +8,11 @@
|
|||||||
"lint": "vue-cli-service lint"
|
"lint": "vue-cli-service lint"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
"@capacitor/android": "^2.4.7",
|
||||||
|
"@capacitor/cli": "^2.4.7",
|
||||||
|
"@capacitor/core": "^2.4.7",
|
||||||
|
"@modular-matrix/parse-mxc": "^1.0.1",
|
||||||
|
"@vue-polkadot/vue-identicon": "^0.0.8",
|
||||||
"core-js": "^3.6.5",
|
"core-js": "^3.6.5",
|
||||||
"jdenticon": "^3.1.0",
|
"jdenticon": "^3.1.0",
|
||||||
"matrix-js-sdk": "^9.1.0",
|
"matrix-js-sdk": "^9.1.0",
|
||||||
|
@ -22,7 +22,7 @@
|
|||||||
type="submit"
|
type="submit"
|
||||||
title="press enter to submit"
|
title="press enter to submit"
|
||||||
class="sendMessageBtn"
|
class="sendMessageBtn"
|
||||||
ic="./sym/ic_send_white.svg"
|
:ic="isSending?'./sym/throbber.svg':'./sym/ic_send_white.svg'"
|
||||||
@click.native="onSubmit(event)"
|
@click.native="onSubmit(event)"
|
||||||
/>
|
/>
|
||||||
<sound-recorder v-else class="recorder" :on-stop="setAttachment" ref="recorder"/>
|
<sound-recorder v-else class="recorder" :on-stop="setAttachment" ref="recorder"/>
|
||||||
@ -74,13 +74,15 @@ export default {
|
|||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
onSubmit(event){
|
onSubmit(event){
|
||||||
console.log(event)
|
if (this.isSending) return;
|
||||||
event.content.msgtype==='m.text'?this.sendEvent(event):this.sendMediaEvent(event);
|
event.content.msgtype==='m.text'?this.sendEvent(event):this.sendMediaEvent(event);
|
||||||
},
|
},
|
||||||
async sendEvent(event){
|
async sendEvent(event){
|
||||||
if (!event.content.body.trim()) return;
|
if (!event.content.body.trim()) return;
|
||||||
this.setReplyTo(this.replyTo);
|
this.setReplyTo(this.replyTo);
|
||||||
matrix.sendEvent(new Proxy(this.event, this.eventProxyHandler), this.roomId);
|
this.isSending = true;
|
||||||
|
await matrix.sendEvent(new Proxy(this.event, this.eventProxyHandler), this.roomId);
|
||||||
|
this.isSending = false;
|
||||||
event.content.body = '';
|
event.content.body = '';
|
||||||
this.resetAttachment();
|
this.resetAttachment();
|
||||||
this.resetReplyTo();
|
this.resetReplyTo();
|
||||||
@ -89,6 +91,7 @@ export default {
|
|||||||
this.onResize(id.parentElement.clientHeight);
|
this.onResize(id.parentElement.clientHeight);
|
||||||
},
|
},
|
||||||
sendMediaEvent(event){
|
sendMediaEvent(event){
|
||||||
|
this.isSending = true;
|
||||||
matrix.client.uploadContent(this.attachment.blob).then(mxc => {
|
matrix.client.uploadContent(this.attachment.blob).then(mxc => {
|
||||||
event.content.url = mxc;
|
event.content.url = mxc;
|
||||||
this.sendEvent(event);
|
this.sendEvent(event);
|
||||||
@ -169,20 +172,21 @@ export default {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
showEmojiPicker: false,
|
|
||||||
waitForSendTyping: false,
|
|
||||||
attachment: undefined,
|
|
||||||
eventProxyHandler: {
|
eventProxyHandler: {
|
||||||
set: () => true,
|
set: () => true,
|
||||||
get: (target, key) => {
|
get: (target, key) => {
|
||||||
if (typeof target[key] === 'object') return new Proxy(Object.assign({}, target[key]), this.eventProxyHandler);
|
if (typeof target[key] === 'object') return new Proxy(Object.assign({}, target[key]), this.eventProxyHandler);
|
||||||
return target[key];
|
return target[key];
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
showEmojiPicker: false,
|
||||||
|
waitForSendTyping: false,
|
||||||
|
attachment: undefined,
|
||||||
|
isSending: false
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
updated() {
|
updated() {
|
||||||
this.resizeMessageBanner();
|
this.$nextTick(this.resizeMessageBanner);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
import {cookieHandler} from '@/lib/cookieHandler';
|
import {cookieHandler} from '@/lib/cookieHandler';
|
||||||
|
import {Capacitor, Plugins} from '@capacitor/core';
|
||||||
|
const {Storage} = Plugins;
|
||||||
|
|
||||||
export class DataStore{
|
export class DataStore{
|
||||||
constructor(){
|
constructor(){
|
||||||
@ -6,17 +8,14 @@ export class DataStore{
|
|||||||
this.cookie.setExpire(15);
|
this.cookie.setExpire(15);
|
||||||
this.store = localStorage;
|
this.store = localStorage;
|
||||||
}
|
}
|
||||||
set(key, value){
|
async set(key, value){
|
||||||
this.cookie.set(key, value);
|
if (Capacitor.isNative) return await Storage.set({key, value: JSON.stringify(value)});
|
||||||
|
this.store.setItem(key, JSON.stringify(value));
|
||||||
|
this.cookie.set(key, JSON.stringify(value));
|
||||||
this.cookie.store();
|
this.cookie.store();
|
||||||
this.store.setItem(key, value);
|
|
||||||
}
|
}
|
||||||
get(key){
|
async get(key){
|
||||||
return this.store.getItem(key) || this.cookie.get(key);
|
if (Capacitor.isNative) return JSON.parse((await Storage.get({key})).value||'null');
|
||||||
}
|
return JSON.parse(this.store.getItem(key) || this.cookie.get(key) || 'null');
|
||||||
setObj(obj){
|
|
||||||
this.cookie.setCookies(obj);
|
|
||||||
this.cookie.store();
|
|
||||||
Object.keys(obj).forEach(key => this.store.setItem(key, obj[key]));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -2,6 +2,8 @@ import {getMxcFromUserId, getPreviewUrl} from '@/lib/getMxc';
|
|||||||
import {calcUserName} from '@/lib/matrixUtils';
|
import {calcUserName} from '@/lib/matrixUtils';
|
||||||
import {getRoom} from '@/lib/matrixUtils';
|
import {getRoom} from '@/lib/matrixUtils';
|
||||||
import {router} from '@/router';
|
import {router} from '@/router';
|
||||||
|
import {Capacitor, Plugins} from '@capacitor/core';
|
||||||
|
const {LocalNotifications} = Plugins;
|
||||||
|
|
||||||
export class NotificationHandler{
|
export class NotificationHandler{
|
||||||
constructor() {
|
constructor() {
|
||||||
@ -17,6 +19,7 @@ export class NotificationHandler{
|
|||||||
.then(permission => {return permission === 'granted'});
|
.then(permission => {return permission === 'granted'});
|
||||||
}
|
}
|
||||||
showNotification(event){
|
showNotification(event){
|
||||||
|
if (Capacitor.isNative) return this.showNativeNotification(event);
|
||||||
if (Notification.permission !== 'granted') return false;
|
if (Notification.permission !== 'granted') return false;
|
||||||
console.log(event);
|
console.log(event);
|
||||||
let mxc = getMxcFromUserId(event.sender);
|
let mxc = getMxcFromUserId(event.sender);
|
||||||
@ -25,4 +28,20 @@ export class NotificationHandler{
|
|||||||
icon: mxc?getPreviewUrl(mxc):undefined
|
icon: mxc?getPreviewUrl(mxc):undefined
|
||||||
}).onclick = ()=>router.push(`/rooms/${event.room_id}`);
|
}).onclick = ()=>router.push(`/rooms/${event.room_id}`);
|
||||||
}
|
}
|
||||||
|
showNativeNotification(event){
|
||||||
|
LocalNotifications.schedule({
|
||||||
|
notifications: [
|
||||||
|
{
|
||||||
|
title: `${calcUserName(event.sender)} in ${getRoom(event.room_id).name}`,
|
||||||
|
body: event.content.body,
|
||||||
|
id: 1,
|
||||||
|
schedule: { at: new Date(Date.now() + 1000 * 5) },
|
||||||
|
sound: null,
|
||||||
|
attachments: null,
|
||||||
|
actionTypeId: '',
|
||||||
|
extra: null
|
||||||
|
}
|
||||||
|
]
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
31
src/main.js
31
src/main.js
@ -10,18 +10,21 @@ Vue.use(VueRouter);
|
|||||||
|
|
||||||
export let matrix = new MatrixHandler();
|
export let matrix = new MatrixHandler();
|
||||||
|
|
||||||
let store = new DataStore();
|
(async () => {
|
||||||
|
let login = await new DataStore().get('login');
|
||||||
if (store.get('baseUrl') && store.get('accessToken') && store.get('userId')) {
|
if (login && login.baseUrl && login.accessToken && login.userId) {
|
||||||
matrix.tokenLogin(store.get('baseUrl'), store.get('accessToken'), store.get('userId'));
|
matrix.tokenLogin(login.baseUrl, login.accessToken, login.userId);
|
||||||
}
|
|
||||||
|
|
||||||
new Vue({
|
|
||||||
el: '#app',
|
|
||||||
router,
|
|
||||||
template: '<App/>',
|
|
||||||
components: {App},
|
|
||||||
data() {
|
|
||||||
return {}
|
|
||||||
}
|
}
|
||||||
}).$mount('#app');
|
|
||||||
|
new Vue({
|
||||||
|
el: '#app',
|
||||||
|
router,
|
||||||
|
template: '<App/>',
|
||||||
|
components: {App},
|
||||||
|
data() {
|
||||||
|
return {}
|
||||||
|
}
|
||||||
|
}).$mount('#app');
|
||||||
|
})()
|
||||||
|
|
||||||
|
|
||||||
|
@ -9,7 +9,7 @@ export const router = new VueRouter({
|
|||||||
{
|
{
|
||||||
path: '/',
|
path: '/',
|
||||||
name: 'home',
|
name: 'home',
|
||||||
component: login
|
component: rooms
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: '/login',
|
path: '/login',
|
||||||
|
@ -25,6 +25,7 @@ import {matrix} from '@/main.js';
|
|||||||
import ThrobberOverlay from '@/components/throbberOverlay';
|
import ThrobberOverlay from '@/components/throbberOverlay';
|
||||||
import {isValidUserId} from '@/lib/matrixUtils';
|
import {isValidUserId} from '@/lib/matrixUtils';
|
||||||
import {DataStore} from '@/lib/DataStore';
|
import {DataStore} from '@/lib/DataStore';
|
||||||
|
const store = new DataStore();
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
name: 'login.vue',
|
name: 'login.vue',
|
||||||
@ -34,25 +35,14 @@ export default {
|
|||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
login(){
|
login(){
|
||||||
if (matrix.client !== undefined) {
|
// eslint-disable-next-line no-cond-assign
|
||||||
this.loginError = 'you are already logged in';
|
if (this.loginError = this.getInputErrors()) return false;
|
||||||
return;
|
|
||||||
} if (this.user === '') {
|
|
||||||
this.loginError = 'username is empty';
|
|
||||||
return;
|
|
||||||
} if (this.password === '') {
|
|
||||||
this.loginError = 'password is empty';
|
|
||||||
return;
|
|
||||||
} if (!isValidUserId(this.user)) {
|
|
||||||
this.loginError = 'username is in wrong style';
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
this.loading = 'logging in';
|
this.loading = 'logging in';
|
||||||
matrix.login(this.user, this.password, this.homeServer, (error) => {
|
matrix.login(this.user, this.password, this.homeServer, (error) => {
|
||||||
this.loginError = `login failed: ${error}`;
|
this.loginError = `login failed: ${error}`;
|
||||||
this.loading = false;
|
this.loading = false;
|
||||||
}, token => {
|
}, token => {
|
||||||
this.store.setObj({
|
this.store.set('login', {
|
||||||
baseUrl: this.homeServer,
|
baseUrl: this.homeServer,
|
||||||
userId: this.user,
|
userId: this.user,
|
||||||
accessToken: token
|
accessToken: token
|
||||||
@ -64,14 +54,17 @@ export default {
|
|||||||
async logout(){
|
async logout(){
|
||||||
this.loading = 'logging out';
|
this.loading = 'logging out';
|
||||||
await matrix.logout();
|
await matrix.logout();
|
||||||
this.store.setObj({
|
this.store.set('login', {});
|
||||||
baseUrl: undefined,
|
|
||||||
userId: undefined,
|
|
||||||
accessToken: undefined
|
|
||||||
});
|
|
||||||
this.loading = false;
|
this.loading = false;
|
||||||
this.$forceUpdate();
|
this.$forceUpdate();
|
||||||
},
|
},
|
||||||
|
getInputErrors(){
|
||||||
|
if (matrix.client !== undefined) return 'you are already logged in';
|
||||||
|
if (this.user === '') return 'username is empty';
|
||||||
|
if (this.password === '') return 'password is empty';
|
||||||
|
if (!isValidUserId(this.user)) return 'username is in wrong style';
|
||||||
|
return false;
|
||||||
|
},
|
||||||
showLogin(){
|
showLogin(){
|
||||||
return matrix.client === undefined;
|
return matrix.client === undefined;
|
||||||
}
|
}
|
||||||
@ -82,7 +75,7 @@ export default {
|
|||||||
password: '',
|
password: '',
|
||||||
homeServer: 'https://adb.sh',
|
homeServer: 'https://adb.sh',
|
||||||
loginError: '',
|
loginError: '',
|
||||||
store: new DataStore(),
|
store,
|
||||||
loading: false
|
loading: false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user