From 55f9c2737ff57a96d2c8896b6e7cfbf17fd8811e Mon Sep 17 00:00:00 2001 From: WolverinDEV Date: Sun, 10 Jan 2021 16:26:45 +0100 Subject: [PATCH] Some app cleanups --- shared/js/ConnectionManager.ts | 73 ++++------- shared/js/KeyControl.ts | 75 +++++++----- shared/js/bookmarks.ts | 4 +- shared/js/connection/CommandHandler.ts | 2 +- .../js/events/ClientGlobalControlHandler.ts | 4 +- shared/js/file/LocalAvatars.ts | 4 +- shared/js/file/LocalIcons.ts | 2 +- shared/js/main.tsx | 114 ++++++++---------- shared/js/stats.ts | 8 +- shared/js/text/bbcode/youtube.tsx | 4 +- shared/js/ui/AppController.ts | 2 +- .../connection-handler-list/Controller.ts | 6 +- shared/js/ui/frames/control-bar/Controller.ts | 18 +-- shared/js/ui/frames/footer/Renderer.tsx | 2 +- shared/js/ui/frames/menu-bar/MainMenu.ts | 18 +-- shared/js/ui/htmltags.ts | 4 +- shared/js/ui/modal/connect/Controller.ts | 6 +- shared/js/ui/modal/settings/Keymap.tsx | 2 +- .../ui/modal/transfer/ModalFileTransfer.tsx | 4 +- 19 files changed, 159 insertions(+), 193 deletions(-) diff --git a/shared/js/ConnectionManager.ts b/shared/js/ConnectionManager.ts index 6f434880..f86c448b 100644 --- a/shared/js/ConnectionManager.ts +++ b/shared/js/ConnectionManager.ts @@ -1,25 +1,7 @@ import {ConnectionHandler, DisconnectReason} from "./ConnectionHandler"; import {Registry} from "./events"; -import * as loader from "tc-loader"; import {Stage} from "tc-loader"; - -export let server_connections: ConnectionManager; - -class ReplaceableContainer { - placeholder: HTMLDivElement; - container: HTMLDivElement; - - constructor(container: HTMLDivElement, placeholder?: HTMLDivElement) { - this.container = container; - this.placeholder = placeholder || document.createElement("div"); - } - - replaceWith(target: HTMLDivElement | undefined) { - target = target || this.placeholder; - this.container.replaceWith(target); - this.container = target; - } -} +import * as loader from "tc-loader"; export interface ConnectionManagerEvents { notify_handler_created: { @@ -51,22 +33,18 @@ export class ConnectionManager { private connectionHandlers: ConnectionHandler[] = []; private activeConnectionHandler: ConnectionHandler | undefined; - private containerChannelVideo: ReplaceableContainer; - constructor() { this.events_ = new Registry(); this.events_.enableDebug("connection-manager"); - /* FIXME! */ - this.containerChannelVideo = new ReplaceableContainer(document.getElementById("channel-video") as HTMLDivElement); - this.set_active_connection(undefined); + this.setActiveConnectionHandler(undefined); } events() : Registry { return this.events_; } - spawn_server_connection() : ConnectionHandler { + spawnConnectionHandler() : ConnectionHandler { const handler = new ConnectionHandler(); handler.initialize_client_state(this.activeConnectionHandler); this.connectionHandlers.push(handler); @@ -75,7 +53,7 @@ export class ConnectionManager { return handler; } - destroy_server_connection(handler: ConnectionHandler) { + destroyConnectionHandler(handler: ConnectionHandler) { if(this.connectionHandlers.length <= 1) { throw "cannot deleted the last connection handler"; } @@ -91,7 +69,7 @@ export class ConnectionManager { } if(handler === this.activeConnectionHandler) { - this.set_active_connection_(this.connectionHandlers[0]); + this.doSetActiveConnectionHandler(this.connectionHandlers[0]); } this.events_.fire("notify_handler_deleted", { handler: handler, handlerId: handler.handlerId }); @@ -99,7 +77,7 @@ export class ConnectionManager { handler.destroy(); } - set_active_connection(handler: ConnectionHandler) { + setActiveConnectionHandler(handler: ConnectionHandler) { if(handler && this.connectionHandlers.indexOf(handler) == -1) { throw "Handler hasn't been registered or is already obsolete!"; } @@ -108,7 +86,21 @@ export class ConnectionManager { return; } - this.set_active_connection_(handler); + this.doSetActiveConnectionHandler(handler); + } + + private doSetActiveConnectionHandler(handler: ConnectionHandler) { + const oldHandler = this.activeConnectionHandler; + this.activeConnectionHandler = handler; + this.events_.fire("notify_active_handler_changed", { + oldHandler: oldHandler, + newHandler: handler, + + oldHandlerId: oldHandler?.handlerId, + newHandlerId: handler?.handlerId + }); + oldHandler?.events().fire("notify_visibility_changed", { visible: false }); + handler?.events().fire("notify_visibility_changed", { visible: true }); } swapHandlerOrder(handlerA: ConnectionHandler, handlerB: ConnectionHandler) { @@ -125,37 +117,20 @@ export class ConnectionManager { this.events().fire("notify_handler_order_changed"); } - private set_active_connection_(handler: ConnectionHandler) { -/* - this.containerChannelVideo.replaceWith(handler?.video_frame.getContainer()); -*/ - - const oldHandler = this.activeConnectionHandler; - this.activeConnectionHandler = handler; - this.events_.fire("notify_active_handler_changed", { - oldHandler: oldHandler, - newHandler: handler, - - oldHandlerId: oldHandler?.handlerId, - newHandlerId: handler?.handlerId - }); - oldHandler?.events().fire("notify_visibility_changed", { visible: false }); - handler?.events().fire("notify_visibility_changed", { visible: true }); - } - findConnection(handlerId: string) : ConnectionHandler | undefined { return this.connectionHandlers.find(e => e.handlerId === handlerId); } - active_connection() : ConnectionHandler | undefined { + getActiveConnectionHandler() : ConnectionHandler | undefined { return this.activeConnectionHandler; } - all_connections() : ConnectionHandler[] { + getAllConnectionHandlers() : ConnectionHandler[] { return this.connectionHandlers; } } +export let server_connections: ConnectionManager; loader.register_task(Stage.JAVASCRIPT_INITIALIZING, { name: "server manager init", function: async () => { diff --git a/shared/js/KeyControl.ts b/shared/js/KeyControl.ts index ea1c4e47..cea12bab 100644 --- a/shared/js/KeyControl.ts +++ b/shared/js/KeyControl.ts @@ -1,10 +1,10 @@ -import {EventType, KeyDescriptor, KeyEvent, KeyHook} from "./PPTListener"; import * as ppt from "tc-backend/ppt"; -import {Settings, settings} from "./settings"; import * as log from "./log"; -import {LogCategory} from "./log"; +import {LogCategory, logWarn} from "./log"; +import {KeyDescriptor, KeyHook} from "./PPTListener"; +import {Settings, settings} from "./settings"; import {server_connections} from "tc-shared/ConnectionManager"; -import { tr } from "./i18n/localize"; +import {tr} from "./i18n/localize"; export interface KeyControl { category: string; @@ -33,51 +33,51 @@ export const KeyTypes: {[key: string]:KeyControl} = { "disconnect-current": { category: "connection", description: "Disconnect from the current server", - handler: () => server_connections.active_connection()?.disconnectFromServer(), + handler: () => server_connections.getActiveConnectionHandler()?.disconnectFromServer(), icon: "client-disconnect" }, "disconnect-all": { category: "connection", description: "Disconnect from all connected servers", - handler: () => server_connections.all_connections().forEach(e => e.disconnectFromServer()), + handler: () => server_connections.getAllConnectionHandlers().forEach(e => e.disconnectFromServer()), icon: "client-disconnect" }, "toggle-microphone": { category: "microphone", description: "Toggle your microphone status", - handler: () => server_connections.active_connection()?.toggleMicrophone(), + handler: () => server_connections.getActiveConnectionHandler()?.toggleMicrophone(), icon: "client-input_muted" }, "enable-microphone": { category: "microphone", description: "Enable your microphone", - handler: () => server_connections.active_connection()?.setMicrophoneMuted(false), + handler: () => server_connections.getActiveConnectionHandler()?.setMicrophoneMuted(false), icon: "client-input_muted" }, "disable-microphone": { category: "microphone", description: "Disable your microphone", - handler: () => server_connections.active_connection()?.setMicrophoneMuted(true), + handler: () => server_connections.getActiveConnectionHandler()?.setMicrophoneMuted(true), icon: "client-input_muted" }, "toggle-speaker": { category: "speaker", description: "Toggle your speaker status", - handler: () => server_connections.active_connection()?.toggleSpeakerMuted(), + handler: () => server_connections.getActiveConnectionHandler()?.toggleSpeakerMuted(), icon: "client-output_muted" }, "enable-speaker": { category: "speaker", description: "Enable your speakers", - handler: () => server_connections.active_connection()?.setSpeakerMuted(false), + handler: () => server_connections.getActiveConnectionHandler()?.setSpeakerMuted(false), icon: "client-output_muted" }, "disable-speaker": { category: "speaker", description: "Disable your speakers", - handler: () => server_connections.active_connection()?.setSpeakerMuted(true), + handler: () => server_connections.getActiveConnectionHandler()?.setSpeakerMuted(true), icon: "client-output_muted" }, @@ -85,42 +85,42 @@ export const KeyTypes: {[key: string]:KeyControl} = { "toggle-away-state": { category: "away", description: "Toggle your away state", - handler: () => server_connections.active_connection()?.toggleAway(), + handler: () => server_connections.getActiveConnectionHandler()?.toggleAway(), icon: "client-away" }, "enable-away-state": { category: "away", description: "Enable away for the current server", - handler: () => server_connections.active_connection()?.setAway(true), + handler: () => server_connections.getActiveConnectionHandler()?.setAway(true), icon: "client-away" }, "disable-away-state": { category: "away", description: "Disable away for the current server", - handler: () => server_connections.active_connection()?.setAway(false), + handler: () => server_connections.getActiveConnectionHandler()?.setAway(false), icon: "client-present" }, "toggle-away-state-globally": { category: "away", description: "Toggle your away state for every server", - handler: () => server_connections.all_connections().forEach(e => e.toggleAway()), + handler: () => server_connections.getAllConnectionHandlers().forEach(e => e.toggleAway()), icon: "client-away" }, "enable-away-state-globally": { category: "away", description: "Enable away for every server", - handler: () => server_connections.all_connections().forEach(e => e.setAway(true)), + handler: () => server_connections.getAllConnectionHandlers().forEach(e => e.setAway(true)), icon: "client-away" }, "disable-away-state-globally": { category: "away", description: "Disable away for every server", - handler: () => server_connections.all_connections().forEach(e => e.setAway(false)), + handler: () => server_connections.getAllConnectionHandlers().forEach(e => e.setAway(false)), icon: "client-present" }, }; -let key_bindings: {[key: string]: { +let keyBindings: {[key: string]: { binding: KeyDescriptor, hook: KeyHook }} = {}; @@ -132,7 +132,7 @@ interface Config { } let config: Config; -export function initialize() { +export function initializeKeyControl() { let cfg: Config; try { cfg = JSON.parse(settings.getValue(Settings.KEY_KEYCONTROL_DATA)); @@ -149,7 +149,14 @@ export function initialize() { case 0: cfg.version = 1; cfg.keys = {}; + + /* fall though wanted */ + case 1: + /* config up to date */ + break; + default: + logWarn(LogCategory.GENERAL, tr("Key control config has an invalid version:%o"), cfg.version); break; } config = cfg; @@ -158,20 +165,21 @@ export function initialize() { if(typeof KeyTypes[key] !== "object") continue; - bind_key(key, config.keys[key]); + bindKey(key, config.keys[key]); } } -function save_config() { +function saveConfig() { settings.setValue(Settings.KEY_KEYCONTROL_DATA, JSON.stringify(config)); } -function bind_key(action: string, key: KeyDescriptor) { +function bindKey(action: string, key: KeyDescriptor) { const control = KeyTypes[action]; - if(typeof control === "undefined") + if(typeof control === "undefined") { throw "missing control event"; + } - key_bindings[action] = { + keyBindings[action] = { hook: Object.assign({ callback_press: () => control.handler(), callback_release: () => {}, @@ -179,22 +187,23 @@ function bind_key(action: string, key: KeyDescriptor) { }, key), binding: key }; - ppt.register_key_hook(key_bindings[action].hook); + ppt.register_key_hook(keyBindings[action].hook); } -export function set_key(action: string, key?: KeyDescriptor) { - if(typeof key_bindings[action] !== "undefined") { - ppt.unregister_key_hook(key_bindings[action].hook); - delete key_bindings[action]; +export function setKey(action: string, key?: KeyDescriptor) { + if(typeof keyBindings[action] !== "undefined") { + ppt.unregister_key_hook(keyBindings[action].hook); + delete keyBindings[action]; } + if(key) { - bind_key(action, key); + bindKey(action, key); config.keys[action] = key; } else { delete config.keys[action]; } - save_config(); + saveConfig(); } -export function key(action: string) : KeyDescriptor | undefined { return key_bindings[action]?.binding; } \ No newline at end of file +export function key(action: string) : KeyDescriptor | undefined { return keyBindings[action]?.binding; } \ No newline at end of file diff --git a/shared/js/bookmarks.ts b/shared/js/bookmarks.ts index 4589e43a..fa9a36f9 100644 --- a/shared/js/bookmarks.ts +++ b/shared/js/bookmarks.ts @@ -18,8 +18,8 @@ export const bookmarkEvents = new Registry(); export const boorkmak_connect = (mark: Bookmark, new_tab?: boolean) => { const profile = findConnectProfile(mark.connect_profile) || defaultConnectProfile(); if(profile.valid()) { - const connection = (typeof(new_tab) !== "boolean" || !new_tab) ? server_connections.active_connection() : server_connections.spawn_server_connection(); - server_connections.set_active_connection(connection); + const connection = (typeof(new_tab) !== "boolean" || !new_tab) ? server_connections.getActiveConnectionHandler() : server_connections.spawnConnectionHandler(); + server_connections.setActiveConnectionHandler(connection); connection.startConnection( mark.server_properties.server_address + ":" + mark.server_properties.server_port, profile, diff --git a/shared/js/connection/CommandHandler.ts b/shared/js/connection/CommandHandler.ts index ea540b54..4870a08b 100644 --- a/shared/js/connection/CommandHandler.ts +++ b/shared/js/connection/CommandHandler.ts @@ -238,7 +238,7 @@ export class ConnectionCommandHandler extends AbstractCommandHandler { if(properties.virtualserver_ask_for_privilegekey) { createInputModal(tr("Use a privilege key"), tr("This is a newly created server for which administrator privileges have not yet been claimed.
Please enter the \"privilege key\" that was automatically generated when this server was created to gain administrator permissions."), message => message.length > 0, result => { if(!result) return; - const scon = server_connections.active_connection(); + const scon = server_connections.getActiveConnectionHandler(); if(scon.serverConnection.connected) scon.serverConnection.send_command("tokenuse", { diff --git a/shared/js/events/ClientGlobalControlHandler.ts b/shared/js/events/ClientGlobalControlHandler.ts index 5268c40b..35aa1ce2 100644 --- a/shared/js/events/ClientGlobalControlHandler.ts +++ b/shared/js/events/ClientGlobalControlHandler.ts @@ -159,7 +159,7 @@ export function initialize(event_registry: Registry) break; case "server-echo-test": - const connection = event.connection || server_connections.active_connection(); + const connection = event.connection || server_connections.getActiveConnectionHandler(); if(connection) { spawnEchoTestModal(connection); } @@ -181,7 +181,7 @@ export function initialize(event_registry: Registry) }); event_registry.on("action_open_window_permissions", event => { - spawnPermissionEditorModal(event.connection ? event.connection : server_connections.active_connection(), event.defaultTab); + spawnPermissionEditorModal(event.connection ? event.connection : server_connections.getActiveConnectionHandler(), event.defaultTab); }); event_registry.on("action_toggle_video_broadcasting", event => { diff --git a/shared/js/file/LocalAvatars.ts b/shared/js/file/LocalAvatars.ts index 85671822..d525e6b1 100644 --- a/shared/js/file/LocalAvatars.ts +++ b/shared/js/file/LocalAvatars.ts @@ -338,7 +338,7 @@ export class AvatarManager extends AbstractAvatarManager { } } (window as any).flush_avatar_cache = async () => { - server_connections.all_connections().forEach(e => { + server_connections.getAllConnectionHandlers().forEach(e => { e.fileManager.avatars.flush_cache(); }); }; @@ -385,7 +385,7 @@ class LocalAvatarManagerFactory extends AbstractAvatarManagerFactory { if(message.type === "query-handlers") { this.ipcChannel.sendMessage("notify-handlers", { - handlers: server_connections.all_connections().map(e => e.handlerId) + handlers: server_connections.getAllConnectionHandlers().map(e => e.handlerId) }, remoteId); return; } else if(message.type === "load-avatar") { diff --git a/shared/js/file/LocalIcons.ts b/shared/js/file/LocalIcons.ts index 514b1b80..100df25c 100644 --- a/shared/js/file/LocalIcons.ts +++ b/shared/js/file/LocalIcons.ts @@ -226,7 +226,7 @@ class IconManager extends AbstractIconManager { logWarn(LogCategory.FILE_TRANSFER, tr("Received handler id hint for icon download, but handler %s does not exists. Trying others."), handlerIdHint); } - const connections = server_connections.all_connections() + const connections = server_connections.getAllConnectionHandlers() .filter(handler => handler.connected) .filter(handler => handler.channelTree.server.properties.virtualserver_unique_identifier === icon.serverUniqueId); diff --git a/shared/js/main.tsx b/shared/js/main.tsx index 806c98e5..7f064308 100644 --- a/shared/js/main.tsx +++ b/shared/js/main.tsx @@ -1,58 +1,52 @@ import * as loader from "tc-loader"; -import {Stage} from "tc-loader"; -import {AppParameters, settings, Settings} from "tc-shared/settings"; -import * as log from "tc-shared/log"; -import {LogCategory} from "tc-shared/log"; import * as bipc from "./ipc/BrowserIPC"; import * as sound from "./sound/Sounds"; import * as i18n from "./i18n/localize"; +import * as stats from "./stats"; +import * as fidentity from "./profiles/identities/TeaForumIdentity"; +import * as aplayer from "tc-backend/audio/player"; +import * as ppt from "tc-backend/ppt"; +import * as global_ev_handler from "./events/ClientGlobalControlHandler"; +import {Stage} from "tc-loader"; +import {AppParameters, settings, Settings} from "tc-shared/settings"; +import {LogCategory, logError, logInfo} from "tc-shared/log"; import {tra} from "./i18n/localize"; import {ConnectionHandler} from "tc-shared/ConnectionHandler"; import {createInfoModal} from "tc-shared/ui/elements/Modal"; -import * as stats from "./stats"; -import * as fidentity from "./profiles/identities/TeaForumIdentity"; import {defaultRecorder, RecorderProfile, setDefaultRecorder} from "tc-shared/voice/RecorderProfile"; import {spawnYesNo} from "tc-shared/ui/modal/ModalYesNo"; import {formatMessage} from "tc-shared/ui/frames/chat"; import {openModalNewcomer} from "tc-shared/ui/modal/ModalNewcomer"; -import * as aplayer from "tc-backend/audio/player"; -import * as ppt from "tc-backend/ppt"; -import * as keycontrol from "./KeyControl"; -import * as React from "react"; -import * as global_ev_handler from "./events/ClientGlobalControlHandler"; import {global_client_actions} from "tc-shared/events/GlobalEvents"; -import {FileTransferState, TransferProvider,} from "tc-shared/file/Transfer"; import {MenuEntryType, spawn_context_menu} from "tc-shared/ui/elements/ContextMenu"; import {copyToClipboard} from "tc-shared/utils/helpers"; import {checkForUpdatedApp} from "tc-shared/update"; import {setupJSRender} from "tc-shared/ui/jsrender"; import {ConnectRequestData} from "tc-shared/ipc/ConnectHandler"; -import "svg-sprites/client-icons"; +import {defaultConnectProfile, findConnectProfile} from "tc-shared/profiles/ConnectionProfile"; +import {server_connections} from "tc-shared/ConnectionManager"; +import {spawnConnectModalNew} from "tc-shared/ui/modal/connect/Controller"; /* required import for init */ +import "svg-sprites/client-icons"; import "../css/load-css" import "./proto"; -import "./ui/elements/ContextDivider"; -import "./ui/elements/Tab"; -import "./connection/CommandHandler"; -import "./connection/ConnectionBase"; import "./video-viewer/Controller"; import "./profiles/ConnectionProfile"; import "./update/UpdaterWeb"; import "./file/LocalIcons"; -import "./ui/frames/menu-bar/MainMenu"; +import "./connection/CommandHandler"; +import "./connection/ConnectionBase"; import "./connection/rtc/Connection"; import "./connection/rtc/video/Connection"; import "./video/VideoSource"; import "./media/Video"; import "./ui/AppController"; - -import {defaultConnectProfile, findConnectProfile} from "tc-shared/profiles/ConnectionProfile"; -import {server_connections} from "tc-shared/ConnectionManager"; -import ContextMenuEvent = JQuery.ContextMenuEvent; - +import "./ui/frames/menu-bar/MainMenu"; import "./ui/modal/connect/Controller"; -import {spawnConnectModalNew} from "tc-shared/ui/modal/connect/Controller"; +import "./ui/elements/ContextDivider"; +import "./ui/elements/Tab"; +import {initializeKeyControl} from "./KeyControl"; let preventWelcomeUI = false; async function initialize() { @@ -67,15 +61,8 @@ async function initialize() { bipc.setup(); } -async function initialize_app() { +async function initializeApp() { global_ev_handler.initialize(global_client_actions); - /* - loader.register_task(loader.Stage.JAVASCRIPT_INITIALIZING, { - name: "settings init", - priority: 10, - function: async () => global_ev_handler.load_default_states(client_control_events) - }); - */ if(!aplayer.initialize()) { console.warn(tr("Failed to initialize audio controller!")); @@ -85,26 +72,25 @@ async function initialize_app() { setDefaultRecorder(new RecorderProfile("default")); defaultRecorder.initialize().catch(error => { - log.error(LogCategory.AUDIO, tr("Failed to initialize default recorder: %o"), error); + logError(LogCategory.AUDIO, tr("Failed to initialize default recorder: %o"), error); }); sound.initialize().then(() => { - log.info(LogCategory.AUDIO, tr("Sounds initialized")); + logInfo(LogCategory.AUDIO, tr("Sounds initialized")); }); sound.set_master_volume(settings.getValue(Settings.KEY_SOUND_MASTER_SOUNDS) / 100); try { await ppt.initialize(); } catch(error) { - log.error(LogCategory.GENERAL, tr("Failed to initialize ppt!\nError: %o"), error); + logError(LogCategory.GENERAL, tr("Failed to initialize ppt!\nError: %o"), error); loader.critical_error(tr("Failed to initialize ppt!")); return; } } export function handle_connect_request(properties: ConnectRequestData, connection: ConnectionHandler) { - const profile_uuid = properties.profile || (defaultConnectProfile() || { id: 'default' }).id; - const profile = findConnectProfile(profile_uuid) || defaultConnectProfile(); + const profile = findConnectProfile(properties.profile) || defaultConnectProfile(); const username = properties.username || profile.connectUsername(); const password = properties.password ? properties.password.value : ""; @@ -114,6 +100,7 @@ export function handle_connect_request(properties: ConnectRequestData, connectio settings.setValue(Settings.KEY_USER_IS_NEW, false); if(!aplayer.initialized()) { + /* Trick the client into clicking somewhere on the site */ spawnYesNo(tra("Connect to {}", properties.address), tra("Would you like to connect to {}?", properties.address), result => { if(result) { aplayer.on_ready(() => handle_connect_request(properties, connection)); @@ -123,6 +110,7 @@ export function handle_connect_request(properties: ConnectRequestData, connectio }).open(); return; } + connection.startConnection(properties.address, profile, true, { nickname: username, password: password.length > 0 ? { @@ -130,7 +118,7 @@ export function handle_connect_request(properties: ConnectRequestData, connectio hashed: password_hashed } : undefined }); - server_connections.set_active_connection(connection); + server_connections.setActiveConnectionHandler(connection); } else { spawnConnectModalNew({ selectedAddress: properties.address, @@ -143,24 +131,26 @@ function main() { /* initialize font */ { const font = settings.getValue(Settings.KEY_FONT_SIZE); - $(document.body).css("font-size", font + "px"); + + document.body.style.fontSize = font + "px"; settings.globalChangeListener(Settings.KEY_FONT_SIZE, value => { - $(document.body).css("font-size", value + "px"); - }) + document.body.style.fontSize = value + "px"; + }); } /* context menu prevent */ - $(document).on('contextmenu', (event: ContextMenuEvent) => { - if(event.isDefaultPrevented()) { + document.addEventListener("contextmenu", event => { + if(event.defaultPrevented) { return; } if(event.target instanceof HTMLInputElement) { + const target = event.target; if((!!event.target.value || __build.target === "client") && !event.target.disabled && !event.target.readOnly && event.target.type !== "number") { spawn_context_menu(event.pageX, event.pageY, { type: MenuEntryType.ENTRY, name: tr("Copy"), - callback: () => copyToClipboard(event.target.value), + callback: () => copyToClipboard(target.value), icon_class: "client-copy", visible: !!event.target.value }, { @@ -168,7 +158,7 @@ function main() { name: tr("Paste"), callback: () => { const { clipboard } = __non_webpack_require__('electron'); - event.target.value = clipboard.readText(); + target.value = clipboard.readText(); }, icon_class: "client-copy", visible: __build.target === "client", @@ -185,13 +175,13 @@ function main() { }); window.removeLoaderContextMenuHook(); - const initialHandler = server_connections.spawn_server_connection(); - server_connections.set_active_connection(initialHandler); + const initialHandler = server_connections.spawnConnectionHandler(); + server_connections.setActiveConnectionHandler(initialHandler); initialHandler.acquireInputHardware().then(() => {}); /** Setup the XF forum identity **/ fidentity.update_forum(); - keycontrol.initialize(); + initializeKeyControl(); stats.initialize({ verbose: true, @@ -199,8 +189,8 @@ function main() { volatile_collection_only: false }); - stats.register_user_count_listener(status => { - log.info(LogCategory.STATISTICS, tr("Received user count update: %o"), status); + stats.registerUserCountListener(status => { + logInfo(LogCategory.STATISTICS, tr("Received user count update: %o"), status); }); checkForUpdatedApp(); @@ -215,10 +205,10 @@ const task_teaweb_starter: loader.Task = { name: "voice app starter", function: async () => { try { - await initialize_app(); + await initializeApp(); main(); if(!aplayer.initialized()) { - log.info(LogCategory.VOICE, tr("Initialize audio controller later!")); + logInfo(LogCategory.VOICE, tr("Initialize audio controller later!")); if(!aplayer.initializeFromGesture) { console.error(tr("Missing aplayer.initializeFromGesture")); } else { @@ -270,7 +260,7 @@ const task_connect_handler: loader.Task = { closeable: false }).open(); })); - log.info(LogCategory.CLIENT, tr("Executed connect successfully in another browser window. Closing this window")); + logInfo(LogCategory.CLIENT, tr("Executed connect successfully in another browser window. Closing this window")); const message = "You're connecting to {0} within the other TeaWeb instance.{:br:}" + @@ -285,7 +275,7 @@ const task_connect_handler: loader.Task = { ).open(); return; } catch(error) { - log.info(LogCategory.CLIENT, tr("Failed to execute connect within other TeaWeb instance. Using this one. Error: %o"), error); + logInfo(LogCategory.CLIENT, tr("Failed to execute connect within other TeaWeb instance. Using this one. Error: %o"), error); } if(chandler) { @@ -296,7 +286,7 @@ const task_connect_handler: loader.Task = { chandler.callback_execute = data => { preventWelcomeUI = true; - handle_connect_request(data, server_connections.spawn_server_connection()); + handle_connect_request(data, server_connections.spawnConnectionHandler()); return true; } } @@ -305,7 +295,7 @@ const task_connect_handler: loader.Task = { preventWelcomeUI = true; loader.register_task(loader.Stage.LOADED, { priority: 0, - function: async () => handle_connect_request(connectData, server_connections.active_connection() || server_connections.spawn_server_connection()), + function: async () => handle_connect_request(connectData, server_connections.getActiveConnectionHandler() || server_connections.spawnConnectionHandler()), name: tr("default url connect") }); loader.register_task(loader.Stage.LOADED, task_teaweb_starter); @@ -365,18 +355,14 @@ loader.register_task(loader.Stage.LOADED, { priority: 2000 }); +/* TODO: Remove this after the image preview has been rewritten into react */ loader.register_task(Stage.JAVASCRIPT_INITIALIZING,{ name: "app init", function: async () => { - try { //Initialize main template - const main = $("#tmpl_main").renderTag({ - multi_session: !settings.getValue(Settings.KEY_DISABLE_MULTI_SESSION), - app_version: __build.version - }).dividerfy(); - - $("body").append(main); + try { + $("body").append($("#tmpl_main").renderTag()); } catch(error) { - log.error(LogCategory.GENERAL, error); + logError(LogCategory.GENERAL, error); loader.critical_error(tr("Failed to setup main page!")); return; } diff --git a/shared/js/stats.ts b/shared/js/stats.ts index be501397..7453886f 100644 --- a/shared/js/stats.ts +++ b/shared/js/stats.ts @@ -79,15 +79,11 @@ export function initialize(config: Config) { connection.start_connection(); } -export function register_user_count_listener(listener: UserCountListener) { +export function registerUserCountListener(listener: UserCountListener) { user_count_listener.push(listener); } -export function all_user_count_listener() : UserCountListener[] { - return user_count_listener; -} - -export function deregister_user_count_listener(listener: UserCountListener) { +export function unregisterUserCountListener(listener: UserCountListener) { user_count_listener.remove(listener); } diff --git a/shared/js/text/bbcode/youtube.tsx b/shared/js/text/bbcode/youtube.tsx index 800fcf4c..2b3ee28a 100644 --- a/shared/js/text/bbcode/youtube.tsx +++ b/shared/js/text/bbcode/youtube.tsx @@ -46,7 +46,7 @@ export const YoutubeRenderer = (props: { children?: React.ReactElement | React.R callback: () => { global_client_actions.fire("action_w2g", { videoUrl: props.url, - handlerId: server_connections.active_connection().handlerId + handlerId: server_connections.getActiveConnectionHandler().handlerId }); }, name: tr("Watch video"), @@ -72,7 +72,7 @@ export const YoutubeRenderer = (props: { children?: React.ReactElement | React.R