Improved key event handling

This commit is contained in:
the-djmaze 2023-02-21 14:26:37 +01:00
parent 81d521c562
commit 1c1b043a50
7 changed files with 35 additions and 43 deletions

View file

@ -33,6 +33,11 @@ export const
new CustomEvent(name, {detail:detail, cancelable: !!cancelable}) new CustomEvent(name, {detail:detail, cancelable: !!cancelable})
), ),
stopEvent = event => {
event.preventDefault();
event.stopPropagation();
},
formFieldFocused = () => doc.activeElement?.matches('input,textarea'), formFieldFocused = () => doc.activeElement?.matches('input,textarea'),
addShortcut = (...args) => shortcuts.add(...args), addShortcut = (...args) => shortcuts.add(...args),

47
dev/External/ko.js vendored
View file

@ -28,6 +28,18 @@ export const
dispose = disposable => isFunction(disposable?.dispose) && disposable.dispose(), dispose = disposable => isFunction(disposable?.dispose) && disposable.dispose(),
onKey = (key, element, fValueAccessor, fAllBindings, viewModel) => {
let fn = event => {
if (key == event.key) {
// stopEvent(event);
// element.dispatchEvent(new Event('change'));
fValueAccessor().call(viewModel);
}
};
element.addEventListener('keydown', fn);
ko.utils.domNodeDisposal.addDisposeCallback(element, () => element.removeEventListener('keydown', fn));
},
// With this we don't need delegateRunOnDestroy // With this we don't need delegateRunOnDestroy
koArrayWithDestroy = data => { koArrayWithDestroy = data => {
data = ko.observableArray(data); data = ko.observableArray(data);
@ -56,41 +68,18 @@ Object.assign(ko.bindingHandlers, {
}, },
onEnter: { onEnter: {
init: (element, fValueAccessor, fAllBindings, viewModel) => { init: (element, fValueAccessor, fAllBindings, viewModel) =>
let fn = event => { onKey('Enter', element, fValueAccessor, fAllBindings, viewModel)
if ('Enter' == event.key) {
element.dispatchEvent(new Event('change'));
fValueAccessor().call(viewModel);
}
};
element.addEventListener('keydown', fn);
ko.utils.domNodeDisposal.addDisposeCallback(element, () => element.removeEventListener('keydown', fn));
}
}, },
onEsc: { onEsc: {
init: (element, fValueAccessor, fAllBindings, viewModel) => { init: (element, fValueAccessor, fAllBindings, viewModel) =>
let fn = event => { onKey('Escape', element, fValueAccessor, fAllBindings, viewModel)
if ('Escape' == event.key) {
element.dispatchEvent(new Event('change'));
fValueAccessor().call(viewModel);
}
};
element.addEventListener('keyup', fn);
ko.utils.domNodeDisposal.addDisposeCallback(element, () => element.removeEventListener('keyup', fn));
}
}, },
onSpace: { onSpace: {
init: (element, fValueAccessor, fAllBindings, viewModel) => { init: (element, fValueAccessor, fAllBindings, viewModel) =>
let fn = event => { onKey(' ', element, fValueAccessor, fAllBindings, viewModel)
if (' ' == event.key) {
fValueAccessor().call(viewModel, event);
}
};
element.addEventListener('keyup', fn);
ko.utils.domNodeDisposal.addDisposeCallback(element, () => element.removeEventListener('keyup', fn));
}
}, },
i18nUpdate: { i18nUpdate: {

View file

@ -1,6 +1,7 @@
import ko from 'ko'; import ko from 'ko';
import { FileInfo, FileType } from 'Common/File'; import { FileInfo, FileType } from 'Common/File';
import { stopEvent } from 'Common/Globals';
import { import {
attachmentDownload, attachmentDownload,
serverRequestRaw serverRequestRaw
@ -53,7 +54,7 @@ export class AttachmentModel extends AbstractModel {
} }
toggleChecked(self, event) { toggleChecked(self, event) {
event.stopPropagation(); stopEvent(event);
self.checked(!self.checked()); self.checked(!self.checked());
} }

View file

@ -1,7 +1,7 @@
import ko from 'ko'; import ko from 'ko';
import { Scope } from 'Common/Enums'; import { Scope } from 'Common/Enums';
import { addShortcut } from 'Common/Globals'; import { addShortcut, stopEvent } from 'Common/Globals';
import { mailBox, settings } from 'Common/Links'; import { mailBox, settings } from 'Common/Links';
//import { setFolderETag } from 'Common/Cache'; //import { setFolderETag } from 'Common/Cache';
import { addComputablesTo } from 'External/ko'; import { addComputablesTo } from 'External/ko';
@ -80,8 +80,7 @@ export class MailFolderList extends AbstractViewLeft {
setExpandedFolder(folder.fullName, collapsed); setExpandedFolder(folder.fullName, collapsed);
folder.collapsed(!collapsed); folder.collapsed(!collapsed);
event.preventDefault(); stopEvent(event);
event.stopPropagation();
return; return;
} }
} }

View file

@ -8,7 +8,7 @@ import { ComposeType, FolderType, MessageSetAction } from 'Common/EnumsUser';
import { doc, import { doc,
leftPanelDisabled, toggleLeftPanel, leftPanelDisabled, toggleLeftPanel,
Settings, SettingsCapa, Settings, SettingsCapa,
addEventsListeners, addEventsListeners, stopEvent,
addShortcut, registerShortcut, formFieldFocused addShortcut, registerShortcut, formFieldFocused
} from 'Common/Globals'; } from 'Common/Globals';
@ -412,8 +412,7 @@ export class MailMessageList extends AbstractViewRight {
moveCommand(vm, event) { moveCommand(vm, event) {
if (this.mobileCheckedStateShow()) { if (this.mobileCheckedStateShow()) {
if (vm && event?.preventDefault) { if (vm && event?.preventDefault) {
event.preventDefault(); stopEvent(event);
event.stopPropagation();
} }
let b = moveAction(); let b = moveAction();

View file

@ -18,6 +18,7 @@ import {
Settings, Settings,
SettingsCapa, SettingsCapa,
fireEvent, fireEvent,
stopEvent,
addShortcut, addShortcut,
registerShortcut registerShortcut
} from 'Common/Globals'; } from 'Common/Globals';
@ -283,19 +284,18 @@ export class MailMessageView extends AbstractViewRight {
let el = eqs(event, 'a'); let el = eqs(event, 'a');
if (el && 0 === event.button && mailToHelper(el.href)) { if (el && 0 === event.button && mailToHelper(el.href)) {
event.preventDefault(); stopEvent(event);
event.stopPropagation();
return; return;
} }
if (eqs(event, '.attachmentsPlace .showPreview')) { if (eqs(event, '.attachmentsPlace .showPreview')) {
event.stopPropagation(); stopEvent(event);
return; return;
} }
el = eqs(event, '.attachmentsPlace .showPreplay'); el = eqs(event, '.attachmentsPlace .showPreplay');
if (el) { if (el) {
event.stopPropagation(); stopEvent(event);
const attachment = ko.dataFor(el); const attachment = ko.dataFor(el);
if (attachment && SMAudio.supported) { if (attachment && SMAudio.supported) {
switch (true) { switch (true) {

View file

@ -12,7 +12,7 @@ import { KeyboardShortcutsHelpPopupView } from 'View/Popup/KeyboardShortcutsHelp
import { AccountPopupView } from 'View/Popup/Account'; import { AccountPopupView } from 'View/Popup/Account';
import { ContactsPopupView } from 'View/Popup/Contacts'; import { ContactsPopupView } from 'View/Popup/Contacts';
import { doc, leftPanelDisabled, fireEvent, SettingsCapa, registerShortcut } from 'Common/Globals'; import { doc, leftPanelDisabled, fireEvent, stopEvent, SettingsCapa, registerShortcut } from 'Common/Globals';
import { ThemeStore } from 'Stores/Theme'; import { ThemeStore } from 'Stores/Theme';
@ -56,8 +56,7 @@ export class SystemDropDownUserView extends AbstractViewRight {
let email = account?.email; let email = account?.email;
if (email && 0 === event.button && AccountUserStore.email() != email) { if (email && 0 === event.button && AccountUserStore.email() != email) {
AccountUserStore.loading(true); AccountUserStore.loading(true);
event.preventDefault(); stopEvent(event);
event.stopPropagation();
Remote.request('AccountSwitch', Remote.request('AccountSwitch',
(iError/*, oData*/) => { (iError/*, oData*/) => {
if (iError) { if (iError) {