Small fixes and code cleanup

- Fix "false" showing in username field.
 - Delay showing the window until the page is rendered to prevent flashing
 - Fix various issues highlighted by Webstorm's inspections.
This commit is contained in:
Keith Maika 2022-03-28 15:25:49 -04:00
parent 2697d61ab1
commit 50c0978148
No known key found for this signature in database
GPG Key ID: F71740E8722C75F1
13 changed files with 104 additions and 181 deletions

View File

@ -1,4 +1,4 @@
<h2 align="center"> <h2 style="text-align: center">
<a href="https://conversejs.org" target="_blank" rel="noopener"> <a href="https://conversejs.org" target="_blank" rel="noopener">
<img alt="Converse-Desktop" src="https://github.com/conversejs/converse.js/blob/master/logo/readme.png" width="480"> <img alt="Converse-Desktop" src="https://github.com/conversejs/converse.js/blob/master/logo/readme.png" width="480">
</a> </a>
@ -12,9 +12,9 @@
A basic integration of [Converse.js](https://conversejs.org/) and Electron. With OMEMO. A basic integration of [Converse.js](https://conversejs.org/) and Electron. With OMEMO.
## Screenshots and feautures ## Screenshots and features
<p float="left"> <p>
<img width="403" alt="Account form" src="https://user-images.githubusercontent.com/1450983/89672948-33bc0e80-d8ee-11ea-983f-21bbb707b45d.png"> <img width="403" alt="Account form" src="https://user-images.githubusercontent.com/1450983/89672948-33bc0e80-d8ee-11ea-983f-21bbb707b45d.png">
<img width="403" alt="Main window" src="https://user-images.githubusercontent.com/1450983/89673019-4f271980-d8ee-11ea-8058-0ac6269983aa.png"> <img width="403" alt="Main window" src="https://user-images.githubusercontent.com/1450983/89673019-4f271980-d8ee-11ea-8058-0ac6269983aa.png">
<img width="403" alt="Chat" src="https://user-images.githubusercontent.com/1450983/89673064-68c86100-d8ee-11ea-86c4-137e1b95dae7.png"> <img width="403" alt="Chat" src="https://user-images.githubusercontent.com/1450983/89673064-68c86100-d8ee-11ea-86c4-137e1b95dae7.png">
@ -33,12 +33,12 @@ See [CHANGES.md](https://github.com/conversejs/converse-desktop/blob/master/CHAN
#### Latest release installers #### Latest release installers
| Operation System | Download link | | Operation System | Download link |
-------------------|---------------- |------------------|------------------------------------------------------------------------------------------------------------------------------------------------------|
| macOS | [Converse_Desktop-0.1.0_x64.dmg](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/Converse_Desktop-0.1.0_x64.dmg) | | macOS | [Converse_Desktop-0.1.0_x64.dmg](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/Converse_Desktop-0.1.0_x64.dmg) |
| Windows | [Converse_Desktop_Setup-0.1.0_x64.exe](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/Converse_Desktop_Setup-0.1.0_x64.exe) | | Windows | [Converse_Desktop_Setup-0.1.0_x64.exe](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/Converse_Desktop_Setup-0.1.0_x64.exe) |
| Linux DEB | [converse_desktop-0.1.0_amd64.deb](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/converse_desktop-0.1.0_amd64.deb) | | Linux DEB | [converse_desktop-0.1.0_amd64.deb](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/converse_desktop-0.1.0_amd64.deb) |
| Linux other | [converse_desktop-0.1.0_x64.tar.gz](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/converse_desktop-0.1.0_x64.tar.gz) | | Linux other | [converse_desktop-0.1.0_x64.tar.gz](https://github.com/conversejs/converse-desktop/releases/download/v0.1.0/converse_desktop-0.1.0_x64.tar.gz) |
- [All releases](https://github.com/conversejs/converse-desktop/releases) - [All releases](https://github.com/conversejs/converse-desktop/releases)
@ -60,10 +60,10 @@ npm start
### Build targets: ### Build targets:
| Operation System | Target | | Operation System | Target |
-------------------|---------------- |------------------|---------------------------|
| macOS | `npm run dist` | | macOS | `npm run dist` |
| Windows | `npm run dist:win64` | | Windows | `npm run dist:win64` |
| Linux DEB | `npm run dist:linux64deb` | | Linux DEB | `npm run dist:linux64deb` |
More targets could be added via `package.json`. See [electron builder docs](https://www.electron.build/configuration/configuration). More targets could be added via `package.json`. See [electron builder docs](https://www.electron.build/configuration/configuration).
@ -84,5 +84,5 @@ under the MPLv2.
This project started as a fork of Nick Denry's [Chimeverse](https://github.com/conversejs/converse-desktop). This project started as a fork of Nick Denry's [Chimeverse](https://github.com/conversejs/converse-desktop).
<a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=6MZ5YRYEDSVSQ&source=url" title="Donate once-off to this project using Paypal"> <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=6MZ5YRYEDSVSQ&source=url" title="Donate once-off to this project using Paypal">
<img src="https://img.shields.io/badge/paypal-donate-yellow.svg" alt="PayPayl donate button" /> <img src="https://img.shields.io/badge/paypal-donate-yellow.svg" alt="PayPal donate button" />
</a> </a>

View File

@ -2,9 +2,9 @@ const credentials = await import('../credentials.js');
converse.plugins.add('converse-desktop-credentials', { converse.plugins.add('converse-desktop-credentials', {
initialize () { initialize() {
const { _converse } = this; const {_converse} = this;
const { api } = _converse; const {api} = _converse;
api.listen.on('afterResourceBinding', () => { api.listen.on('afterResourceBinding', () => {
if (_converse.connection.pass) { if (_converse.connection.pass) {
@ -12,7 +12,9 @@ converse.plugins.add('converse-desktop-credentials', {
_converse.connection.service, _converse.connection.service,
_converse.bare_jid, _converse.bare_jid,
_converse.connection.pass _converse.connection.pass
); ).catch((reason) => {
console.log(reason);
});
} }
}); });

View File

@ -6,9 +6,9 @@ converse.plugins.add('converse-desktop-trayicon', {
const {_converse} = this; const {_converse} = this;
let envelopeIsShowing = false; let envelopeIsShowing = false;
function hideEnvelope() { async function hideEnvelope() {
if (envelopeIsShowing) { if (envelopeIsShowing) {
api.trayService.hideEnvelope(); await api.trayService.hideEnvelope();
envelopeIsShowing = false; envelopeIsShowing = false;
} }
} }
@ -16,8 +16,8 @@ converse.plugins.add('converse-desktop-trayicon', {
window.addEventListener('focus', hideEnvelope); window.addEventListener('focus', hideEnvelope);
_converse.api.listen.on('chatBoxInitialized', hideEnvelope); _converse.api.listen.on('chatBoxInitialized', hideEnvelope);
_converse.api.listen.on('chatBoxFocused', hideEnvelope); _converse.api.listen.on('chatBoxFocused', hideEnvelope);
_converse.api.listen.on('messageNotification', () => { _converse.api.listen.on('messageNotification', async () => {
api.trayService.showEnvelope(); await api.trayService.showEnvelope();
envelopeIsShowing = true; envelopeIsShowing = true;
}); });
} }

View File

@ -9,7 +9,7 @@ async function addCredentials(connectionManager, login, password) {
async function getCredentials() { async function getCredentials() {
const credentials = {} const credentials = {}
credentials.login = await api.settings.get('login') credentials.login = (await api.settings.get('login')) || '';
if (credentials.login) { if (credentials.login) {
credentials.connectionManager = await api.settings.get('connectionManager') || null credentials.connectionManager = await api.settings.get('connectionManager') || null
credentials.xmppService = credentials.login.split('@').pop() credentials.xmppService = credentials.login.split('@').pop()

View File

@ -6,9 +6,6 @@
<link rel="stylesheet" type="text/css" media="screen" href="node_modules/open-iconic/font/css/open-iconic.css"> <link rel="stylesheet" type="text/css" media="screen" href="node_modules/open-iconic/font/css/open-iconic.css">
<link rel="stylesheet" type="text/css" media="screen" href="node_modules/converse.js/dist/converse.min.css"> <link rel="stylesheet" type="text/css" media="screen" href="node_modules/converse.js/dist/converse.min.css">
<link rel="stylesheet" type="text/css" href="resources/css/app.css"> <link rel="stylesheet" type="text/css" href="resources/css/app.css">
<link rel="stylesheet" type="text/css" href="resources/css/_footer.css">
<link rel="stylesheet" type="text/css" href="resources/css/page-default.css">
<link rel="stylesheet" type="text/css" href="resources/css/page-settings.css">
</head> </head>
<base href="./"> <base href="./">
<body class="converse-fullscreen"> <body class="converse-fullscreen">

51
main.js
View File

@ -1,5 +1,5 @@
// Modules to control application life and create native browser window // Modules to control application life and create native browser window
const { app, BrowserWindow, ipcMain, shell } = require('electron') const {app, BrowserWindow, ipcMain, shell} = require('electron')
const path = require('path'); const path = require('path');
// Keep a global reference of the window object, if you don't, the window will // Keep a global reference of the window object, if you don't, the window will
@ -7,9 +7,9 @@ const path = require('path');
let mainWindow let mainWindow
// Require other app modules // Require other app modules
const trayService = require(__dirname+'/modules/tray-service') const trayService = require(__dirname + '/modules/tray-service')
const menuService = require(__dirname+'/modules/menu-service') const menuService = require(__dirname + '/modules/menu-service')
const settingsService = require(__dirname+'/modules/settings-service') const settingsService = require(__dirname + '/modules/settings-service')
const isMac = process.platform === 'darwin' const isMac = process.platform === 'darwin'
const isWin = process.platform === 'win32' const isWin = process.platform === 'win32'
@ -26,10 +26,11 @@ function initApp() {
} }
} }
function createWindow () { function createWindow() {
// Main window options // Main window options
const mainWindowOptions = { const mainWindowOptions = {
zoomToPageWidth: true, zoomToPageWidth: true,
show: false,
webPreferences: { webPreferences: {
preload: path.join(__dirname, 'preload.js') preload: path.join(__dirname, 'preload.js')
}, },
@ -38,13 +39,12 @@ function createWindow () {
// Create the browser window. // Create the browser window.
mainWindow = new BrowserWindow(mainWindowOptions) mainWindow = new BrowserWindow(mainWindowOptions)
mainWindow.maximize();
// Init tray // Init tray
trayService.initTray(mainWindow) trayService.initTray(mainWindow)
// Init menu // Init menu
menuService.createMenu() menuService.createMenu(mainWindow)
// Open the DevTools. // Open the DevTools.
// mainWindow.webContents.openDevTools() // mainWindow.webContents.openDevTools()
@ -61,7 +61,7 @@ function createWindow () {
// Handle shutdown event on Mac with minimizeOnClose // Handle shutdown event on Mac with minimizeOnClose
// to prevent shutdown interrupt // to prevent shutdown interrupt
if (isMac) { if (isMac) {
const { powerMonitor } = require('electron') const {powerMonitor} = require('electron')
powerMonitor.on('shutdown', () => { powerMonitor.on('shutdown', () => {
app.isQuitting = true app.isQuitting = true
app.quit() app.quit()
@ -69,10 +69,9 @@ function createWindow () {
} }
// Handle restart // Handle restart
ipcMain.on('app-restart', () => { ipcMain.on('app-quit', () => {
app.isQuitting = true app.isQuitting = true
app.relaunch() app.quit();
app.exit()
}) })
// Emitted when the window is closed. // Emitted when the window is closed.
@ -84,9 +83,11 @@ function createWindow () {
}) })
// Open links on system default browser // Open links on system default browser
mainWindow.webContents.on('new-window', function(e, url) { mainWindow.webContents.setWindowOpenHandler(function (details) {
e.preventDefault() shell.openExternal(details.url).catch((reason) => {
shell.openExternal(url) console.log(reason);
});
return {action: 'deny'};
}) })
ipcMain.handle('settings', (e, method, ...args) => { ipcMain.handle('settings', (e, method, ...args) => {
@ -97,8 +98,16 @@ function createWindow () {
return trayService[method].apply(trayService, args); return trayService[method].apply(trayService, args);
}); });
mainWindow.on('ready-to-show', () => {
mainWindow.maximize();
});
// and load the index.html of the app. // and load the index.html of the app.
mainWindow.loadFile('index.html') mainWindow.loadFile('index.html').catch((reason) => {
console.log(reason);
app.isQuitting = true;
app.quit();
});
} }
// This method will be called when Electron has finished // This method will be called when Electron has finished
@ -108,7 +117,7 @@ app.on('ready', initApp)
// Quit when all windows are closed. // Quit when all windows are closed.
app.on('window-all-closed', function () { app.on('window-all-closed', function () {
// On macOS it is common for applications and their menu bar // On macOS, it is common for applications and their menu bar
// to stay active until the user quits explicitly with Cmd + Q // to stay active until the user quits explicitly with Cmd + Q
// if (process.platform !== 'darwin') // if (process.platform !== 'darwin')
// ^^^^ NOPE ;) // ^^^^ NOPE ;)
@ -117,7 +126,7 @@ app.on('window-all-closed', function () {
}) })
app.on('activate', function () { app.on('activate', function () {
if (mainWindow === null){ if (mainWindow === null) {
createWindow() createWindow()
} else { } else {
mainWindow.show(); mainWindow.show();
@ -131,11 +140,5 @@ app.on('second-instance', function () {
// In this file you can include the rest of your app's specific main process // In this file you can include the rest of your app's specific main process
// code. You can also put them in separate files and require them here. // code. You can also put them in separate files and require them here.
// Allow to play audio automatically // Allow audio to play automatically
app.commandLine.appendSwitch('autoplay-policy', 'no-user-gesture-required') app.commandLine.appendSwitch('autoplay-policy', 'no-user-gesture-required')
/**
* Export functions
*/
exports.trayService = trayService

View File

@ -1,13 +1,13 @@
/** /**
* Module for Menu functions. * Module for Menu functions.
*/ */
const {app, Menu, MenuItem, BrowserWindow} = require('electron') const {app, Menu, MenuItem} = require('electron')
const settingsService = require(__dirname + '/../modules/settings-service') const settingsService = require(__dirname + '/../modules/settings-service')
const menuService = {} const menuService = {}
menuService.createMenu = () => { menuService.createMenu = (window) => {
let converse; let converse;
const application = new Menu(); const application = new Menu();
application.append(new MenuItem({ application.append(new MenuItem({
@ -17,9 +17,8 @@ menuService.createMenu = () => {
label: 'Reconnect', label: 'Reconnect',
accelerator: 'CmdOrCtrl+R', accelerator: 'CmdOrCtrl+R',
click: () => { click: () => {
const activeWindow = BrowserWindow.getAllWindows()[0] window.show()
activeWindow.show() window.reload()
activeWindow.reload()
} }
}, },
{ {
@ -87,8 +86,7 @@ menuService.createMenu = () => {
label: 'Debug info', label: 'Debug info',
accelerator: 'F12', accelerator: 'F12',
click: () => { click: () => {
const activeWindow = BrowserWindow.getAllWindows()[0] window.webContents.openDevTools()
activeWindow.webContents.openDevTools()
} }
} }
]) ])

View File

@ -2,19 +2,15 @@ const {ipcRenderer, contextBridge} = require('electron');
const keytar = require('keytar'); const keytar = require('keytar');
contextBridge.exposeInMainWorld('api', { contextBridge.exposeInMainWorld('api', {
reload() {
ipcRenderer.send('reload')
},
settings: { settings: {
has(setting) { has(setting) {
return ipcRenderer.invoke('settings', 'has', setting); return ipcRenderer.invoke('settings', 'has', setting);
}, },
set(setting, value) { set(setting, value) {
ipcRenderer.invoke('settings', 'set', setting, value); return ipcRenderer.invoke('settings', 'set', setting, value);
}, },
unset(setting) { unset(setting) {
ipcRenderer.invoke('settings', 'unset', setting); return ipcRenderer.invoke('settings', 'unset', setting);
}, },
get(setting) { get(setting) {
return ipcRenderer.invoke('settings', 'get', setting); return ipcRenderer.invoke('settings', 'get', setting);
@ -22,10 +18,10 @@ contextBridge.exposeInMainWorld('api', {
}, },
trayService: { trayService: {
showEnvelope() { showEnvelope() {
ipcRenderer.invoke('trayService', 'showEnvelope'); return ipcRenderer.invoke('trayService', 'showEnvelope');
}, },
hideEnvelope() { hideEnvelope() {
ipcRenderer.invoke('trayService', 'hideEnvelope'); return ipcRenderer.invoke('trayService', 'hideEnvelope');
} }
}, },
keytar: { keytar: {
@ -38,5 +34,10 @@ contextBridge.exposeInMainWorld('api', {
deletePassword(service, login) { deletePassword(service, login) {
return keytar.deletePassword(service, login); return keytar.deletePassword(service, login);
} }
},
app: {
quit() {
ipcRenderer.send('app-quit');
}
} }
}); });

View File

@ -1,15 +0,0 @@
.page__footer {
bottom: 20px;
color: #777;
display: flex;
left: 50%;
position: absolute;
text-align: center;
transform: translate(-50%, 0%);
}
.footer__version {
font-size: 13px;
margin-right: 30px;
}

View File

@ -1,7 +1,3 @@
[ng\:cloak], [ng-cloak], [data-ng-cloak], [x-ng-cloak], .ng-cloak, .x-ng-cloak {
display: none !important;
}
.noselect { .noselect {
-webkit-touch-callout: none; /* iOS Safari */ -webkit-touch-callout: none; /* iOS Safari */
-webkit-user-select: none; /* Safari */ -webkit-user-select: none; /* Safari */
@ -24,8 +20,8 @@ a {
background: transparent; background: transparent;
pointer-events: none; pointer-events: none;
position: fixed; position: fixed;
left: 0px; left: 0;
top: 0px; top: 0;
width: 100%; width: 100%;
height: 100%; height: 100%;
} }

View File

@ -1,44 +0,0 @@
.chimeverse-branding {
left: 50%;
position: absolute;
top: 50%;
transform: translate(-50%, -50%);
text-align: center;
}
.chimeverse-branding__img {
margin-left: 20px;
}
.chimeverse-branding__header {
font-size: 26px;
font-weight: normal;
color: #999;
margin: 0px;
}
.chimeverse-branding__version {
font-size: 12px;
color: #999;
margin-top: 10px;
}
.update__latest {
background: #bbb;
color: #fff;
border-radius: 3px;
padding: 3px 5px;
}
.update__available {
background: rgb(5,93,228);
background: linear-gradient(0deg, rgba(5,93,228,1) 0%, rgba(76,145,255,1) 100%);
padding: 3px 5px;
color: #fff;
text-decoration: none;
border-radius: 3px;
}
.update__error {
color: #da0000;
}

View File

@ -1,16 +0,0 @@
.settings-page {
padding: 0px 20px 0px 20px;
}
.form-item {
margin-bottom: 15px;
}
.form-item__hint {
color: #777;
font-size: 13px;
}
.form-item__save-button.active {
color: blue;
}

View File

@ -1,44 +1,45 @@
/* global api */
await import('./app/converse-plugins/desktop-credentials.js') await import('./app/converse-plugins/desktop-credentials.js')
await import('./app/converse-plugins/desktop-trayicon.js') await import('./app/converse-plugins/desktop-trayicon.js')
const getCredentials = (await import('./app/credentials.js')).getCredentials; const getCredentials = (await import('./app/credentials.js')).getCredentials;
async function initialize () { let websocket_url, bosh_service_url;
let websocket_url, bosh_service_url; const {connectionManager, login, password} = await getCredentials()
const { connectionManager, login, password } = await getCredentials()
if (connectionManager?.startsWith('ws')) { if (connectionManager?.startsWith('ws')) {
websocket_url = connectionManager websocket_url = connectionManager
} else if (connectionManager?.startsWith('http')) { } else if (connectionManager?.startsWith('http')) {
bosh_service_url = connectionManager bosh_service_url = connectionManager
}
converse.plugins.add('converse-debug', {
initialize () {
const { _converse } = this;
window._converse = _converse;
}
});
converse.initialize({
assets_path: './node_modules/converse.js/dist/',
auto_login: login && password,
bosh_service_url,
i18n: navigator.language,
jid: login,
loglevel: 'debug',
muc_respect_autojoin: true,
muc_show_logs_before_join: true,
password: password,
play_sounds: false,
priority: 50,
prune_messages_above: 250,
theme: 'concord',
view_mode: 'fullscreen',
websocket_url,
whitelisted_plugins: ['converse-debug', 'converse-desktop-credentials', 'converse-desktop-trayicon'],
show_connection_url_input: true
});
} }
initialize(); converse.plugins.add('converse-debug', {
initialize() {
const {_converse} = this;
window._converse = _converse;
}
});
converse.initialize({
assets_path: './node_modules/converse.js/dist/',
auto_login: login && password,
bosh_service_url,
i18n: navigator.language,
jid: login,
loglevel: 'debug',
muc_respect_autojoin: true,
muc_show_logs_before_join: true,
password: password,
play_sounds: false,
priority: 50,
prune_messages_above: 250,
theme: 'concord',
view_mode: 'fullscreen',
websocket_url,
whitelisted_plugins: ['converse-debug', 'converse-desktop-credentials', 'converse-desktop-trayicon'],
show_connection_url_input: true
}).catch((reason) => {
console.log(reason);
api.app.quit();
});