frontend: add OXC lint/format setup and apply semicolon fixes
This commit is contained in:
1 parent
836a563897
commit
f6a40babc9
26 files changed
+3452
-3130
No files matched your search
@@ -1,135 +1,146 @@
|
||||
type InputModality = 'mouse' | 'keyboard' | 'gamepad';
|
||||
type InputModality = "mouse" | "keyboard" | "gamepad"
|
||||
|
||||
const MOUSE_IDLE_MS = 1400;
|
||||
const MOUSE_INTENT_DISTANCE_PX = 28;
|
||||
const MOUSE_INTENT_WINDOW_MS = 700;
|
||||
const MOUSE_IDLE_MS = 1400
|
||||
const MOUSE_INTENT_DISTANCE_PX = 28
|
||||
const MOUSE_INTENT_WINDOW_MS = 700
|
||||
const MOUSE_INTENT_SELECTOR = [
|
||||
'[data-nav-focusable]','button','a[href]','input','select','textarea','[role="button"]',
|
||||
'.media-card','.collage-item','.episode-tile','.version-row','.ctx-btn','.header-nav-item',
|
||||
].join(',');
|
||||
"[data-nav-focusable]",
|
||||
"button",
|
||||
"a[href]",
|
||||
"input",
|
||||
"select",
|
||||
"textarea",
|
||||
'[role="button"]',
|
||||
".media-card",
|
||||
".collage-item",
|
||||
".episode-tile",
|
||||
".version-row",
|
||||
".ctx-btn",
|
||||
".header-nav-item",
|
||||
].join(",")
|
||||
|
||||
let installed = false;
|
||||
let modality: InputModality = 'mouse';
|
||||
let mouseIdleTimer: number | null = null;
|
||||
let pointerVisible = false;
|
||||
let mouseTravelPx = 0;
|
||||
let lastMouseMoveAt = 0;
|
||||
let installed = false
|
||||
let modality: InputModality = "mouse"
|
||||
let mouseIdleTimer: number | null = null
|
||||
let pointerVisible = false
|
||||
let mouseTravelPx = 0
|
||||
let lastMouseMoveAt = 0
|
||||
|
||||
function clearMouseIdleTimer() {
|
||||
if (mouseIdleTimer !== null) {
|
||||
window.clearTimeout(mouseIdleTimer);
|
||||
mouseIdleTimer = null;
|
||||
window.clearTimeout(mouseIdleTimer)
|
||||
mouseIdleTimer = null
|
||||
}
|
||||
}
|
||||
|
||||
function applyInputState(mouseActive: boolean) {
|
||||
const root = document.documentElement;
|
||||
root.classList.toggle('mouse-active', mouseActive);
|
||||
root.classList.toggle('pointer-visible', pointerVisible);
|
||||
const root = document.documentElement
|
||||
root.classList.toggle("mouse-active", mouseActive)
|
||||
root.classList.toggle("pointer-visible", pointerVisible)
|
||||
}
|
||||
|
||||
function scheduleMouseIdle() {
|
||||
clearMouseIdleTimer();
|
||||
clearMouseIdleTimer()
|
||||
mouseIdleTimer = window.setTimeout(() => {
|
||||
pointerVisible = false;
|
||||
applyInputState(false);
|
||||
}, MOUSE_IDLE_MS);
|
||||
pointerVisible = false
|
||||
applyInputState(false)
|
||||
}, MOUSE_IDLE_MS)
|
||||
}
|
||||
|
||||
function activateMouseInput() {
|
||||
modality = 'mouse';
|
||||
pointerVisible = true;
|
||||
applyInputState(true);
|
||||
scheduleMouseIdle();
|
||||
modality = "mouse"
|
||||
pointerVisible = true
|
||||
applyInputState(true)
|
||||
scheduleMouseIdle()
|
||||
}
|
||||
|
||||
function activateNonMouseInput(next: InputModality) {
|
||||
modality = next;
|
||||
pointerVisible = false;
|
||||
mouseTravelPx = 0;
|
||||
clearMouseIdleTimer();
|
||||
applyInputState(false);
|
||||
modality = next
|
||||
pointerVisible = false
|
||||
mouseTravelPx = 0
|
||||
clearMouseIdleTimer()
|
||||
applyInputState(false)
|
||||
}
|
||||
|
||||
function showPointerFromMotion() {
|
||||
pointerVisible = true;
|
||||
applyInputState(modality === 'mouse');
|
||||
scheduleMouseIdle();
|
||||
pointerVisible = true
|
||||
applyInputState(modality === "mouse")
|
||||
scheduleMouseIdle()
|
||||
}
|
||||
|
||||
function isMouseIntentTarget(target: EventTarget | null): boolean {
|
||||
if (!(target instanceof Element)) return false;
|
||||
return Boolean(target.closest(MOUSE_INTENT_SELECTOR));
|
||||
if (!(target instanceof Element)) return false
|
||||
return Boolean(target.closest(MOUSE_INTENT_SELECTOR))
|
||||
}
|
||||
|
||||
function registerMouseIntentTravel(event: MouseEvent): boolean {
|
||||
const now = performance.now();
|
||||
const now = performance.now()
|
||||
if (now - lastMouseMoveAt > MOUSE_INTENT_WINDOW_MS) {
|
||||
mouseTravelPx = 0;
|
||||
mouseTravelPx = 0
|
||||
}
|
||||
lastMouseMoveAt = now;
|
||||
lastMouseMoveAt = now
|
||||
|
||||
const step = Math.hypot(event.movementX || 0, event.movementY || 0);
|
||||
mouseTravelPx += step;
|
||||
const step = Math.hypot(event.movementX || 0, event.movementY || 0)
|
||||
mouseTravelPx += step
|
||||
if (mouseTravelPx >= MOUSE_INTENT_DISTANCE_PX) {
|
||||
mouseTravelPx = 0;
|
||||
return true;
|
||||
mouseTravelPx = 0
|
||||
return true
|
||||
}
|
||||
return false;
|
||||
return false
|
||||
}
|
||||
|
||||
function handleMouseMove(event: MouseEvent) {
|
||||
showPointerFromMotion();
|
||||
showPointerFromMotion()
|
||||
|
||||
if (modality === 'mouse') {
|
||||
applyInputState(true);
|
||||
return;
|
||||
if (modality === "mouse") {
|
||||
applyInputState(true)
|
||||
return
|
||||
}
|
||||
|
||||
if (!isMouseIntentTarget(event.target)) return;
|
||||
if (!isMouseIntentTarget(event.target)) return
|
||||
if (registerMouseIntentTravel(event)) {
|
||||
activateMouseInput();
|
||||
activateMouseInput()
|
||||
}
|
||||
}
|
||||
|
||||
function handleMouseOver(event: MouseEvent) {
|
||||
if (modality === 'mouse') return;
|
||||
if (!isMouseIntentTarget(event.target)) return;
|
||||
if (modality === "mouse") return
|
||||
if (!isMouseIntentTarget(event.target)) return
|
||||
|
||||
// Entering an interactive target indicates likely mouse intent.
|
||||
activateMouseInput();
|
||||
activateMouseInput()
|
||||
}
|
||||
|
||||
function handleMouseIntentAction(event: MouseEvent | WheelEvent) {
|
||||
pointerVisible = true;
|
||||
pointerVisible = true
|
||||
if (isMouseIntentTarget(event.target)) {
|
||||
activateMouseInput();
|
||||
return;
|
||||
activateMouseInput()
|
||||
return
|
||||
}
|
||||
|
||||
applyInputState(modality === 'mouse');
|
||||
scheduleMouseIdle();
|
||||
applyInputState(modality === "mouse")
|
||||
scheduleMouseIdle()
|
||||
}
|
||||
|
||||
function handleKeyboardActivity(event: KeyboardEvent) {
|
||||
if (event.metaKey || event.ctrlKey || event.altKey) return;
|
||||
activateNonMouseInput('keyboard');
|
||||
if (event.metaKey || event.ctrlKey || event.altKey) return
|
||||
activateNonMouseInput("keyboard")
|
||||
}
|
||||
|
||||
function handleGamepadActivity() {
|
||||
activateNonMouseInput('gamepad');
|
||||
activateNonMouseInput("gamepad")
|
||||
}
|
||||
|
||||
export function installInputModalityTracking() {
|
||||
if (installed) return;
|
||||
installed = true;
|
||||
if (installed) return
|
||||
installed = true
|
||||
|
||||
applyInputState(false);
|
||||
applyInputState(false)
|
||||
|
||||
window.addEventListener('mousemove', handleMouseMove, { passive: true });
|
||||
window.addEventListener('mouseover', handleMouseOver, { passive: true });
|
||||
window.addEventListener('mousedown', handleMouseIntentAction, { passive: true });
|
||||
window.addEventListener('wheel', handleMouseIntentAction, { passive: true });
|
||||
window.addEventListener('keydown', handleKeyboardActivity, { passive: true });
|
||||
window.addEventListener('mediahive:gamepad-action', handleGamepadActivity as EventListener);
|
||||
window.addEventListener("mousemove", handleMouseMove, { passive: true })
|
||||
window.addEventListener("mouseover", handleMouseOver, { passive: true })
|
||||
window.addEventListener("mousedown", handleMouseIntentAction, { passive: true })
|
||||
window.addEventListener("wheel", handleMouseIntentAction, { passive: true })
|
||||
window.addEventListener("keydown", handleKeyboardActivity, { passive: true })
|
||||
window.addEventListener("mediahive:gamepad-action", handleGamepadActivity as EventListener)
|
||||
}
|
||||
Reference in new issue
Block a user