From 8478194e30a1e916eb13ca5ffd949640e853dc6f Mon Sep 17 00:00:00 2001 From: Julian Stirling Date: Fri, 13 Feb 2026 10:36:13 +0000 Subject: [PATCH] Better jog comments, use pointer events for robustness --- webapp/src/App.vue | 21 ++++++- .../controlComponents/stageControlButtons.vue | 58 +++++++++++++------ 2 files changed, 59 insertions(+), 20 deletions(-) diff --git a/webapp/src/App.vue b/webapp/src/App.vue index 917f5dcd..671e3d39 100644 --- a/webapp/src/App.vue +++ b/webapp/src/App.vue @@ -243,7 +243,9 @@ export default { eventBus.emit("globalTogglePreview", false); }, - // Handle global mouse wheel events to be associated with navigation + /** + * Handle global mouse wheel events to be associated with navigation + */ wheelMonitor: function (event) { // Only capture scroll if the event target's parent contains the "scrollTarget" class if ( @@ -261,6 +263,13 @@ export default { } }, + /** + * Jog for key-presses. + * + * This is a similar to the function in stageControlButtons.vue however it uses + * uses the key repeat to fire in case a key up is missed. It debounes any + * request to jog that is too recent after the last jog. + */ jog(x, y, z) { // Manually debounce extra requests from keyboard repeat rate. // This is used rather than and interval in case of missing a repeat. @@ -279,6 +288,13 @@ export default { eventBus.emit("globalUpdatePositionEvent"); }, + /** + * Stop jogging on key-up + * + * This is also similar to the function in stageControlButtons.vue. It handles + * stopping jogging and resetting the `lastJogTime` so there is no delay when + * starting a new jog after an old jog finished. + */ jogStop() { this.invokeAction("stage", "jog", { stop: true }); this.lastJogTime = 0; @@ -287,6 +303,9 @@ export default { }, 100); }, + /** + * Track which keys are still down on keypress (or key repeat). + */ updateJogFromKeys() { let x = 0, y = 0, diff --git a/webapp/src/components/tabContentComponents/controlComponents/stageControlButtons.vue b/webapp/src/components/tabContentComponents/controlComponents/stageControlButtons.vue index 158823d2..f75a08a4 100644 --- a/webapp/src/components/tabContentComponents/controlComponents/stageControlButtons.vue +++ b/webapp/src/components/tabContentComponents/controlComponents/stageControlButtons.vue @@ -12,9 +12,9 @@ v-if="showDpad" id="up-button" class="uk-button uk-button-primary dpad-btn" - @mousedown.left="jog(0, 1, 0)" - @mouseup="jogStop()" - @mouseOut="jogStop()" + @pointerdown="jog($event, 0, 1, 0)" + @pointerup="jogStop()" + @mouseLeave="jogStop()" > arrow_upward @@ -23,9 +23,9 @@ v-if="showDpad" id="left-button" class="uk-button uk-button-primary dpad-btn" - @mousedown.left="jog(-1, 0, 0)" - @mouseup="jogStop()" - @mouseOut="jogStop()" + @pointerdown="jog($event, -1, 0, 0)" + @pointerup="jogStop()" + @pointercancel="jogStop()" > arrow_back @@ -34,9 +34,9 @@ v-if="showDpad" id="right-button" class="uk-button uk-button-primary dpad-btn" - @mousedown.left="jog(1, 0, 0)" - @mouseup="jogStop()" - @mouseOut="jogStop()" + @pointerdown="jog($event, 1, 0, 0)" + @pointerup="jogStop()" + @pointercancel="jogStop()" > arrow_forward @@ -45,9 +45,9 @@ v-if="showDpad" id="down-button" class="uk-button uk-button-primary dpad-btn" - @mousedown.left="jog(0, -1, 0)" - @mouseup="jogStop()" - @mouseOut="jogStop()" + @pointerdown="jog($event, 0, -1, 0)" + @pointerup="jogStop()" + @pointercancel="jogStop()" > arrow_downward @@ -56,9 +56,9 @@ v-if="showFocusControls" id="focus-out-button" class="uk-button uk-button-primary dpad-btn" - @mousedown.left="jog(0, 0, -1)" - @mouseup="jogStop()" - @mouseOut="jogStop()" + @pointerdown="jog($event, 0, 0, -1)" + @pointerup="jogStop()" + @pointercancel="jogStop()" > remove @@ -67,9 +67,9 @@ v-if="showFocusControls" id="focus-in-button" class="uk-button uk-button-primary dpad-btn" - @mousedown.left="jog(0, 0, 1)" - @mouseup="jogStop()" - @mouseOut="jogStop()" + @pointerdown="jog($event, 0, 0, 1)" + @pointerup="jogStop()" + @pointercancel="jogStop()" > add @@ -98,10 +98,24 @@ export default { jogTime: 300, }), methods: { - jog(x, y, z) { + /** + * Jog d-pad and focus buttons. + * + * This is a similar to the function in App.vue, however it uses an Interval rather + * than the one in App.vue that uses key repeats. + */ + jog(keyevent, x, y, z) { + // Only respond to primary button (left mouse / primary touch) + if (keyevent.button !== 0) return; + if (this.jogIntervalId) { clearInterval(this.jogIntervalId); } + + // Designate this element to get the pointers next pointerup event wherever that + // pointer is. + keyevent.target.setPointerCapture(keyevent.pointerId); + const navigationInvert = this.$store.state.navigationInvert; let invokeJog = () => this.invokeAction("stage", "jog", { @@ -112,6 +126,12 @@ export default { invokeJog(); this.jogIntervalId = setInterval(invokeJog, this.jogTime); }, + /** + * Stop jogging from d-pad and focus buttons. + * + * This is a similar to the function in App.vue, but it is designed to clear the + * interval used with the d-pad and focus buttons. + */ jogStop() { if (this.jogIntervalId) { clearInterval(this.jogIntervalId);