@fusion.dev/helix-headless 0.145.0 → 0.146.0
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/custom-elements.json +7373 -3849
- package/dist/accordion/item/accordion-item.d.ts +14 -0
- package/dist/accordion/item/accordion-item.js +16 -6
- package/dist/accordion/root/accordion-root.d.ts +8 -5
- package/dist/announcement/root/announcement-root.d.ts +3 -2
- package/dist/announcement/root/announcement-root.js +3 -1
- package/dist/app-header/root/app-header-root.d.ts +7 -2
- package/dist/app-header/root/app-header-root.js +9 -1
- package/dist/app-header/sectioning.d.ts +3 -1
- package/dist/app-header/sectioning.js +3 -2
- package/dist/avatar/group/avatar-group.d.ts +20 -14
- package/dist/avatar/group/avatar-group.js +17 -19
- package/dist/badge/root/badge-root.d.ts +3 -1
- package/dist/badge/root/badge-root.js +2 -2
- package/dist/bar-chart/root/bar-chart-root.d.ts +18 -1
- package/dist/bar-chart/root/bar-chart-root.js +52 -15
- package/dist/bar-chart/stack.d.ts +15 -0
- package/dist/bar-chart/stack.js +19 -0
- package/dist/breadcrumbs/root/breadcrumbs-root.d.ts +25 -0
- package/dist/breadcrumbs/root/breadcrumbs-root.js +50 -3
- package/dist/button/root/button-root.d.ts +26 -0
- package/dist/button/root/button-root.js +38 -18
- package/dist/button-group/root/button-group-root.d.ts +2 -1
- package/dist/button-group/root/button-group-root.js +5 -1
- package/dist/canvas/node/canvas-node.d.ts +4 -3
- package/dist/canvas/node/canvas-node.js +3 -2
- package/dist/canvas/root/canvas-root.js +2 -2
- package/dist/card/root/card-root.d.ts +24 -3
- package/dist/card/root/card-root.js +20 -8
- package/dist/carousel/root/carousel-root.d.ts +43 -4
- package/dist/carousel/root/carousel-root.js +40 -12
- package/dist/carousel/stops.d.ts +20 -0
- package/dist/carousel/stops.js +30 -0
- package/dist/chat/message/chat-message.js +5 -4
- package/dist/chat/naming.d.ts +5 -1
- package/dist/chat/naming.js +4 -2
- package/dist/chat/root/chat-root.d.ts +25 -3
- package/dist/chat/root/chat-root.js +22 -5
- package/dist/checkbox/root/checkbox-root.d.ts +20 -0
- package/dist/checkbox/root/checkbox-root.js +14 -1
- package/dist/checkbox-group/root/checkbox-group-root.d.ts +8 -2
- package/dist/checkbox-group/root/checkbox-group-root.js +12 -10
- package/dist/checkbox-group/select-all.d.ts +27 -0
- package/dist/checkbox-group/select-all.js +12 -0
- package/dist/code-block/highlight.d.ts +15 -0
- package/dist/code-block/highlight.js +4 -0
- package/dist/code-block/root/code-block-root.d.ts +49 -1
- package/dist/code-block/root/code-block-root.js +58 -3
- package/dist/color-input/root/color-input-root.d.ts +3 -0
- package/dist/color-input/root/color-input-root.js +6 -3
- package/dist/color-picker/root/color-picker-root.d.ts +33 -4
- package/dist/color-picker/root/color-picker-root.js +80 -21
- package/dist/color-picker/swatches.d.ts +12 -0
- package/dist/color-picker/swatches.js +26 -0
- package/dist/combobox/root/combobox-root.d.ts +43 -0
- package/dist/combobox/root/combobox-root.js +79 -15
- package/dist/command/root/command-root.d.ts +16 -1
- package/dist/command/root/command-root.js +22 -4
- package/dist/copy-button/root/copy-button-root.d.ts +5 -0
- package/dist/copy-button/root/copy-button-root.js +10 -3
- package/dist/data-table/index.d.ts +1 -1
- package/dist/data-table/index.js +1 -1
- package/dist/data-table/keys.d.ts +24 -0
- package/dist/data-table/keys.js +24 -0
- package/dist/data-table/root/data-table-root.d.ts +27 -18
- package/dist/data-table/root/data-table-root.js +20 -52
- package/dist/data-table/tree.d.ts +16 -1
- package/dist/data-table/tree.js +2 -3
- package/dist/date-input/root/date-input-root.d.ts +3 -1
- package/dist/date-input/root/date-input-root.js +18 -7
- package/dist/date-picker/root/date-picker-root.js +12 -6
- package/dist/dialog/description.js +15 -1
- package/dist/dialog/root/dialog-root.d.ts +8 -2
- package/dist/dialog/root/dialog-root.js +16 -1
- package/dist/divider/root/divider-root.d.ts +3 -0
- package/dist/divider/root/divider-root.js +2 -1
- package/dist/donut-chart/root/donut-chart-root.d.ts +31 -0
- package/dist/donut-chart/root/donut-chart-root.js +48 -1
- package/dist/drawer/reveal.d.ts +8 -0
- package/dist/drawer/reveal.js +1 -0
- package/dist/drawer/root/drawer-root.d.ts +59 -0
- package/dist/drawer/root/drawer-root.js +63 -4
- package/dist/drilldown/item/drilldown-item.js +1 -1
- package/dist/drilldown/root/drilldown-root.d.ts +21 -3
- package/dist/drilldown/root/drilldown-root.js +21 -3
- package/dist/element-events.generated.js +31 -5
- package/dist/empty/root/empty-root.d.ts +3 -1
- package/dist/empty/root/empty-root.js +3 -2
- package/dist/file-input/root/file-input-root.d.ts +69 -6
- package/dist/file-input/root/file-input-root.js +82 -19
- package/dist/file-input/screen.d.ts +2 -1
- package/dist/filter-input/menu/filter-menu.d.ts +2 -0
- package/dist/filter-input/menu/filter-menu.js +12 -4
- package/dist/filter-input/root/filter-input-root.d.ts +30 -6
- package/dist/filter-input/root/filter-input-root.js +1 -1
- package/dist/filter-input/suggest.d.ts +28 -3
- package/dist/filter-input/suggest.js +18 -8
- package/dist/format-date/root/format-date-root.d.ts +9 -16
- package/dist/format-date/root/format-date-root.js +10 -27
- package/dist/heatmap/root/heatmap-root.d.ts +24 -13
- package/dist/heatmap/root/heatmap-root.js +34 -12
- package/dist/icon/root/icon-root.d.ts +12 -1
- package/dist/icon/root/icon-root.js +21 -10
- package/dist/icon/settle.d.ts +7 -0
- package/dist/icon/settle.js +10 -0
- package/dist/icon-button/root/icon-button-root.d.ts +2 -0
- package/dist/image/root/image-root.d.ts +5 -1
- package/dist/image/root/image-root.js +1 -1
- package/dist/input/root/input-root.d.ts +12 -2
- package/dist/input/root/input-root.js +11 -2
- package/dist/kbd/root/kbd-root.d.ts +35 -1
- package/dist/kbd/root/kbd-root.js +23 -4
- package/dist/legend/root/legend-root.d.ts +55 -8
- package/dist/legend/root/legend-root.js +55 -13
- package/dist/lightbox/root/lightbox-root.d.ts +49 -6
- package/dist/lightbox/root/lightbox-root.js +86 -19
- package/dist/lightbox/zoom-controller.d.ts +59 -0
- package/dist/lightbox/zoom-controller.js +128 -0
- package/dist/lightbox/zoom.d.ts +22 -0
- package/dist/lightbox/zoom.js +16 -0
- package/dist/line-chart/root/line-chart-root.d.ts +22 -1
- package/dist/line-chart/root/line-chart-root.js +21 -1
- package/dist/list/item/list-item.d.ts +2 -0
- package/dist/list/item/list-item.js +11 -2
- package/dist/list/root/list-root.d.ts +62 -13
- package/dist/list/root/list-root.js +70 -13
- package/dist/list/selection.d.ts +37 -7
- package/dist/list/selection.js +16 -7
- package/dist/listbox/root/listbox-root.d.ts +37 -1
- package/dist/listbox/root/listbox-root.js +49 -3
- package/dist/loader/busy.d.ts +10 -0
- package/dist/loader/busy.js +11 -0
- package/dist/loader/root/loader-root.d.ts +9 -2
- package/dist/loader/root/loader-root.js +23 -3
- package/dist/megamenu/root/megamenu-root.d.ts +51 -10
- package/dist/megamenu/root/megamenu-root.js +76 -5
- package/dist/menu/item/menu-item.d.ts +51 -2
- package/dist/menu/item/menu-item.js +47 -23
- package/dist/menu/root/menu-root.d.ts +14 -0
- package/dist/menu/root/menu-root.js +2 -2
- package/dist/meter/root/meter-root.d.ts +20 -1
- package/dist/meter/root/meter-root.js +11 -15
- package/dist/navigation/root/navigation-root.d.ts +2 -1
- package/dist/navigation/root/navigation-root.js +2 -2
- package/dist/notifications/root/notifications-root.d.ts +10 -3
- package/dist/notifications/root/notifications-root.js +19 -7
- package/dist/number-input/root/number-input-root.d.ts +17 -8
- package/dist/number-input/root/number-input-root.js +2 -7
- package/dist/object-inspector/root/object-inspector-root.d.ts +75 -27
- package/dist/object-inspector/root/object-inspector-root.js +117 -76
- package/dist/object-inspector/rows.d.ts +18 -0
- package/dist/object-inspector/rows.js +33 -0
- package/dist/option/root/option-root.d.ts +5 -3
- package/dist/outline/root/outline-root.d.ts +18 -0
- package/dist/outline/root/outline-root.js +23 -5
- package/dist/pagination/size/pagination-size.d.ts +1 -0
- package/dist/pagination/size/pagination-size.js +1 -1
- package/dist/pin-input/code.d.ts +10 -0
- package/dist/pin-input/code.js +13 -0
- package/dist/pin-input/root/pin-input-root.d.ts +25 -1
- package/dist/pin-input/root/pin-input-root.js +10 -11
- package/dist/popover/hide-outside.d.ts +14 -0
- package/dist/popover/hide-outside.js +41 -0
- package/dist/popover/root/popover-root.d.ts +57 -7
- package/dist/popover/root/popover-root.js +58 -3
- package/dist/progress/root/progress-root.d.ts +20 -0
- package/dist/progress/root/progress-root.js +15 -15
- package/dist/qr-code/export.d.ts +26 -1
- package/dist/qr-code/export.js +14 -0
- package/dist/qr-code/root/qr-code-root.d.ts +19 -5
- package/dist/qr-code/root/qr-code-root.js +58 -9
- package/dist/quote/marks.d.ts +8 -0
- package/dist/quote/marks.js +5 -0
- package/dist/quote/root/quote-root.d.ts +14 -2
- package/dist/quote/root/quote-root.js +23 -1
- package/dist/radio/root/radio-root.d.ts +6 -2
- package/dist/radio/root/radio-root.js +6 -1
- package/dist/rating/root/rating-root.d.ts +9 -4
- package/dist/rating/root/rating-root.js +31 -7
- package/dist/rating/steps.d.ts +7 -0
- package/dist/rating/steps.js +9 -0
- package/dist/scatter-chart/fit.d.ts +15 -0
- package/dist/scatter-chart/fit.js +35 -0
- package/dist/scatter-chart/root/scatter-chart-root.d.ts +21 -1
- package/dist/scatter-chart/root/scatter-chart-root.js +30 -17
- package/dist/scroll-area/root/scroll-area-root.d.ts +22 -51
- package/dist/scroll-area/root/scroll-area-root.js +57 -173
- package/dist/scroll-area/scrollbar-controller.d.ts +111 -0
- package/dist/scroll-area/scrollbar-controller.js +172 -0
- package/dist/scroll-area/scrollbar.d.ts +27 -0
- package/dist/scroll-area/scrollbar.js +9 -0
- package/dist/select/root/select-root.d.ts +15 -0
- package/dist/select/root/select-root.js +18 -6
- package/dist/skeleton/root/skeleton-root.d.ts +3 -0
- package/dist/skeleton/root/skeleton-root.js +4 -2
- package/dist/skip-link/root/skip-link-root.js +2 -2
- package/dist/slider/root/slider-root.d.ts +41 -4
- package/dist/slider/root/slider-root.js +23 -3
- package/dist/sparkline/readings.d.ts +18 -0
- package/dist/sparkline/readings.js +19 -0
- package/dist/sparkline/root/sparkline-root.d.ts +78 -7
- package/dist/sparkline/root/sparkline-root.js +118 -23
- package/dist/speed-dial/root/speed-dial-root.js +2 -2
- package/dist/splitter/root/splitter-root.d.ts +7 -12
- package/dist/splitter/root/splitter-root.js +209 -204
- package/dist/stat/root/stat-root.d.ts +14 -5
- package/dist/stat/root/stat-root.js +21 -5
- package/dist/steps/reach.d.ts +5 -0
- package/dist/steps/reach.js +3 -0
- package/dist/steps/root/steps-root.d.ts +49 -3
- package/dist/steps/root/steps-root.js +44 -5
- package/dist/steps/step/step.d.ts +7 -0
- package/dist/steps/step/step.js +7 -2
- package/dist/switch/root/switch-root.d.ts +10 -0
- package/dist/table/column/table-column.d.ts +0 -10
- package/dist/table/column/table-column.js +3 -19
- package/dist/table/root/table-root.d.ts +31 -10
- package/dist/table/root/table-root.js +2 -13
- package/dist/tabs/panel/tab-panel.d.ts +16 -3
- package/dist/tabs/panel/tab-panel.js +34 -5
- package/dist/tabs/root/tabs-root.d.ts +12 -0
- package/dist/tabs/root/tabs-root.js +1 -1
- package/dist/tabs/tab/tab.d.ts +5 -0
- package/dist/tabs/tab/tab.js +5 -2
- package/dist/tag/group/tag-group.d.ts +31 -4
- package/dist/tag/group/tag-group.js +46 -7
- package/dist/tag/root/tag-root.js +9 -2
- package/dist/textarea/root/textarea-root.d.ts +28 -1
- package/dist/textarea/root/textarea-root.js +40 -1
- package/dist/time-input/root/time-input-root.d.ts +5 -1
- package/dist/time-input/root/time-input-root.js +16 -8
- package/dist/time-picker/root/time-picker-root.d.ts +18 -4
- package/dist/time-picker/root/time-picker-root.js +7 -10
- package/dist/time-picker/wheel-name.d.ts +9 -0
- package/dist/time-picker/wheel-name.js +15 -0
- package/dist/timeline/group/timeline-group.js +2 -2
- package/dist/toast/item/toast-item.d.ts +14 -1
- package/dist/toast/item/toast-item.js +22 -5
- package/dist/toast/root/toast-root.d.ts +6 -0
- package/dist/toast/root/toast-root.js +16 -1
- package/dist/toggle/group/toggle-group.d.ts +24 -3
- package/dist/toggle/group/toggle-group.js +34 -5
- package/dist/tooltip/root/tooltip-root.d.ts +13 -2
- package/dist/tooltip/root/tooltip-root.js +9 -1
- package/dist/tour/back.d.ts +10 -0
- package/dist/tour/back.js +8 -0
- package/dist/tour/root/tour-root.d.ts +30 -2
- package/dist/tour/root/tour-root.js +34 -8
- package/dist/tree/item/tree-item.d.ts +7 -3
- package/dist/tree/item/tree-item.js +3 -0
- package/dist/tree/root/tree-root.d.ts +24 -3
- package/dist/tree/root/tree-root.js +32 -13
- package/dist/tree/selection.js +2 -15
- package/dist/trend/root/trend-root.d.ts +43 -18
- package/dist/trend/root/trend-root.js +31 -6
- package/dist/video/media-events.d.ts +13 -18
- package/dist/video/media-events.js +1 -5
- package/dist/video/root/video-root.d.ts +18 -5
- package/dist/video/root/video-root.js +19 -10
- package/dist/video-playlist/menu/video-playlist-menu.d.ts +2 -0
- package/dist/video-playlist/menu/video-playlist-menu.js +2 -1
- package/dist/video-playlist/root/video-playlist-root.d.ts +7 -1
- package/dist/virtual-list/fill.d.ts +0 -8
- package/dist/virtual-list/fill.js +1 -17
- package/dist/virtual-list/plan.d.ts +49 -0
- package/dist/virtual-list/plan.js +16 -0
- package/dist/virtual-list/root/virtual-list-root.d.ts +114 -13
- package/dist/virtual-list/root/virtual-list-root.js +183 -40
- package/lint.json +1 -1
- package/package.json +8 -8
- package/types/jsx.d.ts +4577 -835
- package/types/vue.d.ts +926 -168
- package/dist/chat/relative-clock.d.ts +0 -39
- package/dist/chat/relative-clock.js +0 -31
- package/dist/data-table/root/order.d.ts +0 -141
- package/dist/data-table/root/order.js +0 -76
- package/dist/tag/selection.d.ts +0 -10
- package/dist/tag/selection.js +0 -12
|
@@ -30,6 +30,7 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
30
30
|
this.submenu = false;
|
|
31
31
|
this.start = false;
|
|
32
32
|
this.end = false;
|
|
33
|
+
this.description = false;
|
|
33
34
|
this.readStart = () => {
|
|
34
35
|
const slot = this.renderRoot.querySelector('slot[name="start"]');
|
|
35
36
|
this.start = (slot?.assignedNodes().length ?? 0) > 0;
|
|
@@ -38,6 +39,10 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
38
39
|
const slot = this.renderRoot.querySelector('slot[name="end"]');
|
|
39
40
|
this.end = (slot?.assignedNodes().length ?? 0) > 0;
|
|
40
41
|
};
|
|
42
|
+
this.readDescription = () => {
|
|
43
|
+
const slot = this.renderRoot.querySelector('slot[name="description"]');
|
|
44
|
+
this.description = (slot?.assignedNodes().length ?? 0) > 0;
|
|
45
|
+
};
|
|
41
46
|
this.readSubmenu = () => {
|
|
42
47
|
const slot = this.renderRoot.querySelector('slot[name="submenu"]');
|
|
43
48
|
this.submenu = (slot?.assignedElements().length ?? 0) > 0;
|
|
@@ -74,11 +79,27 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
74
79
|
this.submenu = named('submenu');
|
|
75
80
|
this.start = named('start');
|
|
76
81
|
this.end = named('end');
|
|
82
|
+
this.description = named('description');
|
|
77
83
|
}
|
|
78
84
|
firstUpdated(changed) {
|
|
79
85
|
super.firstUpdated(changed);
|
|
80
86
|
this.finishHydration();
|
|
81
87
|
}
|
|
88
|
+
renderDescription() {
|
|
89
|
+
return html `<slot
|
|
90
|
+
id="description"
|
|
91
|
+
name="description"
|
|
92
|
+
aria-hidden="true"
|
|
93
|
+
?data-empty=${!this.description}
|
|
94
|
+
@slotchange=${this.readDescription}
|
|
95
|
+
></slot>`;
|
|
96
|
+
}
|
|
97
|
+
get describedBy() {
|
|
98
|
+
const ids = [this.description ? 'description' : '', this.end ? 'end-words' : '']
|
|
99
|
+
.filter((id) => id !== '')
|
|
100
|
+
.join(' ');
|
|
101
|
+
return ids === '' ? nothing : ids;
|
|
102
|
+
}
|
|
82
103
|
renderEnd() {
|
|
83
104
|
const kbd = this.tag('kbd');
|
|
84
105
|
return html `<span part="end" ?data-empty=${!this.end && this.shortcut === ''}
|
|
@@ -86,10 +107,10 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
86
107
|
? nothing
|
|
87
108
|
: staticHtml `<${kbd}
|
|
88
109
|
part="shortcut"
|
|
89
|
-
exportparts="kbd: shortcut-kbd"
|
|
110
|
+
exportparts="kbd: shortcut-kbd, key: shortcut-key, separator: shortcut-separator"
|
|
90
111
|
aria-hidden="true"
|
|
91
112
|
keys=${this.shortcut}
|
|
92
|
-
></${kbd}>`}<slot name="end" @slotchange=${this.readEnd}></slot
|
|
113
|
+
></${kbd}>`}<slot id="end-words" name="end" aria-hidden="true" @slotchange=${this.readEnd}></slot
|
|
93
114
|
></span>`;
|
|
94
115
|
}
|
|
95
116
|
focus() {
|
|
@@ -152,6 +173,23 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
152
173
|
this.tick();
|
|
153
174
|
this.dispatchEvent(new HelixSelectEvent({ value: this.value }));
|
|
154
175
|
}
|
|
176
|
+
renderMark(submenu) {
|
|
177
|
+
if (submenu) {
|
|
178
|
+
return html `<slot name="chevron" aria-hidden="true"
|
|
179
|
+
><svg part="mark" data-mirror fill="currentColor" viewBox=${caretRight.viewBox} aria-hidden="true">
|
|
180
|
+
${unsafeSVG(caretRight.content)}
|
|
181
|
+
</svg></slot
|
|
182
|
+
>`;
|
|
183
|
+
}
|
|
184
|
+
if (this.checked) {
|
|
185
|
+
return html `<slot name="check" aria-hidden="true"
|
|
186
|
+
><svg part="mark" fill="currentColor" viewBox=${check.viewBox} aria-hidden="true">
|
|
187
|
+
${unsafeSVG(check.content)}
|
|
188
|
+
</svg></slot
|
|
189
|
+
>`;
|
|
190
|
+
}
|
|
191
|
+
return nothing;
|
|
192
|
+
}
|
|
155
193
|
render() {
|
|
156
194
|
if (this.showingSubmenu) {
|
|
157
195
|
return html `<slot name="submenu" @slotchange=${this.readSubmenu}></slot>`;
|
|
@@ -169,28 +207,9 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
169
207
|
><slot name="start" @slotchange=${this.readStart}></slot
|
|
170
208
|
></span>
|
|
171
209
|
<slot></slot>
|
|
210
|
+
${this.renderDescription()}
|
|
172
211
|
${this.renderEnd()}
|
|
173
|
-
${submenu
|
|
174
|
-
? html `<svg
|
|
175
|
-
part="mark"
|
|
176
|
-
data-mirror
|
|
177
|
-
fill="currentColor"
|
|
178
|
-
viewBox=${caretRight.viewBox}
|
|
179
|
-
aria-hidden="true"
|
|
180
|
-
>
|
|
181
|
-
${unsafeSVG(caretRight.content)}
|
|
182
|
-
</svg>`
|
|
183
|
-
: this.checked
|
|
184
|
-
? html `<svg
|
|
185
|
-
part="mark"
|
|
186
|
-
fill="currentColor"
|
|
187
|
-
viewBox=${check.viewBox}
|
|
188
|
-
aria-hidden="true"
|
|
189
|
-
>
|
|
190
|
-
${unsafeSVG(check.content)}
|
|
191
|
-
</svg>`
|
|
192
|
-
:
|
|
193
|
-
nothing}`;
|
|
212
|
+
${this.renderMark(submenu)}`;
|
|
194
213
|
return html `${linked
|
|
195
214
|
? html `<a
|
|
196
215
|
part="item"
|
|
@@ -200,6 +219,7 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
200
219
|
?download=${this.download}
|
|
201
220
|
role=${role}
|
|
202
221
|
aria-checked=${checkedState}
|
|
222
|
+
aria-describedby=${this.describedBy}
|
|
203
223
|
aria-haspopup=${submenu ? 'menu' : nothing}
|
|
204
224
|
aria-keyshortcuts=${keys}
|
|
205
225
|
tabindex="-1"
|
|
@@ -210,6 +230,7 @@ let HelixHeadlessMenuItem = class HelixHeadlessMenuItem extends HelixElement {
|
|
|
210
230
|
part="item"
|
|
211
231
|
role=${role}
|
|
212
232
|
aria-checked=${checkedState}
|
|
233
|
+
aria-describedby=${this.describedBy}
|
|
213
234
|
aria-disabled=${this.disabled ? 'true' : nothing}
|
|
214
235
|
aria-haspopup=${submenu ? 'menu' : nothing}
|
|
215
236
|
aria-keyshortcuts=${keys}
|
|
@@ -265,6 +286,9 @@ __decorate([
|
|
|
265
286
|
__decorate([
|
|
266
287
|
state()
|
|
267
288
|
], HelixHeadlessMenuItem.prototype, "end", void 0);
|
|
289
|
+
__decorate([
|
|
290
|
+
state()
|
|
291
|
+
], HelixHeadlessMenuItem.prototype, "description", void 0);
|
|
268
292
|
HelixHeadlessMenuItem = __decorate([
|
|
269
293
|
customElement('helix-headless-menu-item')
|
|
270
294
|
], HelixHeadlessMenuItem);
|
|
@@ -28,6 +28,20 @@ declare const HelixHeadlessMenu_base: (new (...args: any[]) => import("@fusion.d
|
|
|
28
28
|
* its heading. Between runs of rows, a `<helix-divider announced>` is a
|
|
29
29
|
* separator a screen reader announces.
|
|
30
30
|
*
|
|
31
|
+
* Keys: Enter, Space or Down Arrow on the trigger opens the menu on its first
|
|
32
|
+
* row, and Up Arrow on its last. In the menu, Up and Down Arrow move between
|
|
33
|
+
* rows, Home and End go to the first and the last, a typed letter moves to
|
|
34
|
+
* the next row whose name starts with it, Enter and Space choose, Right Arrow
|
|
35
|
+
* opens a row's submenu and Left Arrow goes back, the two swapping on a
|
|
36
|
+
* right-to-left page, and Escape closes the menu and returns focus to the
|
|
37
|
+
* trigger. Tab closes it and moves on.
|
|
38
|
+
*
|
|
39
|
+
* While it is open, the surface carries the trigger's width as
|
|
40
|
+
* `--floating-anchor-inline-size` and the room left below it as
|
|
41
|
+
* `--floating-available-block-size`, as Radix's dropdown menu publishes its
|
|
42
|
+
* trigger's width, for a menu as wide as its trigger:
|
|
43
|
+
* `helix-menu::part(surface) { min-inline-size: var(--floating-anchor-inline-size) }`.
|
|
44
|
+
*
|
|
31
45
|
* With `context`, the trigger is an area and the menu is its context menu: a
|
|
32
46
|
* right-click, a long press, Shift+F10 or the menu key over the area opens it
|
|
33
47
|
* at the pointer, or at the area's corner from the keyboard, as Radix's context
|
|
@@ -4,7 +4,7 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
|
|
|
4
4
|
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
5
5
|
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
6
|
};
|
|
7
|
-
import { AriaForwardController, anchorElement, customElement, DrilldownController, deepActiveElement, deepContains, HelixElement, inlineStep, KeyboardNavigationController, MixinCollection, MixinControllerOpen, PopoverController, scrollItemIntoView, slottedWords, tellDisclosure, } from '@fusion.dev/helix-core';
|
|
7
|
+
import { AriaForwardController, anchorElement, customElement, DrilldownController, deepActiveElement, deepContains, HelixElement, inlineStep, KeyboardNavigationController, MixinCollection, MixinControllerOpen, PopoverController, scrollItemIntoView, slottedWords, tellDisclosure, typeaheadBy, } from '@fusion.dev/helix-core';
|
|
8
8
|
import { caretLeft } from '@fusion.dev/helix-icons';
|
|
9
9
|
import { html, nothing } from 'lit';
|
|
10
10
|
import { property } from 'lit/decorators.js';
|
|
@@ -29,7 +29,7 @@ let HelixHeadlessMenu = class HelixHeadlessMenu extends MixinCollection(MixinCon
|
|
|
29
29
|
items: () => (this.open ? this.items : []),
|
|
30
30
|
reserved: () => ['ArrowLeft', 'ArrowRight'],
|
|
31
31
|
selects: () => false,
|
|
32
|
-
typeahead: (item) => slottedWords(item, ['']),
|
|
32
|
+
typeahead: typeaheadBy((item) => slottedWords(item, [''])),
|
|
33
33
|
});
|
|
34
34
|
this.aria = new AriaForwardController(this, {
|
|
35
35
|
label: true,
|
|
@@ -71,6 +71,21 @@ export declare class HelixHeadlessMeter extends HelixElement {
|
|
|
71
71
|
* no reader.
|
|
72
72
|
*/
|
|
73
73
|
band?: MeterBand;
|
|
74
|
+
/**
|
|
75
|
+
* `Intl.NumberFormat` options the reading is written with, as React Aria's
|
|
76
|
+
* Meter and ProgressBar take them: a unit, a currency, or a number of
|
|
77
|
+
* decimals. Written as JSON in the attribute.
|
|
78
|
+
*
|
|
79
|
+
* ```html
|
|
80
|
+
* <helix-meter value="18" max="32" format-options='{"style":"unit","unit":"gigabyte"}'></helix-meter>
|
|
81
|
+
* ```
|
|
82
|
+
*
|
|
83
|
+
* A `percent` style writes the share of the range, and any other the value
|
|
84
|
+
* itself, so the example says "18 GB", and a value past an end as it is.
|
|
85
|
+
* Absent is a whole percentage. The words are announced as well as shown.
|
|
86
|
+
* `value-text` still wins.
|
|
87
|
+
*/
|
|
88
|
+
formatOptions?: Intl.NumberFormatOptions;
|
|
74
89
|
/**
|
|
75
90
|
* Bottom of the high band.
|
|
76
91
|
*
|
|
@@ -199,7 +214,11 @@ export declare class HelixHeadlessMeter extends HelixElement {
|
|
|
199
214
|
* keeps an unbanded meter from being painted as good news.
|
|
200
215
|
*/
|
|
201
216
|
private get computedBand();
|
|
202
|
-
/**
|
|
217
|
+
/**
|
|
218
|
+
* What the reading says: the consumer's words, or the reading in
|
|
219
|
+
* `format-options`, a share of the range for a percent and the value for
|
|
220
|
+
* anything else.
|
|
221
|
+
*/
|
|
203
222
|
private get text();
|
|
204
223
|
protected willUpdate(changed: PropertyValues): void;
|
|
205
224
|
/**
|
|
@@ -4,21 +4,10 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
|
|
|
4
4
|
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
5
5
|
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
6
|
};
|
|
7
|
-
import { customElement, HelixElement, hostAria, slottedWords } from '@fusion.dev/helix-core';
|
|
7
|
+
import { customElement, formatNumber, HelixElement, hostAria, slottedWords, } from '@fusion.dev/helix-core';
|
|
8
8
|
import { html, nothing, svg } from 'lit';
|
|
9
9
|
import { property } from 'lit/decorators.js';
|
|
10
|
-
const
|
|
11
|
-
const percent = (share, locale) => {
|
|
12
|
-
let format = percents.get(locale);
|
|
13
|
-
if (!format) {
|
|
14
|
-
format = new Intl.NumberFormat(locale || undefined, {
|
|
15
|
-
maximumFractionDigits: 0,
|
|
16
|
-
style: 'percent',
|
|
17
|
-
});
|
|
18
|
-
percents.set(locale, format);
|
|
19
|
-
}
|
|
20
|
-
return format.format(share);
|
|
21
|
-
};
|
|
10
|
+
const WHOLE_PERCENT = { maximumFractionDigits: 0, style: 'percent' };
|
|
22
11
|
let HelixHeadlessMeter = class HelixHeadlessMeter extends HelixElement {
|
|
23
12
|
constructor() {
|
|
24
13
|
super(...arguments);
|
|
@@ -80,7 +69,11 @@ let HelixHeadlessMeter = class HelixHeadlessMeter extends HelixElement {
|
|
|
80
69
|
return distance === 0 ? 'good' : distance === 1 ? 'fair' : 'poor';
|
|
81
70
|
}
|
|
82
71
|
get text() {
|
|
83
|
-
|
|
72
|
+
const options = this.formatOptions;
|
|
73
|
+
return (this.valueText ||
|
|
74
|
+
(options && options.style !== 'percent'
|
|
75
|
+
? formatNumber(Number.isFinite(this.value) ? this.value : this.span.min, this.locale, options)
|
|
76
|
+
: formatNumber(this.ratio, this.locale, options ?? WHOLE_PERCENT)));
|
|
84
77
|
}
|
|
85
78
|
willUpdate(changed) {
|
|
86
79
|
super.willUpdate(changed);
|
|
@@ -90,7 +83,7 @@ let HelixHeadlessMeter = class HelixHeadlessMeter extends HelixElement {
|
|
|
90
83
|
this.internals.ariaValueMax = String(max);
|
|
91
84
|
this.internals.ariaValueNow = String(this.reading);
|
|
92
85
|
this.internals.ariaValueText =
|
|
93
|
-
this.valueText ||
|
|
86
|
+
this.valueText || this.formatOptions !== undefined || this.beyond ? this.text : null;
|
|
94
87
|
}
|
|
95
88
|
renderRound() {
|
|
96
89
|
const bounds = this.thresholds;
|
|
@@ -144,6 +137,9 @@ let HelixHeadlessMeter = class HelixHeadlessMeter extends HelixElement {
|
|
|
144
137
|
__decorate([
|
|
145
138
|
property()
|
|
146
139
|
], HelixHeadlessMeter.prototype, "band", void 0);
|
|
140
|
+
__decorate([
|
|
141
|
+
property({ attribute: 'format-options', type: Object })
|
|
142
|
+
], HelixHeadlessMeter.prototype, "formatOptions", void 0);
|
|
147
143
|
__decorate([
|
|
148
144
|
property({ type: Number })
|
|
149
145
|
], HelixHeadlessMeter.prototype, "high", void 0);
|
|
@@ -36,8 +36,9 @@ import { type PropertyValues, type TemplateResult } from 'lit';
|
|
|
36
36
|
* @documentation https://fusion.dev/helix/components/navigation
|
|
37
37
|
*
|
|
38
38
|
* @slot - The destinations, as your own links.
|
|
39
|
+
* @slot indicator - A marker of your own, drawn inside the `indicator` part, where the current destination's place and size reach it.
|
|
39
40
|
*
|
|
40
|
-
* @csspart indicator - The marker that moves to the current destination.
|
|
41
|
+
* @csspart indicator - The marker that moves to the current destination. It carries the destination's place and size as `--indicator-x`, `--indicator-y`, `--indicator-inline-size` and `--indicator-block-size`, and `data-placed` once it has been placed.
|
|
41
42
|
* @csspart nav - The navigation landmark.
|
|
42
43
|
*/
|
|
43
44
|
export declare class HelixHeadlessNavigation extends HelixElement {
|
|
@@ -53,7 +53,7 @@ let HelixHeadlessNavigation = class HelixHeadlessNavigation extends HelixElement
|
|
|
53
53
|
});
|
|
54
54
|
}
|
|
55
55
|
get items() {
|
|
56
|
-
const slot = this.renderRoot.querySelector('slot');
|
|
56
|
+
const slot = this.renderRoot.querySelector('slot:not([name])');
|
|
57
57
|
return (slot?.assignedElements() ?? []);
|
|
58
58
|
}
|
|
59
59
|
watch() {
|
|
@@ -80,7 +80,7 @@ let HelixHeadlessNavigation = class HelixHeadlessNavigation extends HelixElement
|
|
|
80
80
|
}
|
|
81
81
|
render() {
|
|
82
82
|
return html `<nav part="nav" aria-label=${this.label}>
|
|
83
|
-
<div part="indicator" aria-hidden="true"></div>
|
|
83
|
+
<div part="indicator" aria-hidden="true"><slot name="indicator"></slot></div>
|
|
84
84
|
<slot @slotchange=${() => this.watch()}></slot>
|
|
85
85
|
</nav>`;
|
|
86
86
|
}
|
|
@@ -32,7 +32,8 @@ declare const HelixHeadlessNotifications_base: (new (...args: any[]) => import("
|
|
|
32
32
|
* **`load-more` adds a button after the list** that sends `helix-load-more`,
|
|
33
33
|
* for a feed that holds one page of a longer list. Append the next page, set
|
|
34
34
|
* `loading` while it is on its way, and take `load-more` off once there is
|
|
35
|
-
* nothing more.
|
|
35
|
+
* nothing more. While the feed is loading the button stays, so focus stays on
|
|
36
|
+
* it, and it is `aria-disabled` and sends nothing.
|
|
36
37
|
*
|
|
37
38
|
* @since 0.1.0
|
|
38
39
|
* @status stable
|
|
@@ -55,7 +56,7 @@ declare const HelixHeadlessNotifications_base: (new (...args: any[]) => import("
|
|
|
55
56
|
* @csspart live - A copy of the empty and loading messages, in a live region that screen readers announce when they change. Visually hidden in the styled tier.
|
|
56
57
|
* @csspart loading - Shown while the feed is loading.
|
|
57
58
|
* @csspart mark-all - The control that marks everything read.
|
|
58
|
-
* @csspart more - The button after the list that asks for more, while `load-more` is set
|
|
59
|
+
* @csspart more - The button after the list that asks for more, while `load-more` is set. It is `aria-disabled` while the feed is loading.
|
|
59
60
|
*
|
|
60
61
|
* @cssstate media - While a notification in the list holds something in its media slot, so every row keeps that column.
|
|
61
62
|
*/
|
|
@@ -260,7 +261,13 @@ export declare class HelixHeadlessNotifications extends HelixHeadlessNotificatio
|
|
|
260
261
|
private markEmpty;
|
|
261
262
|
protected updated(changed: PropertyValues): void;
|
|
262
263
|
protected render(): TemplateResult;
|
|
263
|
-
/**
|
|
264
|
+
/**
|
|
265
|
+
* Asks for the next page, for the `load-more` button, unless a page is
|
|
266
|
+
* already on its way.
|
|
267
|
+
*
|
|
268
|
+
* The button stays while the feed is loading, marked `aria-disabled`, so
|
|
269
|
+
* focus stays on it: removed, it took focus with it to the body.
|
|
270
|
+
*/
|
|
264
271
|
private readonly askForMore;
|
|
265
272
|
/**
|
|
266
273
|
* Marks everything read, and keeps focus in the feed.
|
|
@@ -54,7 +54,9 @@ let HelixHeadlessNotifications = class HelixHeadlessNotifications extends MixinC
|
|
|
54
54
|
}
|
|
55
55
|
};
|
|
56
56
|
this.askForMore = () => {
|
|
57
|
-
this.
|
|
57
|
+
if (!this.loading) {
|
|
58
|
+
this.dispatchEvent(new HelixLoadMoreEvent());
|
|
59
|
+
}
|
|
58
60
|
};
|
|
59
61
|
this.handleMarkAll = (event) => {
|
|
60
62
|
const button = event.currentTarget;
|
|
@@ -151,9 +153,9 @@ let HelixHeadlessNotifications = class HelixHeadlessNotifications extends MixinC
|
|
|
151
153
|
rove() {
|
|
152
154
|
const rows = this.reachable;
|
|
153
155
|
const stop = rovingStop(rows, this.stopRow);
|
|
154
|
-
const
|
|
155
|
-
for (const row of
|
|
156
|
-
const position =
|
|
156
|
+
const items = this.items;
|
|
157
|
+
for (const row of items) {
|
|
158
|
+
const position = items.indexOf(row) + 1;
|
|
157
159
|
whenHydrated(row, () => {
|
|
158
160
|
row.stop = row === stop;
|
|
159
161
|
row.position = this.total === undefined ? 0 : position;
|
|
@@ -210,13 +212,23 @@ let HelixHeadlessNotifications = class HelixHeadlessNotifications extends MixinC
|
|
|
210
212
|
</button>`
|
|
211
213
|
: nothing}
|
|
212
214
|
</div>
|
|
213
|
-
<div
|
|
215
|
+
<div
|
|
216
|
+
part="list"
|
|
217
|
+
role="list"
|
|
218
|
+
aria-busy=${this.loading ? 'true' : nothing}
|
|
219
|
+
aria-label=${this.label || nothing}
|
|
220
|
+
>
|
|
214
221
|
<slot name="items" @slotchange=${this.handleSlotChange}></slot>
|
|
215
222
|
${this.renderStatus(hasItems)}
|
|
216
223
|
</div>
|
|
217
224
|
${this.renderLive(hasItems)}
|
|
218
|
-
${this.loadMore
|
|
219
|
-
? html `<button
|
|
225
|
+
${this.loadMore
|
|
226
|
+
? html `<button
|
|
227
|
+
part="more"
|
|
228
|
+
type="button"
|
|
229
|
+
aria-disabled=${this.loading ? 'true' : nothing}
|
|
230
|
+
@click=${this.askForMore}
|
|
231
|
+
>
|
|
220
232
|
${this.loadMoreLabel}
|
|
221
233
|
</button>`
|
|
222
234
|
: nothing}
|
|
@@ -25,9 +25,10 @@ declare const HelixHeadlessNumberInput_base: (new (...args: any[]) => import("@f
|
|
|
25
25
|
* The locale's group separators are read in every field, so `1,234` is a
|
|
26
26
|
* number in `en-US`.
|
|
27
27
|
*
|
|
28
|
-
* On iOS and iPadOS the field is a text field
|
|
29
|
-
*
|
|
30
|
-
*
|
|
28
|
+
* On iOS and iPadOS the field is a plain text field, with no
|
|
29
|
+
* `role="spinbutton"`, which VoiceOver reads as a slider you cannot type in,
|
|
30
|
+
* and no role description, so VoiceOver says the field is required. React
|
|
31
|
+
* Aria's NumberField does the same.
|
|
31
32
|
*
|
|
32
33
|
* Validity follows the platform's rules: `min`, `max`, and `step` are checked
|
|
33
34
|
* and reported through the host's own `setValidity`, under the platform's flag
|
|
@@ -36,6 +37,19 @@ declare const HelixHeadlessNumberInput_base: (new (...args: any[]) => import("@f
|
|
|
36
37
|
* Stepping is separate from typing, so a number is not corrected while you type
|
|
37
38
|
* it.
|
|
38
39
|
*
|
|
40
|
+
* **Keyboard.** The field is one tab stop, and the stepper buttons are not in
|
|
41
|
+
* the tab order.
|
|
42
|
+
*
|
|
43
|
+
* | Key | What it does |
|
|
44
|
+
* |---|---|
|
|
45
|
+
* | Up, Down | Steps the value up or down by `step`. |
|
|
46
|
+
* | Page Up, Page Down | Steps by `large-step` steps, ten by default. |
|
|
47
|
+
* | Home, End | Goes to `min` or `max`, where there is one. Without one, moves the caret. |
|
|
48
|
+
* | Enter | Commits the typed number and submits the form, as a native field does. |
|
|
49
|
+
*
|
|
50
|
+
* The field has `role="spinbutton"` with `aria-valuenow`, `aria-valuemin`,
|
|
51
|
+
* `aria-valuemax`, and the formatted text in `aria-valuetext`.
|
|
52
|
+
*
|
|
39
53
|
* @since 0.1.0
|
|
40
54
|
* @status stable
|
|
41
55
|
* @category forms
|
|
@@ -154,11 +168,6 @@ export declare class HelixHeadlessNumberInput extends HelixHeadlessNumberInput_b
|
|
|
154
168
|
* Prevents editing. The value is still submitted with the form.
|
|
155
169
|
*/
|
|
156
170
|
readOnly: boolean;
|
|
157
|
-
/**
|
|
158
|
-
* What the field is described as on iOS and iPadOS, where it carries no
|
|
159
|
-
* spinbutton role. See the class description.
|
|
160
|
-
*/
|
|
161
|
-
roleDescription: string;
|
|
162
171
|
/**
|
|
163
172
|
* Makes the label a grip that changes the value when it is dragged.
|
|
164
173
|
*
|
|
@@ -4,7 +4,7 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
|
|
|
4
4
|
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
5
5
|
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
6
|
};
|
|
7
|
-
import { AriaForwardController, appleTouch, valueAsNumber as asNumber, customElement, fillTemplate, formatNumber, numberAsValue as fromNumber, HelixFormElement, holdCaret, MixinControllerValue, MixinField, parseNumber, restoreValue, } from '@fusion.dev/helix-core';
|
|
7
|
+
import { AriaForwardController, appleTouch, valueAsNumber as asNumber, customElement, fillTemplate, formatNumber, numberAsValue as fromNumber, HelixFormElement, holdCaret, MixinControllerValue, MixinField, parseNumber, restoreValue, submitImplicitly, } from '@fusion.dev/helix-core';
|
|
8
8
|
import { minus, plus } from '@fusion.dev/helix-icons';
|
|
9
9
|
import { html, nothing } from 'lit';
|
|
10
10
|
import { property, state } from 'lit/decorators.js';
|
|
@@ -24,7 +24,6 @@ let HelixHeadlessNumberInput = class HelixHeadlessNumberInput extends MixinContr
|
|
|
24
24
|
this.locale = '';
|
|
25
25
|
this.placeholder = '';
|
|
26
26
|
this.readOnly = false;
|
|
27
|
-
this.roleDescription = 'number field';
|
|
28
27
|
this.scrub = false;
|
|
29
28
|
this.step = 1;
|
|
30
29
|
this.valueText = '';
|
|
@@ -138,7 +137,7 @@ let HelixHeadlessNumberInput = class HelixHeadlessNumberInput extends MixinContr
|
|
|
138
137
|
};
|
|
139
138
|
this.handleKeypress = (event) => {
|
|
140
139
|
if (event.key === 'Enter' && !event.defaultPrevented) {
|
|
141
|
-
this.
|
|
140
|
+
submitImplicitly(this.form);
|
|
142
141
|
}
|
|
143
142
|
};
|
|
144
143
|
}
|
|
@@ -317,7 +316,6 @@ let HelixHeadlessNumberInput = class HelixHeadlessNumberInput extends MixinContr
|
|
|
317
316
|
.value=${this.shown}
|
|
318
317
|
type="text"
|
|
319
318
|
role=${this.touchApple ? nothing : 'spinbutton'}
|
|
320
|
-
aria-roledescription=${this.touchApple ? this.roleDescription : nothing}
|
|
321
319
|
inputmode="decimal"
|
|
322
320
|
autocomplete=${this.autocomplete || nothing}
|
|
323
321
|
name=${this.name || nothing}
|
|
@@ -411,9 +409,6 @@ __decorate([
|
|
|
411
409
|
__decorate([
|
|
412
410
|
property({ attribute: 'readonly', reflect: true, type: Boolean })
|
|
413
411
|
], HelixHeadlessNumberInput.prototype, "readOnly", void 0);
|
|
414
|
-
__decorate([
|
|
415
|
-
property({ attribute: 'role-description' })
|
|
416
|
-
], HelixHeadlessNumberInput.prototype, "roleDescription", void 0);
|
|
417
412
|
__decorate([
|
|
418
413
|
property({ reflect: true, type: Boolean })
|
|
419
414
|
], HelixHeadlessNumberInput.prototype, "scrub", void 0);
|
|
@@ -15,13 +15,29 @@ import { type Row } from '../rows.js';
|
|
|
15
15
|
* works with server rendering and with React hydration, which skips object
|
|
16
16
|
* properties. `value` wins when both are set.
|
|
17
17
|
*
|
|
18
|
-
* The tree is one tab stop
|
|
19
|
-
*
|
|
20
|
-
*
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
*
|
|
24
|
-
* a
|
|
18
|
+
* **Keyboard.** The tree is one tab stop, and focus moves from row to row.
|
|
19
|
+
*
|
|
20
|
+
* | Key | What it does |
|
|
21
|
+
* |---|---|
|
|
22
|
+
* | Down, Up | Moves to the next or the previous row. |
|
|
23
|
+
* | Right | Opens a closed branch, or moves into an open one. Left on a right-to-left page. |
|
|
24
|
+
* | Left | Closes an open branch, or moves to the parent. Right on a right-to-left page. |
|
|
25
|
+
* | Home, End | Moves to the first or the last row. |
|
|
26
|
+
* | Enter, Space | Opens or closes a branch. |
|
|
27
|
+
* | `*` | Opens every branch beside the active row. |
|
|
28
|
+
* | A letter or a word | Moves to the next row whose key starts with what you typed. |
|
|
29
|
+
* | Command+C, Control+C | Copies the active row, where no text is selected. |
|
|
30
|
+
*
|
|
31
|
+
* The tree is a `treegrid`, as React Aria's Tree is: each entry is a `row` with
|
|
32
|
+
* one cell, and carries its real level, position, and set size, including in a
|
|
33
|
+
* windowed tree. Nothing in it is chosen, so no row carries `aria-selected`,
|
|
34
|
+
* and a focused row is not announced as selected.
|
|
35
|
+
*
|
|
36
|
+
* A reader opening or closing a branch sends `helix-before-open` or
|
|
37
|
+
* `helix-before-close`, which you can cancel, and then `toggle` with
|
|
38
|
+
* `newState` and `oldState`, as `<details>` does. The branch is the active
|
|
39
|
+
* row, and `expanded` holds every open branch. `*` asks once for all the
|
|
40
|
+
* branches it opens. A script writing `expanded` or `active` sends nothing.
|
|
25
41
|
*
|
|
26
42
|
* `active` is the active row's path, written the way a JSON Pointer writes it:
|
|
27
43
|
* the empty string for the root and `/meta/tags/0` for an entry under it.
|
|
@@ -60,9 +76,12 @@ import { type Row } from '../rows.js';
|
|
|
60
76
|
*
|
|
61
77
|
* @event {HelixActivateEvent} helix-activate - The active row moved, by a key or a click. The detail's `value` is its path.
|
|
62
78
|
* @event {HelixBeforeActivateEvent} helix-before-activate - The active row is about to move, with its new path. Cancelable: cancel it to keep the row where it is.
|
|
79
|
+
* @event {HelixBeforeCloseEvent} helix-before-close - A reader is about to close the active branch. Cancelable: cancel it to keep the branch open.
|
|
80
|
+
* @event {HelixBeforeOpenEvent} helix-before-open - A reader is about to open the active branch, or `*` the branches beside it. Cancelable: cancel it to keep them closed.
|
|
63
81
|
* @event {HelixCopyEvent} helix-copy - A value was put on the clipboard, from the copy button or the keyboard.
|
|
64
82
|
* @event {HelixFilterEvent} helix-filter - Text was typed in the filter field, with what it now holds. Cancelable: cancel it to keep the filter as it was.
|
|
65
83
|
* @event {HelixFilteredEvent} helix-filtered - The filter field changed `filter`, which now holds the text.
|
|
84
|
+
* @event {ToggleEvent} toggle - A reader opened or closed a branch, with `newState` and `oldState`. `expanded` holds every open branch.
|
|
66
85
|
*
|
|
67
86
|
* @csspart after - The space the rows below the drawn rows would take, when `windowed` is set.
|
|
68
87
|
* @csspart before - The space the rows above the drawn rows would take, when `windowed` is set.
|
|
@@ -90,14 +109,14 @@ import { type Row } from '../rows.js';
|
|
|
90
109
|
* @csspart live - How many entries a filter matched, in a region that screen readers announce when it changes. Drawn from the first filter on. Visually hidden in the styled tier.
|
|
91
110
|
* @csspart null - A `null`.
|
|
92
111
|
* @csspart number - A number.
|
|
93
|
-
* @csspart row - One entry, as a tree
|
|
94
|
-
* @csspart row-active - The entry the keyboard is on. Set alongside `row`.
|
|
112
|
+
* @csspart row - One entry, as a row of the tree grid, which takes focus.
|
|
113
|
+
* @csspart row-active - The entry the keyboard is on, which holds the tab stop. Set alongside `row`.
|
|
95
114
|
* @csspart row-match - An entry whose key or value holds the filter. Set alongside `row`.
|
|
96
115
|
* @csspart search-field - The field that sets `filter`, with `filterable`.
|
|
97
116
|
* @csspart string - A string, in quotes.
|
|
98
117
|
* @csspart summary - The brackets that stand for a branch's contents.
|
|
99
118
|
* @csspart toggle - The caret on a branch. It points down when the branch is open and sideways when it is closed.
|
|
100
|
-
* @csspart tree - The tree
|
|
119
|
+
* @csspart tree - The tree grid that holds the rows.
|
|
101
120
|
*
|
|
102
121
|
* @cssproperty --object-inspector-level - How deep a row is, from 0 at the root, for indenting it.
|
|
103
122
|
*/
|
|
@@ -230,6 +249,10 @@ export declare class HelixHeadlessObjectInspector extends HelixElement {
|
|
|
230
249
|
private found;
|
|
231
250
|
/** Set by a keyboard move, so the next render brings the active row into view. */
|
|
232
251
|
private revealing;
|
|
252
|
+
/** Set by a reader's move, so the next render moves focus to the active row. */
|
|
253
|
+
private focusing;
|
|
254
|
+
/** Whether a row held focus as this update began, so a row the render moved gets it back. */
|
|
255
|
+
private hadFocus;
|
|
233
256
|
/** What has been typed toward a key, and when the last letter came. */
|
|
234
257
|
private typed;
|
|
235
258
|
/** The branches of the last value seen, by path, so a new value can tell old ones from new. */
|
|
@@ -266,16 +289,17 @@ export declare class HelixHeadlessObjectInspector extends HelixElement {
|
|
|
266
289
|
/** Opens the branches around each path, where the value has them. */
|
|
267
290
|
private openAround;
|
|
268
291
|
protected willUpdate(changed: PropertyValues): void;
|
|
269
|
-
/**
|
|
270
|
-
* Where the active row goes once the rows have moved: onto `path` where it
|
|
271
|
-
* is still shown, onto the first match where a filter just hid it, and
|
|
272
|
-
* otherwise onto the nearest branch around it that is.
|
|
273
|
-
*/
|
|
274
|
-
private place;
|
|
275
292
|
/** Says how many entries the filter matched, and nothing for an empty one. */
|
|
276
293
|
private tell;
|
|
277
294
|
protected firstUpdated(changed: PropertyValues): void;
|
|
278
295
|
protected updated(changed: PropertyValues): void;
|
|
296
|
+
/**
|
|
297
|
+
* Moves focus to the active row, once it is drawn.
|
|
298
|
+
*
|
|
299
|
+
* After a reader's move only, so a script writing `active` does not take
|
|
300
|
+
* focus from wherever the reader is.
|
|
301
|
+
*/
|
|
302
|
+
private focusActive;
|
|
279
303
|
private load;
|
|
280
304
|
/**
|
|
281
305
|
* Brings the active row into the box.
|
|
@@ -292,6 +316,20 @@ export declare class HelixHeadlessObjectInspector extends HelixElement {
|
|
|
292
316
|
private reveal;
|
|
293
317
|
/** What copying takes: a branch as indented JSON, a string as itself. */
|
|
294
318
|
private copyable;
|
|
319
|
+
/**
|
|
320
|
+
* Asks to open or close branches, and then does and says so:
|
|
321
|
+
* `helix-before-open` or `helix-before-close`, which a listener can cancel,
|
|
322
|
+
* then `toggle`. A reader's act only. Returns whether they moved.
|
|
323
|
+
*/
|
|
324
|
+
private requestOpen;
|
|
325
|
+
/**
|
|
326
|
+
* Says a branch opened or closed under the platform's own name and in its
|
|
327
|
+
* shape: `toggle` with `newState` and `oldState`, not bubbling, as
|
|
328
|
+
* `<details>` sends it and as the open mixin does for the families whose
|
|
329
|
+
* open state it owns. A real `ToggleEvent` where the platform has one, and a
|
|
330
|
+
* plain event carrying the same two fields where it does not.
|
|
331
|
+
*/
|
|
332
|
+
private announceToggle;
|
|
295
333
|
private toggle;
|
|
296
334
|
/**
|
|
297
335
|
* Moves the active row, asking first: `helix-before-activate` with the path,
|
|
@@ -299,8 +337,6 @@ export declare class HelixHeadlessObjectInspector extends HelixElement {
|
|
|
299
337
|
*/
|
|
300
338
|
private move;
|
|
301
339
|
private readonly handleKeydown;
|
|
302
|
-
/** Opens every branch at the active row's level under the same parent, as `*` asks. */
|
|
303
|
-
private openSiblings;
|
|
304
340
|
/**
|
|
305
341
|
* Moves to the next row whose key starts with what was typed.
|
|
306
342
|
*
|
|
@@ -313,7 +349,7 @@ export declare class HelixHeadlessObjectInspector extends HelixElement {
|
|
|
313
349
|
private handleRowClick;
|
|
314
350
|
/** Text typed in the filter field, asked for before the tree narrows to it. */
|
|
315
351
|
private readonly handleFilterInput;
|
|
316
|
-
/** Down from the filter field goes to the
|
|
352
|
+
/** Down from the filter field goes to the active row, where the matches are. */
|
|
317
353
|
private readonly handleFilterKeydown;
|
|
318
354
|
private renderValue;
|
|
319
355
|
/**
|
|
@@ -321,17 +357,29 @@ export declare class HelixHeadlessObjectInspector extends HelixElement {
|
|
|
321
357
|
*
|
|
322
358
|
* **`row-active` and no attribute beside it.** Which row the keys are on is
|
|
323
359
|
* drawn by a sheet and by nothing else: the accessibility tree hears it from
|
|
324
|
-
*
|
|
325
|
-
*
|
|
326
|
-
*
|
|
327
|
-
* attribute selector.
|
|
360
|
+
* focus, which the row holds, so an attribute would be a second spelling with
|
|
361
|
+
* no reader. The name is the one a consumer can reach, nothing being able to
|
|
362
|
+
* follow `::part()` with an attribute selector.
|
|
328
363
|
*
|
|
329
|
-
*
|
|
330
|
-
*
|
|
331
|
-
*
|
|
332
|
-
*
|
|
364
|
+
* **A `row` of a `treegrid` with one cell, focused itself, and no
|
|
365
|
+
* `aria-selected`**, because nothing here is chosen. Chromium takes the
|
|
366
|
+
* focused item of a single-selection `tree` as selected, by focus or by
|
|
367
|
+
* `aria-activedescendant` (measured), so every arrow press was also announced
|
|
368
|
+
* as a selection, and `aria-selected="false"` on every row was the one way to
|
|
369
|
+
* turn it off. A row of a tree grid is not selected by focus, which is why
|
|
370
|
+
* React Aria's Tree is one. The cell is `display: contents`, so the row lays
|
|
371
|
+
* out its text as it did.
|
|
333
372
|
*/
|
|
334
373
|
private renderRow;
|
|
374
|
+
/** Whether a row of the tree holds focus. */
|
|
375
|
+
private hasFocusedRow;
|
|
376
|
+
/**
|
|
377
|
+
* A row that takes focus some other way than the keys, from a script or a
|
|
378
|
+
* screen reader, becomes the active row, so focus and the keys agree.
|
|
379
|
+
*/
|
|
380
|
+
private readonly handleFocusIn;
|
|
381
|
+
/** A row kept drawn for focus is let go once focus leaves it. */
|
|
382
|
+
private readonly handleFocusOut;
|
|
335
383
|
/** The copy button, behind the seam Code Block's uses, so each tier renders its own. */
|
|
336
384
|
protected renderCopyButton(row: Row | undefined): TemplateResult;
|
|
337
385
|
protected render(): TemplateResult;
|