Refactoring, various fixes

This commit is contained in:
barsdeveloper
2022-03-24 22:54:41 +01:00
parent 4dd2929a9f
commit 8a4e60c9ae
43 changed files with 937 additions and 589 deletions

View File

@@ -1,14 +1,36 @@
export default class IContext {
/** @type {HTMLElement} */
target
/** @type {import("../Blueprint").default}" */
blueprint
/** @type {Object} */
options
#hasFocus = false
get hasFocus() {
return this.#hasFocus
}
set hasFocus(_) {
}
constructor(target, blueprint, options) {
/** @type {HTMLElement} */
this.target = target
/** @type {import("../Blueprint").default}" */
this.blueprint = blueprint
this.options = options
let self = this
this.blueprintFocusHandler = _ => self.listenEvents()
this.blueprintUnfocusHandler = _ => self.unlistenEvents()
this.blueprintFocusHandler = _ => {
this.#hasFocus = true
self.listenEvents()
}
this.blueprintUnfocusHandler = _ => {
self.unlistenEvents()
this.#hasFocus = false
}
if (options?.wantsFocusCallback ?? false) {
this.blueprint.addEventListener("blueprint-focus", this.blueprintFocusHandler)
this.blueprint.addEventListener("blueprint-unfocus", this.blueprintUnfocusHandler)

View File

@@ -1,76 +1,71 @@
import Configuration from "../../Configuration"
import IContext from "../IContext"
import Parsimmon from "parsimmon"
let P = Parsimmon
class KeyGrammar {
// Creates a grammar where each alternative is the string from ModifierKey mapped to a number for bit or use
ModifierKey = r => P.alt(...Configuration.ModifierKeys.map((v, i) => P.string(v).map(_ => 1 << i)))
Key = r => P.alt(...Object.keys(Configuration.Keys).map(v => P.string(v))).map(v => Configuration.Keys[v])
KeyboardShortcut = r => P.alt(
P.seqMap(
P.seqMap(r.ModifierKey, P.optWhitespace, P.string(Configuration.keysSeparator), (v, _, __) => v)
.atLeast(1)
.map(v => v.reduce((acc, cur) => acc | cur)),
P.optWhitespace,
r.Key,
(modifierKeysFlag, _, key) => ({
key: key,
ctrlKey: Boolean(modifierKeysFlag & (1 << Configuration.ModifierKeys.indexOf("Ctrl"))),
shiftKey: Boolean(modifierKeysFlag & (1 << Configuration.ModifierKeys.indexOf("Shift"))),
altKey: Boolean(modifierKeysFlag & (1 << Configuration.ModifierKeys.indexOf("Alt"))),
metaKey: Boolean(modifierKeysFlag & (1 << Configuration.ModifierKeys.indexOf("Meta")))
})
),
r.Key.map(v => ({ key: v }))
)
.trim(P.optWhitespace)
}
import ISerializer from "../../serialization/ISerializer"
import KeyBindingEntity from "../../entity/KeyBindingEntity"
export default class IKeyboardShortcut extends IContext {
static keyGrammar = P.createLanguage(new KeyGrammar())
/** @type {KeyBindingEntity} */
#activationKeys
constructor(target, blueprint, options = {}) {
options.wantsFocusCallback = true
options.activationKeys ??= []
if (!(options.activationKeys instanceof Array)) {
options.activationKeys = [options.activationKeys]
}
options.activationKeys = options.activationKeys.map(v => {
if (v instanceof KeyBindingEntity) {
return v
}
if (v.constructor === String) {
const parsed = ISerializer.grammar.KeyBinding.parse(v)
if (parsed.status) {
return parsed.value
}
}
throw new Error("Unexpected key value")
})
super(target, blueprint, options)
/** @type {String[]} */
this.key = this.options.key
this.ctrlKey = options.ctrlKey ?? false
this.shiftKey = options.shiftKey ?? false
this.altKey = options.altKey ?? false
this.metaKey = options.metaKey ?? false
this.#activationKeys = this.options.activationKeys ?? []
let self = this
/** @param {KeyboardEvent} e */
this.keyDownHandler = e => {
if (
e.code == self.key
&& e.ctrlKey === self.ctrlKey
&& e.shiftKey === self.shiftKey
&& e.altKey === self.altKey
&& e.metaKey === self.metaKey
) {
self.fire()
self.#activationKeys.some(keyEntry =>
keyEntry.bShift === e.shiftKey
&& keyEntry.bCtrl === e.ctrlKey
&& keyEntry.bAlt === e.altKey
&& keyEntry.bCmd === e.metaKey
&& Configuration.Keys[keyEntry.Key] === e.code
)) {
e.preventDefault()
return true
self.fire()
document.removeEventListener("keydown", self.keyDownHandler)
document.addEventListener("keyup", self.keyUpHandler)
}
return false
}
}
/**
* @param {String} keyString
* @returns {Object}
*/
static keyOptionsParse(options, keyString) {
options = {
...options,
...IKeyboardShortcut.keyGrammar.KeyboardShortcut.parse(keyString).value
/** @param {KeyboardEvent} e */
this.keyUpHandler = e => {
if (
self.#activationKeys.some(keyEntry =>
keyEntry.bShift && e.key === "Shift"
|| keyEntry.bCtrl && e.key === "Control"
|| keyEntry.bAlt && e.key === "Alt"
|| keyEntry.bCmd && e.key === "Meta" // Unsure about this, what key is that?
|| Configuration.Keys[keyEntry.Key] === e.code
)) {
e.preventDefault()
self.unfire()
document.removeEventListener("keyup", this.keyUpHandler)
document.addEventListener("keydown", this.keyDownHandler)
}
}
return options
}
listenEvents() {
@@ -81,6 +76,11 @@ export default class IKeyboardShortcut extends IContext {
document.removeEventListener("keydown", this.keyDownHandler)
}
// Subclasses will want to override
fire() {
}
unfire() {
}
}

View File

@@ -1,7 +1,7 @@
import Configuration from "../../Configuration"
import IKeyboardShortcut from "./IKeyboardShortcut"
export default class KeyvoardCanc extends IKeyboardShortcut {
export default class KeyboardCanc extends IKeyboardShortcut {
/**
* @param {HTMLElement} target
@@ -9,7 +9,10 @@ export default class KeyvoardCanc extends IKeyboardShortcut {
* @param {OBject} options
*/
constructor(target, blueprint, options = {}) {
options = IKeyboardShortcut.keyOptionsParse(options, Configuration.deleteNodesKeyboardKey)
options = {
...options,
activationKeys: Configuration.deleteNodesKeyboardKey
}
super(target, blueprint, options)
}

View File

@@ -0,0 +1,31 @@
import Configuration from "../../Configuration"
import IKeyboardShortcut from "./IKeyboardShortcut"
import Zoom from "../mouse/Zoom"
export default class KeyboardEnableZoom extends IKeyboardShortcut {
/** @type {} */
#zoomInputObject
/**
* @param {HTMLElement} target
* @param {import("../../Blueprint").default} blueprint
* @param {OBject} options
*/
constructor(target, blueprint, options = {}) {
options = {
...options,
activationKeys: Configuration.enableZoomIn
}
super(target, blueprint, options)
}
fire() {
this.zoomInputObject = this.blueprint.getInputObject(Zoom)
zoomInputObject.enableZoonIn = true
}
unfire() {
this.#zoomInputObject.enableZoom = false
}
}

View File

@@ -9,7 +9,10 @@ export default class KeyboardSelectAll extends IKeyboardShortcut {
* @param {Object} options
*/
constructor(target, blueprint, options = {}) {
options = IKeyboardShortcut.keyOptionsParse(options, Configuration.selectAllKeyboardKey)
options = {
...options,
activationKeys: Configuration.selectAllKeyboardKey
}
super(target, blueprint, options)
}

View File

@@ -101,6 +101,7 @@ export default class IMouseClickDrag extends IPointing {
if (self.started) {
self.endDrag()
}
self.unclicked()
if (self.#trackingMouse) {
const dragEvent = self.getEvent(Configuration.trackingMouseEventName.end)
this.target.dispatchEvent(dragEvent)
@@ -146,4 +147,7 @@ export default class IMouseClickDrag extends IPointing {
endDrag() {
}
unclicked(location) {
}
}

View File

@@ -18,7 +18,11 @@ export default class Select extends IMouseClickDrag {
endDrag() {
if (this.started) {
this.selectorElement.finishSelecting()
} else {
}
}
unclicked() {
if (!this.started) {
this.blueprint.unselectAll()
}
}

View File

@@ -2,9 +2,27 @@ import IMouseWheel from "./IMouseWheel"
export default class Zoom extends IMouseWheel {
#enableZoonIn = false
get enableZoonIn() {
return this.#enableZoonIn
}
set enableZoonIn(value) {
value = Boolean(value)
if (value == this.#enableZoonIn) {
return
}
this.#enableZoonIn = value
}
wheel(variation, location) {
let zoomLevel = this.blueprint.getZoom()
zoomLevel -= variation
variation = -variation
if (!this.enableZoonIn && zoomLevel == 0 && variation > 0) {
return
}
zoomLevel += variation
this.blueprint.setZoom(zoomLevel, location)
}
}