@aceshooting/lyra-ui 1.2.0 → 2.1.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/README.md +98 -14
- package/custom-elements.json +30279 -12124
- package/dist/components/app-rail/app-rail-item.d.ts +30 -0
- package/dist/components/app-rail/app-rail-item.js +68 -0
- package/dist/components/app-rail/app-rail-item.styles.d.ts +1 -0
- package/dist/components/app-rail/app-rail-item.styles.js +65 -0
- package/dist/components/app-rail/app-rail.d.ts +168 -0
- package/dist/components/app-rail/app-rail.js +419 -0
- package/dist/components/app-rail/app-rail.styles.d.ts +1 -0
- package/dist/components/app-rail/app-rail.styles.js +128 -0
- package/dist/components/attachment-chip/attachment-chip.d.ts +141 -0
- package/dist/components/attachment-chip/attachment-chip.js +356 -0
- package/dist/components/attachment-chip/attachment-chip.styles.d.ts +1 -0
- package/dist/components/attachment-chip/attachment-chip.styles.js +184 -0
- package/dist/components/attachment-trigger/attachment-trigger.d.ts +96 -0
- package/dist/components/attachment-trigger/attachment-trigger.js +270 -0
- package/dist/components/attachment-trigger/attachment-trigger.styles.d.ts +1 -0
- package/dist/components/attachment-trigger/attachment-trigger.styles.js +90 -0
- package/dist/components/chart/bar-chart.js +2 -18
- package/dist/components/chart/box-plot.d.ts +25 -1
- package/dist/components/chart/box-plot.js +147 -7
- package/dist/components/chart/box-plot.styles.js +13 -0
- package/dist/components/chart/bubble-chart.js +2 -18
- package/dist/components/chart/chart-loader.d.ts +44 -13
- package/dist/components/chart/chart-loader.js +65 -18
- package/dist/components/chart/chart.d.ts +55 -12
- package/dist/components/chart/chart.js +247 -49
- package/dist/components/chart/doughnut-chart.js +2 -18
- package/dist/components/chart/histogram-bin.d.ts +7 -1
- package/dist/components/chart/histogram-bin.js +32 -14
- package/dist/components/chart/histogram.js +8 -16
- package/dist/components/chart/line-chart.js +2 -18
- package/dist/components/chart/lite-chart.d.ts +134 -3
- package/dist/components/chart/lite-chart.js +382 -67
- package/dist/components/chart/lite-chart.styles.js +9 -0
- package/dist/components/chart/pie-chart.js +2 -18
- package/dist/components/chart/polar-area-chart.js +2 -18
- package/dist/components/chart/radar-chart.js +2 -18
- package/dist/components/chart/scatter-chart.js +2 -18
- package/dist/components/chat-composer/chat-composer.d.ts +133 -0
- package/dist/components/chat-composer/chat-composer.js +366 -0
- package/dist/components/chat-composer/chat-composer.styles.d.ts +1 -0
- package/dist/components/chat-composer/chat-composer.styles.js +145 -0
- package/dist/components/chat-message/chat-message.d.ts +141 -0
- package/dist/components/chat-message/chat-message.js +331 -0
- package/dist/components/chat-message/chat-message.styles.d.ts +1 -0
- package/dist/components/chat-message/chat-message.styles.js +203 -0
- package/dist/components/checkbox/checkbox.d.ts +117 -0
- package/dist/components/checkbox/checkbox.js +353 -0
- package/dist/components/checkbox/checkbox.styles.d.ts +1 -0
- package/dist/components/checkbox/checkbox.styles.js +77 -0
- package/dist/components/chip/chip-group.d.ts +56 -0
- package/dist/components/chip/chip-group.js +130 -0
- package/dist/components/chip/chip-group.styles.d.ts +1 -0
- package/dist/components/chip/chip-group.styles.js +57 -0
- package/dist/components/chip/chip.d.ts +64 -0
- package/dist/components/chip/chip.js +122 -0
- package/dist/components/chip/chip.styles.d.ts +1 -0
- package/dist/components/chip/chip.styles.js +115 -0
- package/dist/components/citation-badge/citation-badge.d.ts +113 -0
- package/dist/components/citation-badge/citation-badge.js +318 -0
- package/dist/components/citation-badge/citation-badge.styles.d.ts +1 -0
- package/dist/components/citation-badge/citation-badge.styles.js +96 -0
- package/dist/components/code-block/code-block.d.ts +127 -0
- package/dist/components/code-block/code-block.js +382 -0
- package/dist/components/code-block/code-block.styles.d.ts +1 -0
- package/dist/components/code-block/code-block.styles.js +187 -0
- package/dist/components/code-block/code-loader.d.ts +87 -0
- package/dist/components/code-block/code-loader.js +142 -0
- package/dist/components/combobox/combobox.d.ts +65 -6
- package/dist/components/combobox/combobox.js +258 -48
- package/dist/components/combobox/combobox.styles.js +3 -3
- package/dist/components/combobox/option.d.ts +5 -1
- package/dist/components/combobox/option.js +35 -0
- package/dist/components/context-meter/context-meter.d.ts +53 -0
- package/dist/components/context-meter/context-meter.js +159 -0
- package/dist/components/context-meter/context-meter.styles.d.ts +1 -0
- package/dist/components/context-meter/context-meter.styles.js +114 -0
- package/dist/components/conversation-item/conversation-item.d.ts +125 -0
- package/dist/components/conversation-item/conversation-item.js +331 -0
- package/dist/components/conversation-item/conversation-item.styles.d.ts +1 -0
- package/dist/components/conversation-item/conversation-item.styles.js +155 -0
- package/dist/components/date-picker/calendar-core.d.ts +24 -0
- package/dist/components/date-picker/calendar-core.js +51 -4
- package/dist/components/date-picker/date-input.d.ts +100 -9
- package/dist/components/date-picker/date-input.js +383 -66
- package/dist/components/date-picker/date-picker.d.ts +35 -4
- package/dist/components/date-picker/date-picker.js +171 -44
- package/dist/components/dialog/confirm.d.ts +40 -0
- package/dist/components/dialog/confirm.js +76 -0
- package/dist/components/dialog/dialog.d.ts +129 -0
- package/dist/components/dialog/dialog.js +288 -0
- package/dist/components/dialog/dialog.styles.d.ts +1 -0
- package/dist/components/dialog/dialog.styles.js +96 -0
- package/dist/components/dock-panel/dock-panel.d.ts +142 -0
- package/dist/components/dock-panel/dock-panel.js +359 -0
- package/dist/components/dock-panel/dock-panel.styles.d.ts +1 -0
- package/dist/components/dock-panel/dock-panel.styles.js +159 -0
- package/dist/components/document-preview/document-preview.d.ts +143 -0
- package/dist/components/document-preview/document-preview.js +388 -0
- package/dist/components/document-preview/document-preview.styles.d.ts +1 -0
- package/dist/components/document-preview/document-preview.styles.js +191 -0
- package/dist/components/empty/empty.d.ts +1 -2
- package/dist/components/empty/empty.js +18 -12
- package/dist/components/empty/empty.styles.js +0 -3
- package/dist/components/export-button/csv.js +1 -1
- package/dist/components/export-button/export-button.d.ts +12 -0
- package/dist/components/export-button/export-button.js +35 -5
- package/dist/components/export-button/export-button.styles.js +5 -1
- package/dist/components/file-input/accept.js +2 -0
- package/dist/components/file-input/file-input.d.ts +10 -1
- package/dist/components/file-input/file-input.js +36 -5
- package/dist/components/flag/flag.d.ts +29 -13
- package/dist/components/flag/flag.js +54 -14
- package/dist/components/flag/flag.styles.js +1 -1
- package/dist/components/flag/language-map.d.ts +4 -1
- package/dist/components/flag/language-map.js +6 -3
- package/dist/components/gauge/gauge.d.ts +10 -1
- package/dist/components/gauge/gauge.js +41 -13
- package/dist/components/generation-status/generation-status.d.ts +117 -0
- package/dist/components/generation-status/generation-status.js +327 -0
- package/dist/components/generation-status/generation-status.styles.d.ts +1 -0
- package/dist/components/generation-status/generation-status.styles.js +84 -0
- package/dist/components/graph/graph.d.ts +37 -3
- package/dist/components/graph/graph.js +132 -20
- package/dist/components/heatmap/calendar-grid.d.ts +19 -7
- package/dist/components/heatmap/calendar-grid.js +42 -18
- package/dist/components/heatmap/heatmap-scale.d.ts +11 -1
- package/dist/components/heatmap/heatmap-scale.js +14 -2
- package/dist/components/heatmap/heatmap.d.ts +227 -12
- package/dist/components/heatmap/heatmap.js +488 -93
- package/dist/components/json-viewer/json-viewer.d.ts +70 -0
- package/dist/components/json-viewer/json-viewer.js +361 -0
- package/dist/components/json-viewer/json-viewer.styles.d.ts +1 -0
- package/dist/components/json-viewer/json-viewer.styles.js +177 -0
- package/dist/components/kbd/kbd.d.ts +77 -0
- package/dist/components/kbd/kbd.js +231 -0
- package/dist/components/kbd/kbd.styles.d.ts +1 -0
- package/dist/components/kbd/kbd.styles.js +52 -0
- package/dist/components/live-region/live-region.d.ts +90 -0
- package/dist/components/live-region/live-region.js +189 -0
- package/dist/components/live-region/live-region.styles.d.ts +1 -0
- package/dist/components/live-region/live-region.styles.js +10 -0
- package/dist/components/map/map.d.ts +32 -7
- package/dist/components/map/map.js +133 -32
- package/dist/components/markdown/markdown-loader.d.ts +58 -0
- package/dist/components/markdown/markdown-loader.js +77 -0
- package/dist/components/markdown/markdown.d.ts +119 -0
- package/dist/components/markdown/markdown.js +389 -0
- package/dist/components/markdown/markdown.styles.d.ts +1 -0
- package/dist/components/markdown/markdown.styles.js +88 -0
- package/dist/components/media-card/media-card.d.ts +130 -0
- package/dist/components/media-card/media-card.js +273 -0
- package/dist/components/media-card/media-card.styles.d.ts +1 -0
- package/dist/components/media-card/media-card.styles.js +132 -0
- package/dist/components/mention-popover/mention-popover.d.ts +203 -0
- package/dist/components/mention-popover/mention-popover.js +493 -0
- package/dist/components/mention-popover/mention-popover.styles.d.ts +1 -0
- package/dist/components/mention-popover/mention-popover.styles.js +101 -0
- package/dist/components/menu/menu-item.d.ts +91 -0
- package/dist/components/menu/menu-item.js +206 -0
- package/dist/components/menu/menu-item.styles.d.ts +1 -0
- package/dist/components/menu/menu-item.styles.js +75 -0
- package/dist/components/menu/menu.d.ts +167 -0
- package/dist/components/menu/menu.js +461 -0
- package/dist/components/menu/menu.styles.d.ts +1 -0
- package/dist/components/menu/menu.styles.js +67 -0
- package/dist/components/model-select/model-select.d.ts +170 -0
- package/dist/components/model-select/model-select.js +588 -0
- package/dist/components/model-select/model-select.styles.d.ts +1 -0
- package/dist/components/model-select/model-select.styles.js +203 -0
- package/dist/components/model-settings-panel/model-settings-panel.d.ts +93 -0
- package/dist/components/model-settings-panel/model-settings-panel.js +209 -0
- package/dist/components/model-settings-panel/model-settings-panel.styles.d.ts +1 -0
- package/dist/components/model-settings-panel/model-settings-panel.styles.js +82 -0
- package/dist/components/playback/playback.d.ts +19 -3
- package/dist/components/playback/playback.js +109 -33
- package/dist/components/playback/playback.styles.js +6 -1
- package/dist/components/responsive-panel/responsive-panel.d.ts +163 -0
- package/dist/components/responsive-panel/responsive-panel.js +363 -0
- package/dist/components/responsive-panel/responsive-panel.styles.d.ts +1 -0
- package/dist/components/responsive-panel/responsive-panel.styles.js +103 -0
- package/dist/components/result-card/result-card.d.ts +50 -0
- package/dist/components/result-card/result-card.js +89 -0
- package/dist/components/result-card/result-card.styles.d.ts +1 -0
- package/dist/components/result-card/result-card.styles.js +49 -0
- package/dist/components/result-card/result-field.d.ts +36 -0
- package/dist/components/result-card/result-field.js +87 -0
- package/dist/components/result-card/result-field.styles.d.ts +1 -0
- package/dist/components/result-card/result-field.styles.js +32 -0
- package/dist/components/select/select.d.ts +84 -4
- package/dist/components/select/select.js +251 -36
- package/dist/components/skeleton/skeleton.d.ts +3 -0
- package/dist/components/skeleton/skeleton.js +7 -1
- package/dist/components/skeleton/skeleton.styles.js +5 -4
- package/dist/components/slider/slider.d.ts +141 -0
- package/dist/components/slider/slider.js +467 -0
- package/dist/components/slider/slider.styles.d.ts +1 -0
- package/dist/components/slider/slider.styles.js +87 -0
- package/dist/components/source-card/source-card.d.ts +104 -0
- package/dist/components/source-card/source-card.js +195 -0
- package/dist/components/source-card/source-card.styles.d.ts +1 -0
- package/dist/components/source-card/source-card.styles.js +69 -0
- package/dist/components/source-list/source-list.d.ts +63 -0
- package/dist/components/source-list/source-list.js +130 -0
- package/dist/components/source-list/source-list.styles.d.ts +1 -0
- package/dist/components/source-list/source-list.styles.js +59 -0
- package/dist/components/sparkline/sparkline.js +58 -20
- package/dist/components/split/split.d.ts +224 -5
- package/dist/components/split/split.js +617 -43
- package/dist/components/split/split.styles.js +47 -0
- package/dist/components/stat/stat.d.ts +15 -4
- package/dist/components/stat/stat.js +53 -12
- package/dist/components/stream-status/stream-status.d.ts +126 -0
- package/dist/components/stream-status/stream-status.js +292 -0
- package/dist/components/stream-status/stream-status.styles.d.ts +1 -0
- package/dist/components/stream-status/stream-status.styles.js +103 -0
- package/dist/components/streaming-text/streaming-text.d.ts +104 -0
- package/dist/components/streaming-text/streaming-text.js +224 -0
- package/dist/components/streaming-text/streaming-text.styles.d.ts +1 -0
- package/dist/components/streaming-text/streaming-text.styles.js +63 -0
- package/dist/components/switch/switch.d.ts +103 -0
- package/dist/components/switch/switch.js +250 -0
- package/dist/components/switch/switch.styles.d.ts +1 -0
- package/dist/components/switch/switch.styles.js +75 -0
- package/dist/components/table/table.d.ts +89 -5
- package/dist/components/table/table.js +243 -26
- package/dist/components/table/table.styles.js +6 -1
- package/dist/components/tabs/tabs.d.ts +74 -0
- package/dist/components/tabs/tabs.js +254 -0
- package/dist/components/tabs/tabs.styles.d.ts +1 -0
- package/dist/components/tabs/tabs.styles.js +74 -0
- package/dist/components/thinking-panel/thinking-panel.d.ts +123 -0
- package/dist/components/thinking-panel/thinking-panel.js +260 -0
- package/dist/components/thinking-panel/thinking-panel.styles.d.ts +1 -0
- package/dist/components/thinking-panel/thinking-panel.styles.js +123 -0
- package/dist/components/time-range/time-range.d.ts +59 -2
- package/dist/components/time-range/time-range.js +163 -67
- package/dist/components/toast/toast-item.d.ts +12 -2
- package/dist/components/toast/toast-item.js +106 -44
- package/dist/components/toast/toast-item.styles.js +59 -28
- package/dist/components/toast/toast.js +17 -5
- package/dist/components/toast/toaster.js +10 -1
- package/dist/components/tool-approval-dialog/tool-approval-dialog.d.ts +131 -0
- package/dist/components/tool-approval-dialog/tool-approval-dialog.js +329 -0
- package/dist/components/tool-approval-dialog/tool-approval-dialog.styles.d.ts +1 -0
- package/dist/components/tool-approval-dialog/tool-approval-dialog.styles.js +160 -0
- package/dist/components/tool-call-chip/tool-call-chip.d.ts +105 -0
- package/dist/components/tool-call-chip/tool-call-chip.js +349 -0
- package/dist/components/tool-call-chip/tool-call-chip.styles.d.ts +1 -0
- package/dist/components/tool-call-chip/tool-call-chip.styles.js +203 -0
- package/dist/components/tool-param-form/tool-param-form.d.ts +206 -0
- package/dist/components/tool-param-form/tool-param-form.js +610 -0
- package/dist/components/tool-param-form/tool-param-form.styles.d.ts +1 -0
- package/dist/components/tool-param-form/tool-param-form.styles.js +75 -0
- package/dist/components/tool-result-dialog/tool-result-dialog.d.ts +122 -0
- package/dist/components/tool-result-dialog/tool-result-dialog.js +358 -0
- package/dist/components/tool-result-dialog/tool-result-dialog.styles.d.ts +1 -0
- package/dist/components/tool-result-dialog/tool-result-dialog.styles.js +176 -0
- package/dist/components/tool-result-view/registry.d.ts +73 -0
- package/dist/components/tool-result-view/registry.js +89 -0
- package/dist/components/tool-result-view/tool-result-view.d.ts +58 -0
- package/dist/components/tool-result-view/tool-result-view.js +152 -0
- package/dist/components/tool-result-view/tool-result-view.styles.d.ts +1 -0
- package/dist/components/tool-result-view/tool-result-view.styles.js +13 -0
- package/dist/components/tool-select-dialog/tool-select-dialog.d.ts +151 -0
- package/dist/components/tool-select-dialog/tool-select-dialog.js +350 -0
- package/dist/components/tool-select-dialog/tool-select-dialog.styles.d.ts +1 -0
- package/dist/components/tool-select-dialog/tool-select-dialog.styles.js +191 -0
- package/dist/components/tree/tree-node.d.ts +15 -3
- package/dist/components/tree/tree-node.js +20 -7
- package/dist/components/tree/tree.d.ts +25 -10
- package/dist/components/tree/tree.js +39 -31
- package/dist/components/typing-indicator/typing-indicator.d.ts +70 -0
- package/dist/components/typing-indicator/typing-indicator.js +108 -0
- package/dist/components/typing-indicator/typing-indicator.styles.d.ts +1 -0
- package/dist/components/typing-indicator/typing-indicator.styles.js +132 -0
- package/dist/components/virtual-list/virtual-list.d.ts +210 -0
- package/dist/components/virtual-list/virtual-list.js +607 -0
- package/dist/components/virtual-list/virtual-list.styles.d.ts +1 -0
- package/dist/components/virtual-list/virtual-list.styles.js +56 -0
- package/dist/components/widget/widget.d.ts +5 -4
- package/dist/components/widget/widget.js +54 -120
- package/dist/components/widget/widget.styles.js +8 -2
- package/dist/components/word-cloud/word-cloud-layout.d.ts +7 -0
- package/dist/components/word-cloud/word-cloud-layout.js +29 -2
- package/dist/components/word-cloud/word-cloud.d.ts +28 -2
- package/dist/components/word-cloud/word-cloud.js +69 -19
- package/dist/components/word-cloud/word-cloud.styles.js +16 -3
- package/dist/internal/anchored-validity.d.ts +1 -0
- package/dist/internal/anchored-validity.js +86 -0
- package/dist/internal/announcer.d.ts +57 -0
- package/dist/internal/announcer.js +71 -0
- package/dist/internal/form-associated.d.ts +8 -0
- package/dist/internal/form-associated.js +98 -15
- package/dist/internal/group-by-recency.d.ts +50 -0
- package/dist/internal/group-by-recency.js +80 -0
- package/dist/internal/numbers.d.ts +12 -0
- package/dist/internal/numbers.js +26 -0
- package/dist/internal/overlay-manager.d.ts +51 -0
- package/dist/internal/overlay-manager.js +523 -0
- package/dist/internal/positioner.js +27 -3
- package/dist/internal/rtl.d.ts +23 -0
- package/dist/internal/rtl.js +28 -0
- package/dist/internal/safe-url.d.ts +12 -0
- package/dist/internal/safe-url.js +41 -0
- package/dist/internal/scroll-lock.d.ts +10 -5
- package/dist/internal/scroll-lock.js +30 -14
- package/dist/internal/tokens.styles.js +22 -10
- package/dist/lyra.d.ts +133 -31
- package/dist/lyra.js +96 -26
- package/llms-full.txt +4546 -183
- package/llms.txt +21 -5
- package/package.json +41 -6
- package/dist/components/chart/bar-chart.stories.d.ts +0 -5
- package/dist/components/chart/bar-chart.stories.js +0 -20
- package/dist/components/chart/box-plot.stories.d.ts +0 -5
- package/dist/components/chart/box-plot.stories.js +0 -29
- package/dist/components/chart/bubble-chart.stories.d.ts +0 -5
- package/dist/components/chart/bubble-chart.stories.js +0 -26
- package/dist/components/chart/chart.stories.d.ts +0 -32
- package/dist/components/chart/chart.stories.js +0 -141
- package/dist/components/chart/doughnut-chart.stories.d.ts +0 -5
- package/dist/components/chart/doughnut-chart.stories.js +0 -26
- package/dist/components/chart/histogram.stories.d.ts +0 -5
- package/dist/components/chart/histogram.stories.js +0 -17
- package/dist/components/chart/line-chart.stories.d.ts +0 -22
- package/dist/components/chart/line-chart.stories.js +0 -99
- package/dist/components/chart/lite-chart.stories.d.ts +0 -14
- package/dist/components/chart/lite-chart.stories.js +0 -114
- package/dist/components/chart/pie-chart.stories.d.ts +0 -5
- package/dist/components/chart/pie-chart.stories.js +0 -26
- package/dist/components/chart/polar-area-chart.stories.d.ts +0 -5
- package/dist/components/chart/polar-area-chart.stories.js +0 -20
- package/dist/components/chart/radar-chart.stories.d.ts +0 -5
- package/dist/components/chart/radar-chart.stories.js +0 -20
- package/dist/components/chart/scatter-chart.stories.d.ts +0 -5
- package/dist/components/chart/scatter-chart.stories.js +0 -31
- package/dist/components/combobox/combobox.stories.d.ts +0 -24
- package/dist/components/combobox/combobox.stories.js +0 -102
- package/dist/components/date-picker/date-input.stories.d.ts +0 -10
- package/dist/components/date-picker/date-input.stories.js +0 -48
- package/dist/components/date-picker/date-picker.stories.d.ts +0 -10
- package/dist/components/date-picker/date-picker.stories.js +0 -25
- package/dist/components/empty/empty.stories.d.ts +0 -7
- package/dist/components/empty/empty.stories.js +0 -34
- package/dist/components/export-button/export-button.stories.d.ts +0 -7
- package/dist/components/export-button/export-button.stories.js +0 -37
- package/dist/components/file-input/file-input.stories.d.ts +0 -7
- package/dist/components/file-input/file-input.stories.js +0 -19
- package/dist/components/flag/flag.stories.d.ts +0 -6
- package/dist/components/flag/flag.stories.js +0 -31
- package/dist/components/gauge/gauge.stories.d.ts +0 -8
- package/dist/components/gauge/gauge.stories.js +0 -19
- package/dist/components/graph/graph.stories.d.ts +0 -8
- package/dist/components/graph/graph.stories.js +0 -68
- package/dist/components/heatmap/heatmap.stories.d.ts +0 -27
- package/dist/components/heatmap/heatmap.stories.js +0 -179
- package/dist/components/map/map.stories.d.ts +0 -15
- package/dist/components/map/map.stories.js +0 -135
- package/dist/components/playback/playback.stories.d.ts +0 -7
- package/dist/components/playback/playback.stories.js +0 -16
- package/dist/components/select/select.stories.d.ts +0 -21
- package/dist/components/select/select.stories.js +0 -91
- package/dist/components/skeleton/skeleton.stories.d.ts +0 -5
- package/dist/components/skeleton/skeleton.stories.js +0 -16
- package/dist/components/sparkline/sparkline.stories.d.ts +0 -11
- package/dist/components/sparkline/sparkline.stories.js +0 -39
- package/dist/components/split/split.stories.d.ts +0 -7
- package/dist/components/split/split.stories.js +0 -36
- package/dist/components/stat/stat.stories.d.ts +0 -9
- package/dist/components/stat/stat.stories.js +0 -81
- package/dist/components/table/table.stories.d.ts +0 -12
- package/dist/components/table/table.stories.js +0 -67
- package/dist/components/time-range/time-range.stories.d.ts +0 -8
- package/dist/components/time-range/time-range.stories.js +0 -26
- package/dist/components/toast/toast.stories.d.ts +0 -8
- package/dist/components/toast/toast.stories.js +0 -72
- package/dist/components/tree/tree.stories.d.ts +0 -9
- package/dist/components/tree/tree.stories.js +0 -52
- package/dist/components/widget/widget.stories.d.ts +0 -9
- package/dist/components/widget/widget.stories.js +0 -74
- package/dist/components/word-cloud/word-cloud.stories.d.ts +0 -10
- package/dist/components/word-cloud/word-cloud.stories.js +0 -55
|
@@ -8,9 +8,25 @@ import { html, nothing } from 'lit';
|
|
|
8
8
|
import { property, query, state } from 'lit/decorators.js';
|
|
9
9
|
import { LyraElement } from '../../internal/lyra-element.js';
|
|
10
10
|
import { defineElement } from '../../internal/prefix.js';
|
|
11
|
-
import {
|
|
11
|
+
import { nextId, srOnly } from '../../internal/a11y.js';
|
|
12
|
+
import { loadChartJs, loadChartJsWithZoom } from './chart-loader.js';
|
|
12
13
|
import { styles } from './chart.styles.js';
|
|
13
14
|
import '../skeleton/skeleton.js';
|
|
15
|
+
const CHART_TYPES = new Set([
|
|
16
|
+
'line',
|
|
17
|
+
'bar',
|
|
18
|
+
'scatter',
|
|
19
|
+
'pie',
|
|
20
|
+
'doughnut',
|
|
21
|
+
'radar',
|
|
22
|
+
'polarArea',
|
|
23
|
+
'bubble',
|
|
24
|
+
]);
|
|
25
|
+
function normalizeChartType(value) {
|
|
26
|
+
return typeof value === 'string' && CHART_TYPES.has(value)
|
|
27
|
+
? value
|
|
28
|
+
: 'line';
|
|
29
|
+
}
|
|
14
30
|
/**
|
|
15
31
|
* Recursively merges `override` onto `base`, matching JSON-merge semantics:
|
|
16
32
|
* plain objects are merged key-by-key at every depth; arrays, functions, and
|
|
@@ -39,15 +55,21 @@ const FALLBACK_TICK_COLOR = '#6b7280';
|
|
|
39
55
|
const FALLBACK_LEGEND_COLOR = '#1a1a1a';
|
|
40
56
|
const FALLBACK_TOOLTIP_BG = '#fff';
|
|
41
57
|
const FALLBACK_TOOLTIP_TEXT = '#1a1a1a';
|
|
42
|
-
function deepMerge(base, override) {
|
|
58
|
+
function deepMerge(base, override, seen = new WeakMap()) {
|
|
59
|
+
if (typeof override === 'object' && override !== null) {
|
|
60
|
+
const previous = seen.get(override);
|
|
61
|
+
if (previous !== undefined)
|
|
62
|
+
return previous;
|
|
63
|
+
}
|
|
43
64
|
if (!isPlainObject(base) || !isPlainObject(override)) {
|
|
44
65
|
return (override === undefined ? base : override);
|
|
45
66
|
}
|
|
46
67
|
const result = { ...base };
|
|
68
|
+
seen.set(override, result);
|
|
47
69
|
for (const key of Object.keys(override)) {
|
|
48
70
|
if (UNSAFE_KEYS.has(key))
|
|
49
71
|
continue;
|
|
50
|
-
result[key] = deepMerge(base[key], override[key]);
|
|
72
|
+
result[key] = deepMerge(base[key], override[key], seen);
|
|
51
73
|
}
|
|
52
74
|
return result;
|
|
53
75
|
}
|
|
@@ -76,7 +98,12 @@ function deepMerge(base, override) {
|
|
|
76
98
|
* intersect-only — see `handlePointClick()`) a data point/segment.
|
|
77
99
|
* `detail: { datasetIndex: number, index: number, label: string |
|
|
78
100
|
* undefined, value: unknown }`.
|
|
79
|
-
* @csspart base
|
|
101
|
+
* @csspart base - The chart wrapper.
|
|
102
|
+
* @csspart canvas - The Chart.js canvas.
|
|
103
|
+
* @csspart reset-zoom-button - The reset-zoom control when zoom is active.
|
|
104
|
+
* @csspart description - The accessible chart summary.
|
|
105
|
+
* @csspart data-table - The optional generated or slotted data table.
|
|
106
|
+
* @slot data-table - An optional consumer-provided accessible table alternative.
|
|
80
107
|
*/
|
|
81
108
|
export class LyraChart extends LyraElement {
|
|
82
109
|
constructor() {
|
|
@@ -92,6 +119,12 @@ export class LyraChart extends LyraElement {
|
|
|
92
119
|
this.yLabel = '';
|
|
93
120
|
this.y2Label = '';
|
|
94
121
|
this.beginAtZero = true;
|
|
122
|
+
/** Accessible name applied to the canvas. Falls back to the dataset labels. */
|
|
123
|
+
this.accessibleLabel = '';
|
|
124
|
+
/** Accessible description for the canvas. When unset, a concise data/trend summary is generated. */
|
|
125
|
+
this.accessibleDescription = '';
|
|
126
|
+
/** Makes the generated data table visible; it remains screen-reader available when false. */
|
|
127
|
+
this.showDataTable = false;
|
|
95
128
|
/** Sets `options.indexAxis = 'y'`, Chart.js's own mechanism for horizontal bars (also applies to line/area types). */
|
|
96
129
|
this.horizontal = false;
|
|
97
130
|
/** Stacks the `x`/`y`(/`y2`) scale entries `buildScales()` returns; only meaningful for `bar` and `line` types. */
|
|
@@ -100,18 +133,21 @@ export class LyraChart extends LyraElement {
|
|
|
100
133
|
this.loading = true;
|
|
101
134
|
this.zoomed = false;
|
|
102
135
|
this.visible = true;
|
|
103
|
-
this.lastSignature = '';
|
|
104
136
|
// `chartjs-plugin-zoom`'s own `resetZoom()` synchronously re-invokes the
|
|
105
137
|
// `onZoomComplete` callback below as part of its reset, which would emit a
|
|
106
138
|
// stale `{zoomed: true}` right before `resetZoom()` emits the real
|
|
107
139
|
// `{zoomed: false}`. Set while this component's own `resetZoom()` is
|
|
108
140
|
// driving the plugin so that re-entrant callback is ignored.
|
|
109
141
|
this.suppressZoomComplete = false;
|
|
142
|
+
this.descriptionId = nextId('chart-description');
|
|
110
143
|
}
|
|
111
|
-
static { this.styles = [LyraElement.styles, styles]; }
|
|
144
|
+
static { this.styles = [LyraElement.styles, styles, srOnly]; }
|
|
112
145
|
connectedCallback() {
|
|
113
146
|
super.connectedCallback();
|
|
114
|
-
|
|
147
|
+
const load = this.zoom ? loadChartJsWithZoom() : loadChartJs();
|
|
148
|
+
void load.then((mod) => {
|
|
149
|
+
if (!this.isConnected)
|
|
150
|
+
return;
|
|
115
151
|
this.loading = false;
|
|
116
152
|
if (!mod)
|
|
117
153
|
return;
|
|
@@ -134,7 +170,41 @@ export class LyraChart extends LyraElement {
|
|
|
134
170
|
this.chart = undefined;
|
|
135
171
|
this.intersectionObserver?.disconnect();
|
|
136
172
|
}
|
|
173
|
+
/**
|
|
174
|
+
* Resets a stale `zoomed` flag before the render pass that's about to call
|
|
175
|
+
* `draw()`: a `type` (or `config.type` override) change that lands on a
|
|
176
|
+
* *different* effective Chart.js type makes `draw()` destroy the old
|
|
177
|
+
* `Chart` instance and construct a brand-new one, which was never zoomed —
|
|
178
|
+
* without this, `render()`'s reset-zoom-button stays visible for an
|
|
179
|
+
* instance that has no zoom/pan state left to reset. Computed here (before
|
|
180
|
+
* render), not in `updated()`/`draw()`, because setting `zoomed` — a
|
|
181
|
+
* reactive `@state` property — from `updated()` would schedule a second,
|
|
182
|
+
* redundant update pass; `willUpdate()` runs before this cycle's render is
|
|
183
|
+
* considered complete, so the same set just folds into the render already
|
|
184
|
+
* in progress. Same rationale as `toast-item.ts`'s `willUpdate()`-vs-
|
|
185
|
+
* `updated()` split.
|
|
186
|
+
*/
|
|
187
|
+
willUpdate() {
|
|
188
|
+
if (!this.zoomed)
|
|
189
|
+
return;
|
|
190
|
+
if (this.effectiveType() !== this.builtType) {
|
|
191
|
+
this.zoomed = false;
|
|
192
|
+
}
|
|
193
|
+
}
|
|
137
194
|
updated(changed) {
|
|
195
|
+
// Disconnected between the property change that scheduled this update
|
|
196
|
+
// and Lit's (microtask-deferred) processing of it — e.g. a property
|
|
197
|
+
// changes and the element is removed in the same synchronous tick, so
|
|
198
|
+
// `disconnectedCallback()` (which already destroyed `this.chart`) runs
|
|
199
|
+
// *before* this method does. Nothing below should run in that case:
|
|
200
|
+
// this method's own unconditional `draw()` call further down would
|
|
201
|
+
// otherwise construct a brand-new `Chart` bound to the now-detached
|
|
202
|
+
// canvas — `draw()`'s own guard (`!chartJsModule || !canvasEl`) doesn't
|
|
203
|
+
// catch this, since both persist on a disconnected-but-intact element.
|
|
204
|
+
// If the component is reconnected later, `connectedCallback()` re-kicks
|
|
205
|
+
// its own load/draw sequence, so nothing is lost by bailing out here.
|
|
206
|
+
if (!this.isConnected)
|
|
207
|
+
return;
|
|
138
208
|
if (this.loading)
|
|
139
209
|
this.setAttribute('aria-busy', 'true');
|
|
140
210
|
else
|
|
@@ -154,15 +224,43 @@ export class LyraChart extends LyraElement {
|
|
|
154
224
|
// other property having changed in the meantime.
|
|
155
225
|
if (this.loading)
|
|
156
226
|
return;
|
|
157
|
-
|
|
158
|
-
|
|
227
|
+
// `zoom` can also turn on after connect (it was false at
|
|
228
|
+
// `connectedCallback()` time, so only the core `loadChartJs()` load was
|
|
229
|
+
// kicked off) — load the zoom plugin on demand now and redraw once it's
|
|
230
|
+
// registered. Mirrors the same `isConnected` guard `connectedCallback()`
|
|
231
|
+
// uses: this method already bailed out above if *already* disconnected,
|
|
232
|
+
// but the element can *also* disconnect during the gap while this
|
|
233
|
+
// dynamic import is in flight — without this guard, `draw()` would
|
|
234
|
+
// construct a new, leaked `Chart` bound to the now-detached canvas once
|
|
235
|
+
// the import resolves.
|
|
236
|
+
if (changed.has('zoom') && this.zoom) {
|
|
237
|
+
void loadChartJsWithZoom().then(() => {
|
|
238
|
+
if (!this.isConnected)
|
|
239
|
+
return;
|
|
240
|
+
this.draw();
|
|
241
|
+
});
|
|
242
|
+
}
|
|
243
|
+
const contentChanged = [
|
|
244
|
+
'type',
|
|
245
|
+
'labels',
|
|
246
|
+
'datasets',
|
|
247
|
+
'legend',
|
|
248
|
+
'area',
|
|
249
|
+
'height',
|
|
250
|
+
'xLabel',
|
|
251
|
+
'yLabel',
|
|
252
|
+
'y2Label',
|
|
253
|
+
'beginAtZero',
|
|
254
|
+
'horizontal',
|
|
255
|
+
'stacked',
|
|
256
|
+
'config',
|
|
257
|
+
'zoom',
|
|
258
|
+
'loading',
|
|
259
|
+
].some((name) => changed.has(name));
|
|
260
|
+
if (!contentChanged)
|
|
159
261
|
return;
|
|
160
262
|
if (!this.visible)
|
|
161
263
|
return; // becoming visible again triggers its own draw() via the observer above
|
|
162
|
-
const signature = this.computeSignature();
|
|
163
|
-
if (signature === this.lastSignature)
|
|
164
|
-
return;
|
|
165
|
-
this.lastSignature = signature;
|
|
166
264
|
this.draw();
|
|
167
265
|
}
|
|
168
266
|
seriesToDataset(s) {
|
|
@@ -170,7 +268,20 @@ export class LyraChart extends LyraElement {
|
|
|
170
268
|
return {
|
|
171
269
|
label: s.label,
|
|
172
270
|
data: s.points ?? s.data ?? [],
|
|
173
|
-
|
|
271
|
+
// Leave unset rather than defaulting to `this.type`: Chart.js already
|
|
272
|
+
// falls back to the chart-level (effective) type for any dataset that
|
|
273
|
+
// doesn't set its own `type`, and forcing `this.type` here unconditionally
|
|
274
|
+
// used to be harmless (it normally matched the effective type anyway) —
|
|
275
|
+
// but it actively breaks a `config.type` override to a different chart
|
|
276
|
+
// family (e.g. attribute `type="line"` + `config.type: 'radar'`): every
|
|
277
|
+
// dataset would carry an explicit `type: 'line'` under a chart whose
|
|
278
|
+
// scales are built for `radar` (a single radial `r` scale, no `x`/`y`),
|
|
279
|
+
// which Chart.js can't reconcile — it hangs the page trying to lay out
|
|
280
|
+
// a cartesian-scale controller against a radial-only scale set. Only
|
|
281
|
+
// `s.type` (an explicit per-series mixed-type override, e.g. a line
|
|
282
|
+
// series over a bar chart of the *same* effective family) is passed
|
|
283
|
+
// through.
|
|
284
|
+
type: s.type,
|
|
174
285
|
fill: s.fill ?? this.area,
|
|
175
286
|
borderWidth: s.width ?? 2,
|
|
176
287
|
borderDash: s.dash ? [4, 4] : undefined,
|
|
@@ -179,7 +290,6 @@ export class LyraChart extends LyraElement {
|
|
|
179
290
|
pointBackgroundColor: s.pointColors,
|
|
180
291
|
pointRadius: s.pointRadius,
|
|
181
292
|
yAxisID: s.axis === 'y2' ? 'y2' : 'y',
|
|
182
|
-
tooltip: s.noTooltip ? { enabled: false } : undefined,
|
|
183
293
|
};
|
|
184
294
|
}
|
|
185
295
|
/**
|
|
@@ -200,29 +310,6 @@ export class LyraChart extends LyraElement {
|
|
|
200
310
|
tooltipText: cs.getPropertyValue('--lyra-chart-tooltip-text').trim() || FALLBACK_TOOLTIP_TEXT,
|
|
201
311
|
};
|
|
202
312
|
}
|
|
203
|
-
/**
|
|
204
|
-
* A content-affecting-properties fingerprint used by `updated()` to skip a
|
|
205
|
-
* redundant `draw()` when neither visibility nor any of these properties
|
|
206
|
-
* actually changed since the last draw (e.g. an unrelated property/state
|
|
207
|
-
* update, or `requestUpdate()` with nothing changed). Mirrors
|
|
208
|
-
* `lite-chart.ts`'s `computeSignature()`.
|
|
209
|
-
*/
|
|
210
|
-
computeSignature() {
|
|
211
|
-
return JSON.stringify([
|
|
212
|
-
this.type,
|
|
213
|
-
this.labels,
|
|
214
|
-
this.datasets,
|
|
215
|
-
this.legend,
|
|
216
|
-
this.area,
|
|
217
|
-
this.xLabel,
|
|
218
|
-
this.yLabel,
|
|
219
|
-
this.y2Label,
|
|
220
|
-
this.beginAtZero,
|
|
221
|
-
this.horizontal,
|
|
222
|
-
this.stacked,
|
|
223
|
-
this.config,
|
|
224
|
-
]);
|
|
225
|
-
}
|
|
226
313
|
/**
|
|
227
314
|
* Builds `options.scales` for the effective chart type: no scale at all for
|
|
228
315
|
* pie/doughnut (a proportional-area chart has no axis), the single radial
|
|
@@ -235,10 +322,10 @@ export class LyraChart extends LyraElement {
|
|
|
235
322
|
* scale's `ticks.color`/`grid.color`/axis `title.color` so grid lines and
|
|
236
323
|
* labels retheme instead of sitting at Chart.js's own hardcoded defaults.
|
|
237
324
|
*/
|
|
238
|
-
buildScales(theme) {
|
|
239
|
-
if (
|
|
325
|
+
buildScales(effectiveType, theme) {
|
|
326
|
+
if (effectiveType === 'pie' || effectiveType === 'doughnut')
|
|
240
327
|
return {};
|
|
241
|
-
if (
|
|
328
|
+
if (effectiveType === 'radar' || effectiveType === 'polarArea') {
|
|
242
329
|
return {
|
|
243
330
|
r: {
|
|
244
331
|
beginAtZero: this.beginAtZero,
|
|
@@ -253,10 +340,10 @@ export class LyraChart extends LyraElement {
|
|
|
253
340
|
// `stacked` only applies to bar/line-family charts sharing a categorical
|
|
254
341
|
// axis, per the design spec — scatter/bubble's linear x scale and the
|
|
255
342
|
// radial r scale above are out of scope.
|
|
256
|
-
const stacked = this.stacked && (
|
|
343
|
+
const stacked = this.stacked && (effectiveType === 'bar' || effectiveType === 'line');
|
|
257
344
|
return {
|
|
258
345
|
x: {
|
|
259
|
-
type:
|
|
346
|
+
type: effectiveType === 'scatter' || effectiveType === 'bubble' ? 'linear' : 'category',
|
|
260
347
|
title: { display: !!this.xLabel, text: this.xLabel, color: theme.tick },
|
|
261
348
|
ticks: { color: theme.tick },
|
|
262
349
|
grid: { color: theme.grid },
|
|
@@ -308,10 +395,27 @@ export class LyraChart extends LyraElement {
|
|
|
308
395
|
const value = chart.data.datasets[datasetIndex]?.data?.[index] ?? null;
|
|
309
396
|
this.emit('lyra-point-click', { datasetIndex, index, label, value });
|
|
310
397
|
}
|
|
398
|
+
/**
|
|
399
|
+
* `config.type` (if set) overrides the attribute `type` post-merge — this
|
|
400
|
+
* is the one place that resolution logic lives, shared by `buildConfig()`
|
|
401
|
+
* (which needs it to build scales/interaction for the right type) and
|
|
402
|
+
* `willUpdate()` (which needs it to detect a type change against the last
|
|
403
|
+
* *actually built* type, `this.builtType`, before the render pass that
|
|
404
|
+
* would rebuild the `Chart` instance).
|
|
405
|
+
*/
|
|
406
|
+
effectiveType() {
|
|
407
|
+
return (this.config?.type ?? normalizeChartType(this.type));
|
|
408
|
+
}
|
|
311
409
|
buildConfig() {
|
|
312
410
|
const theme = this.themeColors();
|
|
411
|
+
// Resolve the effective type up front: `config.type` (if set) overrides
|
|
412
|
+
// the attribute `type` post-merge, so scales/interaction must be built
|
|
413
|
+
// for *that* type, not `this.type` — otherwise a config.type override
|
|
414
|
+
// (e.g. line -> radar) ships with the wrong axis shape (categorical x/y
|
|
415
|
+
// instead of a radial r scale).
|
|
416
|
+
const effectiveType = this.effectiveType();
|
|
313
417
|
const generated = {
|
|
314
|
-
type:
|
|
418
|
+
type: effectiveType,
|
|
315
419
|
data: {
|
|
316
420
|
labels: this.labels,
|
|
317
421
|
datasets: this.datasets.map((s) => this.seriesToDataset(s)),
|
|
@@ -329,7 +433,7 @@ export class LyraChart extends LyraElement {
|
|
|
329
433
|
// canvas-internal animation loop, so `prefersReducedMotion()` is
|
|
330
434
|
// checked here instead and fed into `options.animation`.
|
|
331
435
|
animation: prefersReducedMotion() ? false : undefined,
|
|
332
|
-
interaction: { intersect: false, mode:
|
|
436
|
+
interaction: { intersect: false, mode: effectiveType === 'scatter' ? 'nearest' : 'index' },
|
|
333
437
|
onClick: (event, _elements, chart) => this.handlePointClick(event, chart),
|
|
334
438
|
plugins: {
|
|
335
439
|
legend: { display: this.legend, labels: { color: theme.legend } },
|
|
@@ -337,6 +441,10 @@ export class LyraChart extends LyraElement {
|
|
|
337
441
|
backgroundColor: theme.tooltipBg,
|
|
338
442
|
titleColor: theme.tooltipText,
|
|
339
443
|
bodyColor: theme.tooltipText,
|
|
444
|
+
// Chart.js's tooltip plugin has no per-dataset `tooltip.enabled`
|
|
445
|
+
// — `Series.noTooltip` is implemented here instead, via the one
|
|
446
|
+
// mechanism the core tooltip plugin actually reads.
|
|
447
|
+
filter: (item) => !this.datasets[item.datasetIndex]?.noTooltip,
|
|
340
448
|
},
|
|
341
449
|
zoom: this.zoom
|
|
342
450
|
? {
|
|
@@ -357,7 +465,7 @@ export class LyraChart extends LyraElement {
|
|
|
357
465
|
}
|
|
358
466
|
: undefined,
|
|
359
467
|
},
|
|
360
|
-
scales: this.buildScales(theme),
|
|
468
|
+
scales: this.buildScales(effectiveType, theme),
|
|
361
469
|
},
|
|
362
470
|
};
|
|
363
471
|
if (!this.config)
|
|
@@ -408,6 +516,56 @@ export class LyraChart extends LyraElement {
|
|
|
408
516
|
refreshTheme() {
|
|
409
517
|
this.draw();
|
|
410
518
|
}
|
|
519
|
+
seriesValues(series) {
|
|
520
|
+
if (series.points)
|
|
521
|
+
return series.points.map((point) => point.y).filter((value) => Number.isFinite(value));
|
|
522
|
+
return (series.data ?? []).filter((value) => value != null && Number.isFinite(value));
|
|
523
|
+
}
|
|
524
|
+
chartDescription() {
|
|
525
|
+
if (this.accessibleDescription)
|
|
526
|
+
return this.accessibleDescription;
|
|
527
|
+
const summaries = this.datasets.map((series) => {
|
|
528
|
+
const values = this.seriesValues(series);
|
|
529
|
+
if (!values.length)
|
|
530
|
+
return `${series.label}: no data`;
|
|
531
|
+
const first = values[0];
|
|
532
|
+
const last = values[values.length - 1];
|
|
533
|
+
const trend = last > first ? 'increasing' : last < first ? 'decreasing' : 'flat';
|
|
534
|
+
let min = values[0];
|
|
535
|
+
let max = values[0];
|
|
536
|
+
for (const value of values) {
|
|
537
|
+
min = Math.min(min, value);
|
|
538
|
+
max = Math.max(max, value);
|
|
539
|
+
}
|
|
540
|
+
return `${series.label}: ${values.length} values, range ${min} to ${max}, ${trend} trend`;
|
|
541
|
+
});
|
|
542
|
+
return `${this.effectiveType()} chart${summaries.length ? `. ${summaries.join('. ')}` : ' with no data'}.`;
|
|
543
|
+
}
|
|
544
|
+
renderDataTable() {
|
|
545
|
+
const rowCount = Math.max(this.labels.length, ...this.datasets.map((series) => (series.points ? series.points.length : series.data?.length ?? 0)), 0);
|
|
546
|
+
return html `
|
|
547
|
+
<table class=${this.showDataTable ? nothing : 'sr-only'}>
|
|
548
|
+
<caption>${this.accessibleLabel || 'Chart data'}</caption>
|
|
549
|
+
<thead>
|
|
550
|
+
<tr>
|
|
551
|
+
<th scope="col">Category</th>
|
|
552
|
+
${this.datasets.map((series) => html `<th scope="col">${series.label}</th>`)}
|
|
553
|
+
</tr>
|
|
554
|
+
</thead>
|
|
555
|
+
<tbody>
|
|
556
|
+
${Array.from({ length: rowCount }, (_, index) => html `
|
|
557
|
+
<tr>
|
|
558
|
+
<th scope="row">${this.labels[index] ?? `Point ${index + 1}`}</th>
|
|
559
|
+
${this.datasets.map((series) => {
|
|
560
|
+
const value = series.points ? series.points[index]?.y : series.data?.[index];
|
|
561
|
+
return html `<td>${value == null || !Number.isFinite(value) ? 'No data' : value}</td>`;
|
|
562
|
+
})}
|
|
563
|
+
</tr>
|
|
564
|
+
`)}
|
|
565
|
+
</tbody>
|
|
566
|
+
</table>
|
|
567
|
+
`;
|
|
568
|
+
}
|
|
411
569
|
render() {
|
|
412
570
|
if (this.loading) {
|
|
413
571
|
return html `
|
|
@@ -416,10 +574,16 @@ export class LyraChart extends LyraElement {
|
|
|
416
574
|
</div>
|
|
417
575
|
`;
|
|
418
576
|
}
|
|
419
|
-
const label = this.datasets.map((d) => d.label).join(', ') || 'Chart';
|
|
577
|
+
const label = this.accessibleLabel || this.datasets.map((d) => d.label).join(', ') || 'Chart';
|
|
578
|
+
const description = this.chartDescription();
|
|
420
579
|
return html `
|
|
421
580
|
<div part="base">
|
|
422
|
-
<canvas part="canvas" role="img" aria-label=${label}></canvas>
|
|
581
|
+
<canvas part="canvas" role="img" aria-label=${label} aria-describedby=${this.descriptionId}></canvas>
|
|
582
|
+
<p part="description" id=${this.descriptionId} class="sr-only">${description}</p>
|
|
583
|
+
<div part="data-table">
|
|
584
|
+
<slot name="data-table"></slot>
|
|
585
|
+
${this.renderDataTable()}
|
|
586
|
+
</div>
|
|
423
587
|
${this.zoom && this.zoomed
|
|
424
588
|
? html `<button part="reset-zoom-button" type="button" @click=${() => this.resetZoom()}>
|
|
425
589
|
Reset zoom
|
|
@@ -430,7 +594,7 @@ export class LyraChart extends LyraElement {
|
|
|
430
594
|
}
|
|
431
595
|
}
|
|
432
596
|
__decorate([
|
|
433
|
-
property()
|
|
597
|
+
property({ converter: { fromAttribute: (value) => normalizeChartType(value) } })
|
|
434
598
|
], LyraChart.prototype, "type", void 0);
|
|
435
599
|
__decorate([
|
|
436
600
|
property({ attribute: false })
|
|
@@ -462,6 +626,15 @@ __decorate([
|
|
|
462
626
|
__decorate([
|
|
463
627
|
property({ type: Boolean, attribute: 'begin-at-zero' })
|
|
464
628
|
], LyraChart.prototype, "beginAtZero", void 0);
|
|
629
|
+
__decorate([
|
|
630
|
+
property({ attribute: 'accessible-label' })
|
|
631
|
+
], LyraChart.prototype, "accessibleLabel", void 0);
|
|
632
|
+
__decorate([
|
|
633
|
+
property({ attribute: 'accessible-description' })
|
|
634
|
+
], LyraChart.prototype, "accessibleDescription", void 0);
|
|
635
|
+
__decorate([
|
|
636
|
+
property({ type: Boolean, attribute: 'show-data-table' })
|
|
637
|
+
], LyraChart.prototype, "showDataTable", void 0);
|
|
465
638
|
__decorate([
|
|
466
639
|
property({ type: Boolean })
|
|
467
640
|
], LyraChart.prototype, "horizontal", void 0);
|
|
@@ -484,3 +657,28 @@ __decorate([
|
|
|
484
657
|
query('canvas')
|
|
485
658
|
], LyraChart.prototype, "canvasEl", void 0);
|
|
486
659
|
defineElement('chart', LyraChart);
|
|
660
|
+
/**
|
|
661
|
+
* Installs a read-only `type` accessor pair on a `LyraChart` subclass's
|
|
662
|
+
* prototype, locking it to `value` — assigning `.type` afterwards (attribute
|
|
663
|
+
* or property) is silently ignored. `LyraChart` declares `type` as a plain
|
|
664
|
+
* (decorator-managed) class field, and TypeScript forbids a subclass from
|
|
665
|
+
* re-declaring a base field as a getter/setter pair via ordinary class
|
|
666
|
+
* syntax (TS2611), so the accessor pair is installed directly on the
|
|
667
|
+
* prototype instead, which is runtime-equivalent (same shadowing semantics
|
|
668
|
+
* as a class-syntax override) without tripping that check. Shared by every
|
|
669
|
+
* `lyra-*-chart` subclass (bar/line/pie/doughnut/scatter/bubble/radar/
|
|
670
|
+
* polarArea) plus `lyra-histogram`, replacing what used to be an identical
|
|
671
|
+
* ~16-line `Object.defineProperty` block copy-pasted into each file.
|
|
672
|
+
*/
|
|
673
|
+
export function lockChartType(ctor, value) {
|
|
674
|
+
Object.defineProperty(ctor.prototype, 'type', {
|
|
675
|
+
configurable: true,
|
|
676
|
+
enumerable: true,
|
|
677
|
+
get() {
|
|
678
|
+
return value;
|
|
679
|
+
},
|
|
680
|
+
set(_v) {
|
|
681
|
+
/* locked to `value`; direct writes are ignored */
|
|
682
|
+
},
|
|
683
|
+
});
|
|
684
|
+
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { LyraChart } from './chart.js';
|
|
1
|
+
import { LyraChart, lockChartType } from './chart.js';
|
|
2
2
|
import { defineElement } from '../../internal/prefix.js';
|
|
3
3
|
/**
|
|
4
4
|
* `<lyra-doughnut-chart>` — `<lyra-chart>` with `type` locked to `"doughnut"`.
|
|
@@ -7,21 +7,5 @@ import { defineElement } from '../../internal/prefix.js';
|
|
|
7
7
|
*/
|
|
8
8
|
export class LyraDoughnutChart extends LyraChart {
|
|
9
9
|
}
|
|
10
|
-
|
|
11
|
-
// default value — `LyraChart` declares it as a plain (decorator-managed)
|
|
12
|
-
// class field, and TypeScript forbids a subclass from re-declaring a base
|
|
13
|
-
// field as a getter/setter pair via ordinary class syntax (TS2611) — so the
|
|
14
|
-
// accessor pair is installed directly on the prototype instead, which is
|
|
15
|
-
// runtime-equivalent (same shadowing semantics as a class-syntax override)
|
|
16
|
-
// without tripping that check.
|
|
17
|
-
Object.defineProperty(LyraDoughnutChart.prototype, 'type', {
|
|
18
|
-
configurable: true,
|
|
19
|
-
enumerable: true,
|
|
20
|
-
get() {
|
|
21
|
-
return 'doughnut';
|
|
22
|
-
},
|
|
23
|
-
set(_v) {
|
|
24
|
-
/* locked to 'doughnut'; direct writes are ignored */
|
|
25
|
-
},
|
|
26
|
-
});
|
|
10
|
+
lockChartType(LyraDoughnutChart, 'doughnut');
|
|
27
11
|
defineElement('doughnut-chart', LyraDoughnutChart);
|
|
@@ -2,5 +2,11 @@ export interface HistogramBucket {
|
|
|
2
2
|
label: string;
|
|
3
3
|
count: number;
|
|
4
4
|
}
|
|
5
|
-
|
|
5
|
+
export declare const MAX_HISTOGRAM_BINS = 1000;
|
|
6
|
+
/** Converts an untyped bucket count to a bounded, non-negative integer. */
|
|
7
|
+
export declare function normalizeHistogramBinCount(binCount: unknown): number;
|
|
8
|
+
/** Splits `values` into `binCount` equal-width buckets and counts membership.
|
|
9
|
+
* Non-finite `binCount` (or <= 0) yields no buckets; a fractional `binCount`
|
|
10
|
+
* is floored and an excessive count is capped; non-finite samples in
|
|
11
|
+
* `values` are dropped rather than corrupting bucket-index math. */
|
|
6
12
|
export declare function binValues(values: number[], binCount: number): HistogramBucket[];
|
|
@@ -1,29 +1,47 @@
|
|
|
1
|
-
|
|
1
|
+
export const MAX_HISTOGRAM_BINS = 1_000;
|
|
2
|
+
/** Converts an untyped bucket count to a bounded, non-negative integer. */
|
|
3
|
+
export function normalizeHistogramBinCount(binCount) {
|
|
4
|
+
const numeric = typeof binCount === 'number' ? binCount : Number(binCount);
|
|
5
|
+
if (!Number.isFinite(numeric))
|
|
6
|
+
return 0;
|
|
7
|
+
return Math.min(MAX_HISTOGRAM_BINS, Math.max(0, Math.floor(numeric)));
|
|
8
|
+
}
|
|
9
|
+
/** Splits `values` into `binCount` equal-width buckets and counts membership.
|
|
10
|
+
* Non-finite `binCount` (or <= 0) yields no buckets; a fractional `binCount`
|
|
11
|
+
* is floored and an excessive count is capped; non-finite samples in
|
|
12
|
+
* `values` are dropped rather than corrupting bucket-index math. */
|
|
2
13
|
export function binValues(values, binCount) {
|
|
3
|
-
|
|
14
|
+
const finite = values.filter((v) => Number.isFinite(v));
|
|
15
|
+
if (finite.length === 0)
|
|
16
|
+
return [];
|
|
17
|
+
const bins = normalizeHistogramBinCount(binCount);
|
|
18
|
+
if (bins <= 0)
|
|
4
19
|
return [];
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
// instead so an arbitrarily large sample never crashes.
|
|
9
|
-
let lo = values[0];
|
|
10
|
-
let hi = values[0];
|
|
11
|
-
for (const v of values) {
|
|
20
|
+
let lo = finite[0];
|
|
21
|
+
let hi = finite[0];
|
|
22
|
+
for (const v of finite) {
|
|
12
23
|
if (v < lo)
|
|
13
24
|
lo = v;
|
|
14
25
|
if (v > hi)
|
|
15
26
|
hi = v;
|
|
16
27
|
}
|
|
28
|
+
// Constant data (lo === hi) previously fell into the `v === hi` branch
|
|
29
|
+
// below, which places every value in the *last* bucket alone — misleading,
|
|
30
|
+
// since every other bucket reads 0 and the label implies a spread that
|
|
31
|
+
// isn't real. Spread it into the *first* bucket instead so a single-value
|
|
32
|
+
// dataset reads as "N items, one bucket populated" starting from the data's
|
|
33
|
+
// own value, not its synthetic +1 upper edge.
|
|
34
|
+
const constant = hi === lo;
|
|
17
35
|
const span = hi - lo || 1;
|
|
18
|
-
const width = span /
|
|
19
|
-
const buckets = Array.from({ length:
|
|
36
|
+
const width = span / bins;
|
|
37
|
+
const buckets = Array.from({ length: bins }, (_, i) => {
|
|
20
38
|
const bLo = lo + i * width;
|
|
21
39
|
const bHi = lo + (i + 1) * width;
|
|
22
40
|
return { label: `${bLo.toFixed(1)}–${bHi.toFixed(1)}`, count: 0 };
|
|
23
41
|
});
|
|
24
|
-
for (const v of
|
|
25
|
-
const index = v === hi ?
|
|
26
|
-
buckets[Math.min(
|
|
42
|
+
for (const v of finite) {
|
|
43
|
+
const index = constant ? 0 : v === hi ? bins - 1 : Math.floor((v - lo) / width);
|
|
44
|
+
buckets[Math.min(bins - 1, Math.max(0, index))].count++;
|
|
27
45
|
}
|
|
28
46
|
return buckets;
|
|
29
47
|
}
|
|
@@ -5,10 +5,10 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
|
|
|
5
5
|
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
6
|
};
|
|
7
7
|
import { property } from 'lit/decorators.js';
|
|
8
|
-
import { LyraChart } from './chart.js';
|
|
8
|
+
import { LyraChart, lockChartType } from './chart.js';
|
|
9
9
|
import { LyraElement } from '../../internal/lyra-element.js';
|
|
10
10
|
import { defineElement } from '../../internal/prefix.js';
|
|
11
|
-
import { binValues } from './histogram-bin.js';
|
|
11
|
+
import { binValues, normalizeHistogramBinCount, } from './histogram-bin.js';
|
|
12
12
|
import { styles } from './histogram.styles.js';
|
|
13
13
|
/**
|
|
14
14
|
* `<lyra-histogram>` — bins `values` into `bins` equal-width buckets and
|
|
@@ -32,7 +32,7 @@ export class LyraHistogram extends LyraChart {
|
|
|
32
32
|
static { this.styles = [LyraElement.styles, styles]; }
|
|
33
33
|
}
|
|
34
34
|
__decorate([
|
|
35
|
-
property({
|
|
35
|
+
property({ converter: { fromAttribute: (value) => normalizeHistogramBinCount(value) } })
|
|
36
36
|
], LyraHistogram.prototype, "bins", void 0);
|
|
37
37
|
__decorate([
|
|
38
38
|
property({ attribute: false })
|
|
@@ -48,12 +48,13 @@ __decorate([
|
|
|
48
48
|
// change doesn't re-run the O(n) bucketing loop from scratch on every access.
|
|
49
49
|
const bucketCache = new WeakMap();
|
|
50
50
|
export function binnedBuckets(el) {
|
|
51
|
+
const bins = normalizeHistogramBinCount(el.bins);
|
|
51
52
|
const cached = bucketCache.get(el);
|
|
52
|
-
if (cached && cached.values === el.values && cached.bins ===
|
|
53
|
+
if (cached && cached.values === el.values && cached.bins === bins) {
|
|
53
54
|
return cached.buckets;
|
|
54
55
|
}
|
|
55
|
-
const buckets = binValues(el.values,
|
|
56
|
-
bucketCache.set(el, { values: el.values, bins
|
|
56
|
+
const buckets = binValues(el.values, bins);
|
|
57
|
+
bucketCache.set(el, { values: el.values, bins, buckets });
|
|
57
58
|
return buckets;
|
|
58
59
|
}
|
|
59
60
|
// `labels`/`datasets` are computed from `values`/`bins` rather than settable
|
|
@@ -87,14 +88,5 @@ Object.defineProperty(LyraHistogram.prototype, 'datasets', {
|
|
|
87
88
|
// just a default value, not an enforced lock, so without this a `type="line"`
|
|
88
89
|
// attribute (or `el.type = 'line'`) would silently turn a histogram into a
|
|
89
90
|
// line chart of its own bucket counts.
|
|
90
|
-
|
|
91
|
-
configurable: true,
|
|
92
|
-
enumerable: true,
|
|
93
|
-
get() {
|
|
94
|
-
return 'bar';
|
|
95
|
-
},
|
|
96
|
-
set(_v) {
|
|
97
|
-
/* locked to 'bar'; direct writes are ignored */
|
|
98
|
-
},
|
|
99
|
-
});
|
|
91
|
+
lockChartType(LyraHistogram, 'bar');
|
|
100
92
|
defineElement('histogram', LyraHistogram);
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { LyraChart } from './chart.js';
|
|
1
|
+
import { LyraChart, lockChartType } from './chart.js';
|
|
2
2
|
import { defineElement } from '../../internal/prefix.js';
|
|
3
3
|
/**
|
|
4
4
|
* `<lyra-line-chart>` — `<lyra-chart>` with `type` locked to `"line"`.
|
|
@@ -7,21 +7,5 @@ import { defineElement } from '../../internal/prefix.js';
|
|
|
7
7
|
*/
|
|
8
8
|
export class LyraLineChart extends LyraChart {
|
|
9
9
|
}
|
|
10
|
-
|
|
11
|
-
// default value — `LyraChart` declares it as a plain (decorator-managed)
|
|
12
|
-
// class field, and TypeScript forbids a subclass from re-declaring a base
|
|
13
|
-
// field as a getter/setter pair via ordinary class syntax (TS2611) — so the
|
|
14
|
-
// accessor pair is installed directly on the prototype instead, which is
|
|
15
|
-
// runtime-equivalent (same shadowing semantics as a class-syntax override)
|
|
16
|
-
// without tripping that check.
|
|
17
|
-
Object.defineProperty(LyraLineChart.prototype, 'type', {
|
|
18
|
-
configurable: true,
|
|
19
|
-
enumerable: true,
|
|
20
|
-
get() {
|
|
21
|
-
return 'line';
|
|
22
|
-
},
|
|
23
|
-
set(_v) {
|
|
24
|
-
/* locked to 'line'; direct writes are ignored */
|
|
25
|
-
},
|
|
26
|
-
});
|
|
10
|
+
lockChartType(LyraLineChart, 'line');
|
|
27
11
|
defineElement('line-chart', LyraLineChart);
|