UNPKG

@adyen/adyen-platform-experience-web

Version:

![Platform Experience header](https://github.com/Adyen/adyen-platform-experience-web/assets/7926613/18094965-9e01-450e-8dc9-ea84e6b22c2b)

95 lines (94 loc) 3.21 kB
import { some as f } from "../../../utils/collection/main.js"; import { isNumber as N, isUndefined as h, isNullish as R } from "../../../utils/value/is.js"; import { mod as x } from "../../../utils/value/number.js"; const p = ` a[href], audio[controls], video[controls], button, input, select, textarea, [contenteditable], [tabindex] `.replace(/\s+/, ""), E = ["contenteditable", "controls", "disabled", "hidden", "href", "inert", "tabindex"], l = /* @__PURE__ */ new Map(), g = (t) => t.tagName === "INPUT", I = (t) => g(t) && t.type === "radio", b = (t) => { const n = t.name, r = t.form, e = l.get(r); let i = e == null ? void 0 : e.get(n); return h(i) && r && (i = r.querySelector(`input[type=radio][name='${n}']:checked`) || null, l.set(r, (e || /* @__PURE__ */ new Map()).set(n, i))), i === t; }, S = (t, n) => { for (const r of n) if (r.type !== "attributes") { if (f(r.addedNodes, (e) => e instanceof Element && s(e)) || f(r.removedNodes, (e) => t.includes(e))) return !0; } else { if (s(r.target)) return !0; if (t.includes(r.target)) return !0; } return !1; }, v = (t = document.body, n) => { if (h(t)) return !1; if (R(n)) return !!document.activeElement && v(t, document.activeElement); let r = n == null ? void 0 : n.parentNode; for (; r; ) { if (r === t) return !0; r = r == null ? void 0 : r.parentNode; } return !1; }, w = (t) => !// [TODO]: Include all of these checks // (1) matches focusable elements selector // (2) is disabled element // (3) is inert or inert subtree child // (4) is hidden input // (5) with visibility: hidden // (6) is summary of open details element // (7) is details with summary element // (8) is disabled fieldset subtree child /* (1) */ (!t.matches(p) || /* (2) */ t != null && t.disabled || /* (3) */ /^(true)?$/.test(t.getAttribute("inert")) || /* (4) */ g(t) && t.hidden), s = (t) => !(I(t) && !b(t) || // (1) is not checked radio button (t == null ? void 0 : t.tabIndex) < 0 || // (2) has negative tabindex !w(t)), U = () => { const t = new MutationObserver((o) => S(n, o) && u()), n = []; let r = -1, e = null; const i = (o) => { var a; if (o < 0) return; const d = Math.min(o, n.length - 1); r !== d && (r = d), (a = n[r]) == null || a.focus(); }, u = () => { n.length = 0, e instanceof Element && (e.querySelectorAll(p).forEach((o) => s(o) && n.push(o)), v(e) && (c.current = document.activeElement)); }, c = Object.create(null, { current: { get: () => n[r] ?? null, set: (o) => { if (o) { if (!N(o)) return i(n.indexOf(o)); if (o === ~~o) return i(x(r + o, n.length)); } } }, root: { get: () => e, set: (o) => { o !== e && (e && t.disconnect(), e = o instanceof Element ? o : null, n.length = 0, e && (t.observe(e, { attributeFilter: E, attributes: !0, childList: !0, subtree: !0 }), u())); } }, tabbables: { value: n } }); return c; }; export { p as SELECTORS, U as default, v as focusIsWithin, w as isFocusable, s as isTabbable, U as withTabbableRoot };