power-focusable 4.3.30 → 4.3.31
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -3
- package/dist/index.cjs +38 -45
- package/dist/index.d.cts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +38 -45
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -24,11 +24,11 @@ import {
|
|
|
24
24
|
} from 'power-focusable';
|
|
25
25
|
|
|
26
26
|
// CDNs
|
|
27
|
-
import { ... } 'https://esm.sh/power-focusable@4.3.
|
|
27
|
+
import { ... } 'https://esm.sh/power-focusable@4.3.31';
|
|
28
28
|
// or
|
|
29
|
-
import { ... } 'https://cdn.jsdelivr.net/npm/power-focusable@4.3.
|
|
29
|
+
import { ... } 'https://cdn.jsdelivr.net/npm/power-focusable@4.3.31/+esm';
|
|
30
30
|
// or
|
|
31
|
-
import { ... } 'https://esm.unpkg.com/power-focusable@4.3.
|
|
31
|
+
import { ... } 'https://esm.unpkg.com/power-focusable@4.3.31';
|
|
32
32
|
```
|
|
33
33
|
|
|
34
34
|
## 🪄 Options
|
package/dist/index.cjs
CHANGED
|
@@ -78,21 +78,21 @@ function getFocusables(container = document.body, options = {}) {
|
|
|
78
78
|
skipNegativeTabIndexCheck,
|
|
79
79
|
skipVisibilityCheck
|
|
80
80
|
}) || include?.(node)) {
|
|
81
|
-
candidates
|
|
81
|
+
candidates.push(node);
|
|
82
82
|
}
|
|
83
|
-
(composed ? getComposedChildren(node) :
|
|
83
|
+
(composed ? getComposedChildren(node) : [...node.children]).map(traverse2);
|
|
84
84
|
};
|
|
85
|
-
(composed ? getComposedChildren(container) :
|
|
85
|
+
(composed ? getComposedChildren(container) : [...container.children]).map(
|
|
86
86
|
traverse2
|
|
87
87
|
);
|
|
88
88
|
} else {
|
|
89
|
-
for (const
|
|
89
|
+
for (const m of container.querySelectorAll(
|
|
90
90
|
skipNegativeTabIndexCheck ? FOCUSABLE_SELECTOR_WITH_NEGATIVE_TABINDEX : FOCUSABLE_SELECTOR
|
|
91
91
|
)) {
|
|
92
|
-
|
|
92
|
+
m && isFocusable(m, {
|
|
93
93
|
skipNegativeTabIndexCheck,
|
|
94
94
|
skipVisibilityCheck
|
|
95
|
-
}) && candidates.push(
|
|
95
|
+
}) && candidates.push(m);
|
|
96
96
|
}
|
|
97
97
|
}
|
|
98
98
|
return normalizeRadioGroup(
|
|
@@ -228,58 +228,58 @@ function isDisabledDeep(element) {
|
|
|
228
228
|
}
|
|
229
229
|
function normalizeRadioGroup(elements) {
|
|
230
230
|
let map = null;
|
|
231
|
-
for (const
|
|
232
|
-
if (!(
|
|
231
|
+
for (const e of elements) {
|
|
232
|
+
if (!(e instanceof HTMLInputElement)) {
|
|
233
233
|
continue;
|
|
234
234
|
}
|
|
235
|
-
if (!isUngroupedRadio(
|
|
235
|
+
if (!isUngroupedRadio(e)) {
|
|
236
236
|
continue;
|
|
237
237
|
}
|
|
238
238
|
if (!map) {
|
|
239
239
|
map = /* @__PURE__ */ new Map();
|
|
240
240
|
}
|
|
241
|
-
const root =
|
|
242
|
-
let
|
|
243
|
-
if (!
|
|
244
|
-
|
|
245
|
-
map.set(root,
|
|
241
|
+
const root = e.getRootNode();
|
|
242
|
+
let groups = map.get(root);
|
|
243
|
+
if (!groups) {
|
|
244
|
+
groups = /* @__PURE__ */ new Map();
|
|
245
|
+
map.set(root, groups);
|
|
246
246
|
}
|
|
247
|
-
let
|
|
248
|
-
if (!
|
|
249
|
-
|
|
250
|
-
|
|
247
|
+
let group = groups.get(e.form);
|
|
248
|
+
if (!group) {
|
|
249
|
+
group = /* @__PURE__ */ new Map();
|
|
250
|
+
groups.set(e.form, group);
|
|
251
251
|
}
|
|
252
|
-
let
|
|
253
|
-
if (!
|
|
254
|
-
|
|
255
|
-
|
|
252
|
+
let radios = group.get(e.name);
|
|
253
|
+
if (!radios) {
|
|
254
|
+
radios = [];
|
|
255
|
+
group.set(e.name, radios);
|
|
256
256
|
}
|
|
257
|
-
|
|
257
|
+
radios.push(e);
|
|
258
258
|
}
|
|
259
259
|
if (!map) {
|
|
260
260
|
return elements;
|
|
261
261
|
}
|
|
262
262
|
const placeholder = /* @__PURE__ */ new Set();
|
|
263
|
-
for (const
|
|
264
|
-
for (const
|
|
265
|
-
for (const
|
|
266
|
-
const radio =
|
|
263
|
+
for (const v of map.values()) {
|
|
264
|
+
for (const w of v.values()) {
|
|
265
|
+
for (const x of w.values()) {
|
|
266
|
+
const radio = x.find((r) => r.checked) ?? x[0];
|
|
267
267
|
radio && placeholder.add(radio);
|
|
268
268
|
}
|
|
269
269
|
}
|
|
270
270
|
}
|
|
271
|
-
return elements.filter((
|
|
272
|
-
if (!(
|
|
271
|
+
return elements.filter((e) => {
|
|
272
|
+
if (!(e instanceof HTMLInputElement)) {
|
|
273
273
|
return true;
|
|
274
274
|
}
|
|
275
|
-
return !isUngroupedRadio(
|
|
275
|
+
return !isUngroupedRadio(e) || placeholder.has(e);
|
|
276
276
|
});
|
|
277
277
|
}
|
|
278
278
|
function sortByTabIndex(elements) {
|
|
279
279
|
const ordered = [];
|
|
280
280
|
const natural = [];
|
|
281
|
-
for (const
|
|
282
|
-
(getTabIndex(
|
|
281
|
+
for (const e of elements) {
|
|
282
|
+
(getTabIndex(e) > 0 ? ordered : natural).push(e);
|
|
283
283
|
}
|
|
284
284
|
return ordered.sort((a, b) => getTabIndex(a) - getTabIndex(b)).concat(natural);
|
|
285
285
|
}
|
|
@@ -296,7 +296,7 @@ function containsComposed(container, element) {
|
|
|
296
296
|
}
|
|
297
297
|
function getComposedChildren(node) {
|
|
298
298
|
if (node instanceof ShadowRoot) {
|
|
299
|
-
return
|
|
299
|
+
return [...node.children];
|
|
300
300
|
}
|
|
301
301
|
if (!(node instanceof Element)) {
|
|
302
302
|
return [];
|
|
@@ -308,9 +308,9 @@ function getComposedChildren(node) {
|
|
|
308
308
|
}
|
|
309
309
|
}
|
|
310
310
|
if (node instanceof HTMLElement && node.shadowRoot?.mode === "open") {
|
|
311
|
-
return
|
|
311
|
+
return [...node.shadowRoot.children];
|
|
312
312
|
}
|
|
313
|
-
return
|
|
313
|
+
return [...node.children];
|
|
314
314
|
}
|
|
315
315
|
function getComposedParent(node) {
|
|
316
316
|
if (node instanceof Element && node.assignedSlot) {
|
|
@@ -326,8 +326,8 @@ function getComposedSiblings(node) {
|
|
|
326
326
|
return [];
|
|
327
327
|
}
|
|
328
328
|
const filtered = [];
|
|
329
|
-
for (const
|
|
330
|
-
filtered.push(
|
|
329
|
+
for (const s of (parent instanceof HTMLSlotElement ? parent.assignedElements({ flatten: true }) : getComposedChildren(parent)).filter((s2) => s2 !== node)) {
|
|
330
|
+
filtered.push(s);
|
|
331
331
|
}
|
|
332
332
|
return filtered;
|
|
333
333
|
}
|
|
@@ -364,13 +364,6 @@ function getActiveElement() {
|
|
|
364
364
|
}
|
|
365
365
|
return current;
|
|
366
366
|
}
|
|
367
|
-
function getChildren(node) {
|
|
368
|
-
const elements = [];
|
|
369
|
-
for (let child = node.firstElementChild; child; child = child.nextElementSibling) {
|
|
370
|
-
elements[elements.length] = child;
|
|
371
|
-
}
|
|
372
|
-
return elements;
|
|
373
|
-
}
|
|
374
367
|
function getTabIndex(element) {
|
|
375
368
|
return "tabIndex" in element ? Number(element.tabIndex) : 0;
|
|
376
369
|
}
|
|
@@ -447,7 +440,7 @@ function resolveOptions(options) {
|
|
|
447
440
|
* High-precision focus management utility with full composed tree support.
|
|
448
441
|
* Handles complex focus rules including tabindex ordering, radio groups, inert.
|
|
449
442
|
*
|
|
450
|
-
* @version 4.3.
|
|
443
|
+
* @version 4.3.31
|
|
451
444
|
* @author Yusuke Kamiyamane
|
|
452
445
|
* @license MIT
|
|
453
446
|
* @copyright Copyright (c) Yusuke Kamiyamane
|
package/dist/index.d.cts
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
* High-precision focus management utility with full composed tree support.
|
|
4
4
|
* Handles complex focus rules including tabindex ordering, radio groups, inert.
|
|
5
5
|
*
|
|
6
|
-
* @version 4.3.
|
|
6
|
+
* @version 4.3.31
|
|
7
7
|
* @author Yusuke Kamiyamane
|
|
8
8
|
* @license MIT
|
|
9
9
|
* @copyright Copyright (c) Yusuke Kamiyamane
|
package/dist/index.d.ts
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
* High-precision focus management utility with full composed tree support.
|
|
4
4
|
* Handles complex focus rules including tabindex ordering, radio groups, inert.
|
|
5
5
|
*
|
|
6
|
-
* @version 4.3.
|
|
6
|
+
* @version 4.3.31
|
|
7
7
|
* @author Yusuke Kamiyamane
|
|
8
8
|
* @license MIT
|
|
9
9
|
* @copyright Copyright (c) Yusuke Kamiyamane
|
package/dist/index.js
CHANGED
|
@@ -76,21 +76,21 @@ function getFocusables(container = document.body, options = {}) {
|
|
|
76
76
|
skipNegativeTabIndexCheck,
|
|
77
77
|
skipVisibilityCheck
|
|
78
78
|
}) || include?.(node)) {
|
|
79
|
-
candidates
|
|
79
|
+
candidates.push(node);
|
|
80
80
|
}
|
|
81
|
-
(composed ? getComposedChildren(node) :
|
|
81
|
+
(composed ? getComposedChildren(node) : [...node.children]).map(traverse2);
|
|
82
82
|
};
|
|
83
|
-
(composed ? getComposedChildren(container) :
|
|
83
|
+
(composed ? getComposedChildren(container) : [...container.children]).map(
|
|
84
84
|
traverse2
|
|
85
85
|
);
|
|
86
86
|
} else {
|
|
87
|
-
for (const
|
|
87
|
+
for (const m of container.querySelectorAll(
|
|
88
88
|
skipNegativeTabIndexCheck ? FOCUSABLE_SELECTOR_WITH_NEGATIVE_TABINDEX : FOCUSABLE_SELECTOR
|
|
89
89
|
)) {
|
|
90
|
-
|
|
90
|
+
m && isFocusable(m, {
|
|
91
91
|
skipNegativeTabIndexCheck,
|
|
92
92
|
skipVisibilityCheck
|
|
93
|
-
}) && candidates.push(
|
|
93
|
+
}) && candidates.push(m);
|
|
94
94
|
}
|
|
95
95
|
}
|
|
96
96
|
return normalizeRadioGroup(
|
|
@@ -226,58 +226,58 @@ function isDisabledDeep(element) {
|
|
|
226
226
|
}
|
|
227
227
|
function normalizeRadioGroup(elements) {
|
|
228
228
|
let map = null;
|
|
229
|
-
for (const
|
|
230
|
-
if (!(
|
|
229
|
+
for (const e of elements) {
|
|
230
|
+
if (!(e instanceof HTMLInputElement)) {
|
|
231
231
|
continue;
|
|
232
232
|
}
|
|
233
|
-
if (!isUngroupedRadio(
|
|
233
|
+
if (!isUngroupedRadio(e)) {
|
|
234
234
|
continue;
|
|
235
235
|
}
|
|
236
236
|
if (!map) {
|
|
237
237
|
map = /* @__PURE__ */ new Map();
|
|
238
238
|
}
|
|
239
|
-
const root =
|
|
240
|
-
let
|
|
241
|
-
if (!
|
|
242
|
-
|
|
243
|
-
map.set(root,
|
|
239
|
+
const root = e.getRootNode();
|
|
240
|
+
let groups = map.get(root);
|
|
241
|
+
if (!groups) {
|
|
242
|
+
groups = /* @__PURE__ */ new Map();
|
|
243
|
+
map.set(root, groups);
|
|
244
244
|
}
|
|
245
|
-
let
|
|
246
|
-
if (!
|
|
247
|
-
|
|
248
|
-
|
|
245
|
+
let group = groups.get(e.form);
|
|
246
|
+
if (!group) {
|
|
247
|
+
group = /* @__PURE__ */ new Map();
|
|
248
|
+
groups.set(e.form, group);
|
|
249
249
|
}
|
|
250
|
-
let
|
|
251
|
-
if (!
|
|
252
|
-
|
|
253
|
-
|
|
250
|
+
let radios = group.get(e.name);
|
|
251
|
+
if (!radios) {
|
|
252
|
+
radios = [];
|
|
253
|
+
group.set(e.name, radios);
|
|
254
254
|
}
|
|
255
|
-
|
|
255
|
+
radios.push(e);
|
|
256
256
|
}
|
|
257
257
|
if (!map) {
|
|
258
258
|
return elements;
|
|
259
259
|
}
|
|
260
260
|
const placeholder = /* @__PURE__ */ new Set();
|
|
261
|
-
for (const
|
|
262
|
-
for (const
|
|
263
|
-
for (const
|
|
264
|
-
const radio =
|
|
261
|
+
for (const v of map.values()) {
|
|
262
|
+
for (const w of v.values()) {
|
|
263
|
+
for (const x of w.values()) {
|
|
264
|
+
const radio = x.find((r) => r.checked) ?? x[0];
|
|
265
265
|
radio && placeholder.add(radio);
|
|
266
266
|
}
|
|
267
267
|
}
|
|
268
268
|
}
|
|
269
|
-
return elements.filter((
|
|
270
|
-
if (!(
|
|
269
|
+
return elements.filter((e) => {
|
|
270
|
+
if (!(e instanceof HTMLInputElement)) {
|
|
271
271
|
return true;
|
|
272
272
|
}
|
|
273
|
-
return !isUngroupedRadio(
|
|
273
|
+
return !isUngroupedRadio(e) || placeholder.has(e);
|
|
274
274
|
});
|
|
275
275
|
}
|
|
276
276
|
function sortByTabIndex(elements) {
|
|
277
277
|
const ordered = [];
|
|
278
278
|
const natural = [];
|
|
279
|
-
for (const
|
|
280
|
-
(getTabIndex(
|
|
279
|
+
for (const e of elements) {
|
|
280
|
+
(getTabIndex(e) > 0 ? ordered : natural).push(e);
|
|
281
281
|
}
|
|
282
282
|
return ordered.sort((a, b) => getTabIndex(a) - getTabIndex(b)).concat(natural);
|
|
283
283
|
}
|
|
@@ -294,7 +294,7 @@ function containsComposed(container, element) {
|
|
|
294
294
|
}
|
|
295
295
|
function getComposedChildren(node) {
|
|
296
296
|
if (node instanceof ShadowRoot) {
|
|
297
|
-
return
|
|
297
|
+
return [...node.children];
|
|
298
298
|
}
|
|
299
299
|
if (!(node instanceof Element)) {
|
|
300
300
|
return [];
|
|
@@ -306,9 +306,9 @@ function getComposedChildren(node) {
|
|
|
306
306
|
}
|
|
307
307
|
}
|
|
308
308
|
if (node instanceof HTMLElement && node.shadowRoot?.mode === "open") {
|
|
309
|
-
return
|
|
309
|
+
return [...node.shadowRoot.children];
|
|
310
310
|
}
|
|
311
|
-
return
|
|
311
|
+
return [...node.children];
|
|
312
312
|
}
|
|
313
313
|
function getComposedParent(node) {
|
|
314
314
|
if (node instanceof Element && node.assignedSlot) {
|
|
@@ -324,8 +324,8 @@ function getComposedSiblings(node) {
|
|
|
324
324
|
return [];
|
|
325
325
|
}
|
|
326
326
|
const filtered = [];
|
|
327
|
-
for (const
|
|
328
|
-
filtered.push(
|
|
327
|
+
for (const s of (parent instanceof HTMLSlotElement ? parent.assignedElements({ flatten: true }) : getComposedChildren(parent)).filter((s2) => s2 !== node)) {
|
|
328
|
+
filtered.push(s);
|
|
329
329
|
}
|
|
330
330
|
return filtered;
|
|
331
331
|
}
|
|
@@ -362,13 +362,6 @@ function getActiveElement() {
|
|
|
362
362
|
}
|
|
363
363
|
return current;
|
|
364
364
|
}
|
|
365
|
-
function getChildren(node) {
|
|
366
|
-
const elements = [];
|
|
367
|
-
for (let child = node.firstElementChild; child; child = child.nextElementSibling) {
|
|
368
|
-
elements[elements.length] = child;
|
|
369
|
-
}
|
|
370
|
-
return elements;
|
|
371
|
-
}
|
|
372
365
|
function getTabIndex(element) {
|
|
373
366
|
return "tabIndex" in element ? Number(element.tabIndex) : 0;
|
|
374
367
|
}
|
|
@@ -445,7 +438,7 @@ function resolveOptions(options) {
|
|
|
445
438
|
* High-precision focus management utility with full composed tree support.
|
|
446
439
|
* Handles complex focus rules including tabindex ordering, radio groups, inert.
|
|
447
440
|
*
|
|
448
|
-
* @version 4.3.
|
|
441
|
+
* @version 4.3.31
|
|
449
442
|
* @author Yusuke Kamiyamane
|
|
450
443
|
* @license MIT
|
|
451
444
|
* @copyright Copyright (c) Yusuke Kamiyamane
|