cobalt/web/src/lib/polyfills/user-activation.ts

54 lines
2 KiB
TypeScript

import { browser } from "$app/environment";
import type { Writeable } from "$lib/types/generic";
if (browser && !navigator.userActivation) {
const TRANSIENT_TIMEOUT = navigator.userAgent.includes('Firefox') ? 5000 : 2000;
let _timeout: number | undefined;
const userActivation: Writeable<UserActivation> = {
isActive: false,
hasBeenActive: false
};
const receiveEvent = (e: Event) => {
// An activation triggering input event is any event whose isTrusted attribute is true [...]
if (!e.isTrusted) return;
// and whose type is one of:
if (e instanceof PointerEvent) {
if (
// "pointerdown", provided the event's pointerType is "mouse";
(e.type === 'pointerdown' && e.pointerType !== 'mouse')
// "pointerup", provided the event's pointerType is not "mouse";
|| (e.type === 'pointerup' && e.pointerType === 'mouse')
)
return;
} else if (e instanceof KeyboardEvent) {
// "keydown", provided the key is neither the Esc key nor a shortcut key
// reserved by the user agent;
if (e.ctrlKey || e.shiftKey || e.altKey || e.metaKey)
return;
// the handling for this is a bit more complex,
// but this is fine for our use case
if (e.key !== 'Return' && e.key !== 'Enter' && e.key.length > 1)
return;
}
userActivation.hasBeenActive = true;
userActivation.isActive = true;
clearTimeout(_timeout);
_timeout = window.setTimeout(() => {
userActivation.isActive = false;
_timeout = undefined;
}, TRANSIENT_TIMEOUT);
}
// https://html.spec.whatwg.org/multipage/interaction.html#the-useractivation-interface
for (const event of [ 'keydown', 'mousedown', 'pointerdown', 'pointerup', 'touchend' ]) {
window.addEventListener(event, receiveEvent);
}
(navigator.userActivation as UserActivation) = userActivation;
}