@k2b/ui 0.51.0 → 0.52.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/dist/base.css +3 -0
- package/dist/browser/actions/Toolbar.js +8 -2
- package/dist/browser/actions/Toolbar.js.map +1 -1
- package/dist/browser/charts/core/bar-labels.js +5 -0
- package/dist/browser/charts/core/bar-labels.js.map +1 -0
- package/dist/browser/charts/core/bubble.js +166 -0
- package/dist/browser/charts/core/bubble.js.map +1 -0
- package/dist/browser/charts/core/default-styles.js +83 -0
- package/dist/browser/charts/core/default-styles.js.map +1 -0
- package/dist/browser/charts/core/funnel-layout.js +79 -0
- package/dist/browser/charts/core/funnel-layout.js.map +1 -0
- package/dist/browser/charts/core/funnel.js +27 -0
- package/dist/browser/charts/core/funnel.js.map +1 -0
- package/dist/browser/charts/core/index.js +6 -1
- package/dist/browser/charts/core/index.js.map +1 -1
- package/dist/browser/charts/core/pareto.js +120 -0
- package/dist/browser/charts/core/pareto.js.map +1 -0
- package/dist/browser/charts/core/radar.js +101 -0
- package/dist/browser/charts/core/radar.js.map +1 -0
- package/dist/browser/charts/core/registry.js +11 -1
- package/dist/browser/charts/core/registry.js.map +1 -1
- package/dist/browser/charts/core/render-size.js +3 -1
- package/dist/browser/charts/core/render-size.js.map +1 -1
- package/dist/browser/charts/core/render.js +19 -0
- package/dist/browser/charts/core/render.js.map +1 -1
- package/dist/browser/charts/core/snapshot.js +1 -1
- package/dist/browser/charts/core/snapshot.js.map +1 -1
- package/dist/browser/charts/core/svg-barGauge.js +67 -0
- package/dist/browser/charts/core/svg-barGauge.js.map +1 -0
- package/dist/browser/charts/core/svg-boxplot.js +127 -0
- package/dist/browser/charts/core/svg-boxplot.js.map +1 -0
- package/dist/browser/charts/core/svg-common.js +1065 -0
- package/dist/browser/charts/core/svg-common.js.map +1 -0
- package/dist/browser/charts/core/svg-gauge.js +185 -0
- package/dist/browser/charts/core/svg-gauge.js.map +1 -0
- package/dist/browser/charts/core/svg-heatmap.js +80 -0
- package/dist/browser/charts/core/svg-heatmap.js.map +1 -0
- package/dist/browser/charts/core/svg-histogram.js +73 -0
- package/dist/browser/charts/core/svg-histogram.js.map +1 -0
- package/dist/browser/charts/core/svg-renderers.js +9 -1777
- package/dist/browser/charts/core/svg-renderers.js.map +1 -1
- package/dist/browser/charts/core/svg-scatter.js +114 -0
- package/dist/browser/charts/core/svg-scatter.js.map +1 -0
- package/dist/browser/charts/core/treemap.js +138 -0
- package/dist/browser/charts/core/treemap.js.map +1 -0
- package/dist/browser/charts/description.js.map +1 -1
- package/dist/browser/content/ChartRoot.js +21 -7
- package/dist/browser/content/ChartRoot.js.map +1 -1
- package/dist/browser/content/ChartSnapshotView.js +4 -1
- package/dist/browser/content/ChartSnapshotView.js.map +1 -1
- package/dist/browser/content/DataTable.js +186 -193
- package/dist/browser/content/DataTable.js.map +1 -1
- package/dist/browser/content/Lightbox.js +55 -23
- package/dist/browser/content/Lightbox.js.map +1 -1
- package/dist/browser/content/ThumbnailStrip.js +174 -0
- package/dist/browser/content/ThumbnailStrip.js.map +1 -0
- package/dist/browser/content/chart-bar.js +98 -0
- package/dist/browser/content/chart-bar.js.map +1 -1
- package/dist/browser/content/chart-inspection-core.js +28 -8
- package/dist/browser/content/chart-inspection-core.js.map +1 -1
- package/dist/browser/content/chart-message-catalog.js +18 -0
- package/dist/browser/content/chart-message-catalog.js.map +1 -1
- package/dist/browser/content/index.js +1 -0
- package/dist/browser/content/index.js.map +1 -1
- package/dist/browser/content/thumbnail-strip-messages.js +24 -0
- package/dist/browser/content/thumbnail-strip-messages.js.map +1 -0
- package/dist/browser/inputs/ChoiceInputs.js +132 -101
- package/dist/browser/inputs/ChoiceInputs.js.map +1 -1
- package/dist/browser/inputs/index.js +1 -0
- package/dist/browser/inputs/index.js.map +1 -1
- package/dist/browser/inputs/markdown/MarkdownSelectionToolbar.js +330 -0
- package/dist/browser/inputs/markdown/MarkdownSelectionToolbar.js.map +1 -0
- package/dist/browser/internal/field.js +96 -77
- package/dist/browser/internal/field.js.map +1 -1
- package/dist/browser/layout/AppWorkspace.js +7 -5
- package/dist/browser/layout/AppWorkspace.js.map +1 -1
- package/dist/browser/layout/PanelDialog.js +92 -68
- package/dist/browser/layout/PanelDialog.js.map +1 -1
- package/dist/browser/surfaces/StatCell.js +82 -70
- package/dist/browser/surfaces/StatCell.js.map +1 -1
- package/dist/browser/surfaces/stat-cell-messages.js +4 -2
- package/dist/browser/surfaces/stat-cell-messages.js.map +1 -1
- package/dist/browser/widgets/DashboardFrame.js +93 -88
- package/dist/browser/widgets/DashboardFrame.js.map +1 -1
- package/dist/ssr/actions/Toolbar.js +8 -2
- package/dist/ssr/actions/Toolbar.js.map +1 -1
- package/dist/ssr/charts/core/bar-labels.js +5 -0
- package/dist/ssr/charts/core/bar-labels.js.map +1 -0
- package/dist/ssr/charts/core/bubble.js +166 -0
- package/dist/ssr/charts/core/bubble.js.map +1 -0
- package/dist/ssr/charts/core/default-styles.js +83 -0
- package/dist/ssr/charts/core/default-styles.js.map +1 -0
- package/dist/ssr/charts/core/funnel-layout.js +79 -0
- package/dist/ssr/charts/core/funnel-layout.js.map +1 -0
- package/dist/ssr/charts/core/funnel.js +27 -0
- package/dist/ssr/charts/core/funnel.js.map +1 -0
- package/dist/ssr/charts/core/index.js +6 -1
- package/dist/ssr/charts/core/index.js.map +1 -1
- package/dist/ssr/charts/core/pareto.js +120 -0
- package/dist/ssr/charts/core/pareto.js.map +1 -0
- package/dist/ssr/charts/core/radar.js +101 -0
- package/dist/ssr/charts/core/radar.js.map +1 -0
- package/dist/ssr/charts/core/registry.js +11 -1
- package/dist/ssr/charts/core/registry.js.map +1 -1
- package/dist/ssr/charts/core/render-size.js +3 -1
- package/dist/ssr/charts/core/render-size.js.map +1 -1
- package/dist/ssr/charts/core/render.js +19 -0
- package/dist/ssr/charts/core/render.js.map +1 -1
- package/dist/ssr/charts/core/snapshot.js +1 -1
- package/dist/ssr/charts/core/snapshot.js.map +1 -1
- package/dist/ssr/charts/core/svg-barGauge.js +67 -0
- package/dist/ssr/charts/core/svg-barGauge.js.map +1 -0
- package/dist/ssr/charts/core/svg-boxplot.js +127 -0
- package/dist/ssr/charts/core/svg-boxplot.js.map +1 -0
- package/dist/ssr/charts/core/svg-common.js +1065 -0
- package/dist/ssr/charts/core/svg-common.js.map +1 -0
- package/dist/ssr/charts/core/svg-gauge.js +185 -0
- package/dist/ssr/charts/core/svg-gauge.js.map +1 -0
- package/dist/ssr/charts/core/svg-heatmap.js +80 -0
- package/dist/ssr/charts/core/svg-heatmap.js.map +1 -0
- package/dist/ssr/charts/core/svg-histogram.js +73 -0
- package/dist/ssr/charts/core/svg-histogram.js.map +1 -0
- package/dist/ssr/charts/core/svg-renderers.js +9 -1777
- package/dist/ssr/charts/core/svg-renderers.js.map +1 -1
- package/dist/ssr/charts/core/svg-scatter.js +114 -0
- package/dist/ssr/charts/core/svg-scatter.js.map +1 -0
- package/dist/ssr/charts/core/treemap.js +138 -0
- package/dist/ssr/charts/core/treemap.js.map +1 -0
- package/dist/ssr/charts/description.js.map +1 -1
- package/dist/ssr/content/ChartRoot.js +21 -7
- package/dist/ssr/content/ChartRoot.js.map +1 -1
- package/dist/ssr/content/ChartSnapshotView.js +1 -0
- package/dist/ssr/content/ChartSnapshotView.js.map +1 -1
- package/dist/ssr/content/DataTable.js +12 -16
- package/dist/ssr/content/DataTable.js.map +1 -1
- package/dist/ssr/content/Lightbox.js +32 -3
- package/dist/ssr/content/Lightbox.js.map +1 -1
- package/dist/ssr/content/ThumbnailStrip.js +103 -0
- package/dist/ssr/content/ThumbnailStrip.js.map +1 -0
- package/dist/ssr/content/chart-bar.js +98 -0
- package/dist/ssr/content/chart-bar.js.map +1 -1
- package/dist/ssr/content/chart-inspection-core.js +28 -8
- package/dist/ssr/content/chart-inspection-core.js.map +1 -1
- package/dist/ssr/content/chart-message-catalog.js +18 -0
- package/dist/ssr/content/chart-message-catalog.js.map +1 -1
- package/dist/ssr/content/index.js +1 -0
- package/dist/ssr/content/index.js.map +1 -1
- package/dist/ssr/content/thumbnail-strip-messages.js +24 -0
- package/dist/ssr/content/thumbnail-strip-messages.js.map +1 -0
- package/dist/ssr/inputs/ChoiceInputs.js +55 -40
- package/dist/ssr/inputs/ChoiceInputs.js.map +1 -1
- package/dist/ssr/inputs/index.js +1 -0
- package/dist/ssr/inputs/index.js.map +1 -1
- package/dist/ssr/inputs/markdown/MarkdownSelectionToolbar.js +293 -0
- package/dist/ssr/inputs/markdown/MarkdownSelectionToolbar.js.map +1 -0
- package/dist/ssr/internal/field.js +36 -24
- package/dist/ssr/internal/field.js.map +1 -1
- package/dist/ssr/layout/AppWorkspace.js +5 -1
- package/dist/ssr/layout/AppWorkspace.js.map +1 -1
- package/dist/ssr/layout/PanelDialog.js +40 -26
- package/dist/ssr/layout/PanelDialog.js.map +1 -1
- package/dist/ssr/surfaces/StatCell.js +29 -18
- package/dist/ssr/surfaces/StatCell.js.map +1 -1
- package/dist/ssr/surfaces/stat-cell-messages.js +4 -2
- package/dist/ssr/surfaces/stat-cell-messages.js.map +1 -1
- package/dist/ssr/widgets/DashboardFrame.js +6 -11
- package/dist/ssr/widgets/DashboardFrame.js.map +1 -1
- package/dist/styles.css +1 -1
- package/dist/types/actions/Toolbar.d.ts +2 -0
- package/dist/types/charts/core/bar-labels.d.ts +1 -0
- package/dist/types/charts/core/bubble.d.ts +66 -0
- package/dist/types/charts/core/default-styles.d.ts +1 -0
- package/dist/types/charts/core/funnel-layout.d.ts +43 -0
- package/dist/types/charts/core/funnel.d.ts +13 -0
- package/dist/types/charts/core/index.d.ts +6 -1
- package/dist/types/charts/core/pareto.d.ts +40 -0
- package/dist/types/charts/core/radar.d.ts +47 -0
- package/dist/types/charts/core/registry.d.ts +10 -0
- package/dist/types/charts/core/render-size.d.ts +1 -1
- package/dist/types/charts/core/svg-barGauge.d.ts +3 -0
- package/dist/types/charts/core/svg-boxplot.d.ts +18 -0
- package/dist/types/charts/core/svg-common.d.ts +612 -0
- package/dist/types/charts/core/svg-gauge.d.ts +6 -0
- package/dist/types/charts/core/svg-heatmap.d.ts +6 -0
- package/dist/types/charts/core/svg-histogram.d.ts +16 -0
- package/dist/types/charts/core/svg-renderers.d.ts +8 -612
- package/dist/types/charts/core/svg-scatter.d.ts +23 -0
- package/dist/types/charts/core/treemap.d.ts +45 -0
- package/dist/types/charts/description.d.ts +63 -0
- package/dist/types/content/ChartRoot.d.ts +1 -1
- package/dist/types/content/Lightbox.d.ts +2 -0
- package/dist/types/content/ThumbnailStrip.d.ts +29 -0
- package/dist/types/content/chart-bar.d.ts +38 -2
- package/dist/types/content/chart-inspection-core.d.ts +7 -0
- package/dist/types/content/chart-inspection.d.ts +1 -0
- package/dist/types/content/chart-message-catalog.d.ts +8 -0
- package/dist/types/content/index.d.ts +1 -0
- package/dist/types/content/thumbnail-strip-messages.d.ts +10 -0
- package/dist/types/inputs/ChoiceInputs.d.ts +2 -0
- package/dist/types/inputs/index.d.ts +2 -0
- package/dist/types/inputs/markdown/MarkdownSelectionToolbar.d.ts +19 -0
- package/dist/types/internal/field.d.ts +2 -0
- package/dist/types/layout/PanelDialog.d.ts +5 -0
- package/dist/types/surfaces/stat-cell-messages.d.ts +1 -0
- package/dist/types/widgets/DashboardFrame.d.ts +4 -1
- package/package.json +2 -2
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
import { memo as _$memo } from "solid-js/web";
|
|
2
|
-
import { ssr as _$ssr } from "solid-js/web";
|
|
3
1
|
import { createComponent as _$createComponent } from "solid-js/web";
|
|
2
|
+
import { ssr as _$ssr } from "solid-js/web";
|
|
3
|
+
import { memo as _$memo } from "solid-js/web";
|
|
4
4
|
import { ssrAttribute as _$ssrAttribute } from "solid-js/web";
|
|
5
5
|
import { escape as _$escape } from "solid-js/web";
|
|
6
|
-
var _tmpl$ = ["<
|
|
7
|
-
_tmpl$2 = ["<
|
|
8
|
-
_tmpl$3 = ["<
|
|
9
|
-
_tmpl$4 = ["<
|
|
10
|
-
_tmpl$5 = ["<
|
|
6
|
+
var _tmpl$ = ["<span class=\"k2b-panel-dialog__icon k2b-icon-tile\"", " aria-hidden=\"true\"><i", "></i></span>"],
|
|
7
|
+
_tmpl$2 = ["<p>", "</p>"],
|
|
8
|
+
_tmpl$3 = ["<div class=\"", "\">", "</div>"],
|
|
9
|
+
_tmpl$4 = ["<button type=\"button\" class=\"", "\"", "", "><i class=\"ti ti-x\" aria-hidden=\"true\"></i></button>"],
|
|
10
|
+
_tmpl$5 = ["<header class=\"k2b-panel-dialog__header\"", ">", "<div class=\"", "\">", "<h2", ">", "</h2>", "</div>", "", "</header>"],
|
|
11
11
|
_tmpl$6 = ["<span class=\"k2b-sr-only\" data-dialog-tone-label>", "</span>"],
|
|
12
12
|
_tmpl$7 = ["<div class=\"k2b-panel-dialog__body\"", ">", "</div>"],
|
|
13
13
|
_tmpl$8 = ["<footer class=\"k2b-panel-dialog__footer\"", ">", "</footer>"],
|
|
@@ -16,11 +16,12 @@ var _tmpl$ = ["<p>", "</p>"],
|
|
|
16
16
|
_tmpl$1 = "<i class=\"ti ti-eye\" aria-hidden=\"true\"></i>",
|
|
17
17
|
_tmpl$10 = ["<div", ">", "</div>"],
|
|
18
18
|
_tmpl$11 = ["<p class=\"k2b-panel-dialog__section-subtitle\">", "</p>"],
|
|
19
|
-
_tmpl$12 = "<
|
|
20
|
-
_tmpl$13 =
|
|
21
|
-
_tmpl$14 = ["<
|
|
22
|
-
_tmpl$15 = ["<
|
|
23
|
-
_tmpl$16 = ["<
|
|
19
|
+
_tmpl$12 = ["<div class=\"k2b-panel-dialog__actions\">", "</div>"],
|
|
20
|
+
_tmpl$13 = "<i class=\"ti ti-eye-off\" aria-hidden=\"true\"></i>",
|
|
21
|
+
_tmpl$14 = ["<section class=\"k2b-panel-dialog__section\"", ">", "<header", ">", "<div><h3", ">", "</h3>", "</div>", "", "</header><div id=\"", "\" class=\"k2b-panel-dialog__section-body\"", ">", "</div></section>"],
|
|
22
|
+
_tmpl$15 = ["<i", " aria-hidden=\"true\"></i>"],
|
|
23
|
+
_tmpl$16 = ["<span class=\"k2b-panel-dialog__section-icon\"><i", " aria-hidden=\"true\"></i></span>"],
|
|
24
|
+
_tmpl$17 = ["<div class=\"k2b-panel-dialog\"", ">", "</div>"];
|
|
24
25
|
import { createContext, createEffect, createSignal, createUniqueId, Show, useContext } from "solid-js";
|
|
25
26
|
import { Button } from "../actions/Button";
|
|
26
27
|
import { Tabs } from "../actions/Tabs";
|
|
@@ -33,6 +34,7 @@ import { createScrollFade } from "./scroll-fade";
|
|
|
33
34
|
const PanelDialogSurfaceContext = createContext("contained");
|
|
34
35
|
const usePanelDialogSurface = () => useContext(PanelDialogSurfaceContext);
|
|
35
36
|
const PanelDialogToneContext = createContext(() => undefined);
|
|
37
|
+
const PanelDialogMediaContext = createContext(false);
|
|
36
38
|
const panelDialogBasePanelClass = "k2b-dialog k2b-panel-dialog-frame";
|
|
37
39
|
export const panelDialogPanelClass = `${panelDialogBasePanelClass} is-standard`;
|
|
38
40
|
export const panelDialogOptions = {
|
|
@@ -70,36 +72,41 @@ const PanelDialogHeader = props => {
|
|
|
70
72
|
const value = tone();
|
|
71
73
|
return value ? dialogToneIcon(value) : props.icon;
|
|
72
74
|
};
|
|
73
|
-
|
|
75
|
+
// Over a picture the header's parts are glass layers of their own; the dialog owns them, so it sets the surface.
|
|
76
|
+
const media = useContext(PanelDialogMediaContext);
|
|
77
|
+
const layer = media ? " k2b-overlay-surface" : "";
|
|
78
|
+
return _$ssr(_tmpl$5, _$ssrAttribute("data-surface", _$escape(usePanelDialogSurface(), true), false) + _$ssrAttribute("data-has-subtitle", _$escape(Boolean(props.subtitle), true), false), _$escape(_$createComponent(Show, {
|
|
74
79
|
get when() {
|
|
75
|
-
return icon();
|
|
80
|
+
return icon() && !media;
|
|
76
81
|
},
|
|
77
|
-
children
|
|
78
|
-
|
|
82
|
+
get children() {
|
|
83
|
+
return _$ssr(_tmpl$, _$ssrAttribute("data-tone", _$escape(tone(), true), false), _$ssrAttribute("class", _$escape(icon(), true), false));
|
|
84
|
+
}
|
|
85
|
+
})), `k2b-panel-dialog__heading${_$escape(layer, true)}`, _$escape(_$createComponent(Show, {
|
|
79
86
|
get when() {
|
|
80
87
|
return tone();
|
|
81
88
|
},
|
|
82
89
|
children: value => _$ssr(_tmpl$6, _$escape(dialogToneLabel(messages(), value())))
|
|
83
|
-
})), _$escape(props.title), _$escape(_$createComponent(Show, {
|
|
90
|
+
})), _$ssrAttribute("class", media ? "k2b-truncate-fade" : _$escape(undefined, true), false), _$escape(props.title), _$escape(_$createComponent(Show, {
|
|
84
91
|
get when() {
|
|
85
92
|
return props.subtitle;
|
|
86
93
|
},
|
|
87
94
|
get children() {
|
|
88
|
-
return _$ssr(_tmpl
|
|
95
|
+
return _$ssr(_tmpl$2, _$escape(props.subtitle));
|
|
89
96
|
}
|
|
90
97
|
})), _$escape(_$createComponent(Show, {
|
|
91
98
|
get when() {
|
|
92
99
|
return props.actions;
|
|
93
100
|
},
|
|
94
101
|
get children() {
|
|
95
|
-
return _$ssr(_tmpl$
|
|
102
|
+
return _$ssr(_tmpl$3, `k2b-panel-dialog__actions${_$escape(layer, true)}`, _$escape(props.actions));
|
|
96
103
|
}
|
|
97
104
|
})), _$escape(_$createComponent(Show, {
|
|
98
105
|
get when() {
|
|
99
106
|
return props.close;
|
|
100
107
|
},
|
|
101
108
|
get children() {
|
|
102
|
-
return _$ssr(_tmpl$
|
|
109
|
+
return _$ssr(_tmpl$4, `k2b-dialog__close${_$escape(layer, true)}`, _$ssrAttribute("aria-label", _$escape(props.closeLabel ?? messages().closeDialog, true), false), _$ssrAttribute("disabled", props.closeDisabled, true));
|
|
103
110
|
}
|
|
104
111
|
})));
|
|
105
112
|
};
|
|
@@ -131,7 +138,7 @@ const PanelDialogSection = props => {
|
|
|
131
138
|
if (!expanded && active && active !== expand && section?.contains(active)) expand?.focus();
|
|
132
139
|
});
|
|
133
140
|
});
|
|
134
|
-
return _$ssr(_tmpl$
|
|
141
|
+
return _$ssr(_tmpl$14, _$ssrAttribute("data-surface", _$escape(usePanelDialogSurface(), true), false) + _$ssrAttribute("data-hideable", _$escape(props.hideable || undefined, true), false) + _$ssrAttribute("data-open", props.hideable ? _$escape(open(), true) : _$escape(undefined, true), false) + _$ssrAttribute("aria-labelledby", open() ? _$escape(id, true) : `${_$escape(id, true)}-closed`, false), _$escape(_$createComponent(Show, {
|
|
135
142
|
get when() {
|
|
136
143
|
return props.hideable;
|
|
137
144
|
},
|
|
@@ -150,7 +157,7 @@ const PanelDialogSection = props => {
|
|
|
150
157
|
get when() {
|
|
151
158
|
return props.icon;
|
|
152
159
|
},
|
|
153
|
-
children: icon => _$ssr(_tmpl$
|
|
160
|
+
children: icon => _$ssr(_tmpl$15, _$ssrAttribute("class", _$escape(icon(), true), false))
|
|
154
161
|
}), _$ssr(_tmpl$0, `${_$escape(id, true)}-closed`, _$escape(props.title), _$escape(_$createComponent(Show, {
|
|
155
162
|
get when() {
|
|
156
163
|
return props.subtitle;
|
|
@@ -166,7 +173,7 @@ const PanelDialogSection = props => {
|
|
|
166
173
|
get when() {
|
|
167
174
|
return props.icon;
|
|
168
175
|
},
|
|
169
|
-
children: icon => _$ssr(_tmpl$
|
|
176
|
+
children: icon => _$ssr(_tmpl$16, _$ssrAttribute("class", _$escape(icon(), true), false))
|
|
170
177
|
})), _$ssrAttribute("id", _$escape(id, true), false), _$escape(props.title), _$escape(_$createComponent(Show, {
|
|
171
178
|
get when() {
|
|
172
179
|
return props.subtitle;
|
|
@@ -179,7 +186,7 @@ const PanelDialogSection = props => {
|
|
|
179
186
|
return props.actions;
|
|
180
187
|
},
|
|
181
188
|
get children() {
|
|
182
|
-
return _$ssr(_tmpl$
|
|
189
|
+
return _$ssr(_tmpl$12, _$escape(props.actions));
|
|
183
190
|
}
|
|
184
191
|
})), _$escape(_$createComponent(Show, {
|
|
185
192
|
get when() {
|
|
@@ -198,7 +205,7 @@ const PanelDialogSection = props => {
|
|
|
198
205
|
"aria-controls": `${id}-body`,
|
|
199
206
|
onClick: () => toggle(false),
|
|
200
207
|
get children() {
|
|
201
|
-
return _$ssr(_tmpl$
|
|
208
|
+
return _$ssr(_tmpl$13);
|
|
202
209
|
}
|
|
203
210
|
});
|
|
204
211
|
}
|
|
@@ -230,7 +237,14 @@ const PanelDialog = props => {
|
|
|
230
237
|
return _$createComponent(PanelDialogToneContext.Provider, {
|
|
231
238
|
value: () => props.tone,
|
|
232
239
|
get children() {
|
|
233
|
-
return _$
|
|
240
|
+
return _$createComponent(PanelDialogMediaContext.Provider, {
|
|
241
|
+
get value() {
|
|
242
|
+
return Boolean(props.media);
|
|
243
|
+
},
|
|
244
|
+
get children() {
|
|
245
|
+
return _$ssr(_tmpl$17, _$ssrAttribute("data-surface", _$escape(surface, true), false) + _$ssrAttribute("data-tone", _$escape(props.tone, true), false) + _$ssrAttribute("data-media", props.media ? "" : _$escape(undefined, true), false), _$escape(props.children));
|
|
246
|
+
}
|
|
247
|
+
});
|
|
234
248
|
}
|
|
235
249
|
});
|
|
236
250
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["layout/PanelDialog.tsx"],"sourcesContent":["import { createContext, createEffect, createSignal, createUniqueId, type JSX, Show, useContext } from \"solid-js\";\nimport { Button } from \"../actions/Button\";\nimport { Tabs } from \"../actions/Tabs\";\nimport type { OpenDialogOptions } from \"../feedback/dialog-core\";\nimport { type DialogTone, dialogToneIcon, dialogToneLabel } from \"../feedback/dialog-tone\";\nimport { sharedPrompts } from \"../feedback/prompt-confirm\";\nimport { resolvePromptMessages } from \"../feedback/prompt-messages\";\nimport { useUiMessages } from \"../intl/messages\";\nimport { usePanelDialogMessages } from \"./panel-dialog-messages\";\nimport { createScrollFade } from \"./scroll-fade\";\n\nexport type PanelDialogSurface = \"contained\" | \"floating\";\n\nexport type PanelDialogProps = {\n children: JSX.Element;\n surface?: PanelDialogSurface;\n /** A 2 px edge in the tone's colour inside the dialog frame; the header shows the tone's icon instead of its own. */\n tone?: DialogTone;\n};\n\nexport type PanelDialogHeaderProps = {\n title: JSX.Element;\n subtitle?: JSX.Element;\n icon?: string;\n actions?: JSX.Element;\n close?: () => void;\n closeDisabled?: boolean;\n closeLabel?: string;\n};\n\nexport type PanelDialogBodyProps = {\n children: JSX.Element;\n scrollPreserveKey?: string;\n scrollFade?: boolean;\n};\n\nexport type PanelDialogFooterProps = {\n children: JSX.Element;\n};\n\nexport type PanelDialogSectionProps = {\n title: JSX.Element;\n subtitle?: JSX.Element;\n icon?: string;\n actions?: JSX.Element;\n children: JSX.Element;\n} & (\n | { hideable?: false; open?: never; defaultOpen?: never; onOpenChange?: never; disabled?: never }\n | { hideable: true; open?: boolean; defaultOpen?: boolean; onOpenChange?: (open: boolean) => void; disabled?: boolean }\n);\n\nexport type PanelDialogTabOption<T extends string = string> = {\n value: T;\n label: JSX.Element;\n icon?: string;\n disabled?: boolean;\n};\n\nexport type PanelDialogTabsProps<T extends string = string> = {\n options: readonly PanelDialogTabOption<T>[];\n value: T | (() => T);\n onValueChange: (value: T) => void;\n ariaLabel?: string;\n label?: string;\n};\n\ntype PanelDialogComponent = ((props: PanelDialogProps) => JSX.Element) & {\n Header: (props: PanelDialogHeaderProps) => JSX.Element;\n Body: (props: PanelDialogBodyProps) => JSX.Element;\n Footer: (props: PanelDialogFooterProps) => JSX.Element;\n Section: (props: PanelDialogSectionProps) => JSX.Element;\n Tabs: <T extends string>(props: PanelDialogTabsProps<T>) => JSX.Element;\n};\n\nconst PanelDialogSurfaceContext = createContext<PanelDialogSurface>(\"contained\");\nconst usePanelDialogSurface = () => useContext(PanelDialogSurfaceContext);\nconst PanelDialogToneContext = createContext<() => DialogTone | undefined>(() => undefined);\n\nconst panelDialogBasePanelClass = \"k2b-dialog k2b-panel-dialog-frame\";\n\nexport const panelDialogPanelClass = `${panelDialogBasePanelClass} is-standard`;\nexport const panelDialogOptions = {\n panelClassName: panelDialogPanelClass,\n contentClassName: \"k2b-panel-dialog-viewport\",\n} satisfies OpenDialogOptions;\n\nexport const panelDialogWidePanelClass = `${panelDialogBasePanelClass} is-wide`;\nexport const panelDialogWideOptions = {\n panelClassName: panelDialogWidePanelClass,\n contentClassName: \"k2b-panel-dialog-viewport\",\n} satisfies OpenDialogOptions;\n\nexport const panelDialogFixedPanelClass = `${panelDialogBasePanelClass} is-fixed`;\nexport const panelDialogFixedOptions = {\n panelClassName: panelDialogFixedPanelClass,\n contentClassName: \"k2b-panel-dialog-viewport is-fixed\",\n} satisfies OpenDialogOptions;\n\nexport const panelDialogWorkspacePanelClass = `${panelDialogBasePanelClass} is-workspace`;\nexport const panelDialogWorkspaceOptions = {\n panelClassName: panelDialogWorkspacePanelClass,\n contentClassName: \"k2b-panel-dialog-viewport is-workspace\",\n} satisfies OpenDialogOptions;\n\nexport const confirmDiscardIfDirty = async (dirty: boolean | (() => boolean)): Promise<boolean> => {\n const hasChanges = typeof dirty === \"function\" ? dirty() : dirty;\n if (!hasChanges) return true;\n return Boolean(\n await sharedPrompts.confirm(resolvePromptMessages().discardUnsavedChanges, {\n title: resolvePromptMessages().unsavedChangesTitle,\n variant: \"danger\",\n confirmText: resolvePromptMessages().discard,\n }),\n );\n};\n\nconst PanelDialogHeader = (props: PanelDialogHeaderProps): JSX.Element => {\n const messages = useUiMessages();\n const tone = useContext(PanelDialogToneContext);\n const icon = () => {\n const value = tone();\n return value ? dialogToneIcon(value) : props.icon;\n };\n return (\n <header class=\"k2b-panel-dialog__header\" data-surface={usePanelDialogSurface()} data-has-subtitle={Boolean(props.subtitle)}>\n <Show when={icon()}>\n {(icon) => (\n <span class=\"k2b-panel-dialog__icon k2b-icon-tile\" data-tone={tone()} aria-hidden=\"true\">\n <i class={icon()} />\n </span>\n )}\n </Show>\n <div class=\"k2b-panel-dialog__heading\">\n <Show when={tone()}>\n {(value) => (\n <span class=\"k2b-sr-only\" data-dialog-tone-label>\n {dialogToneLabel(messages(), value())}\n </span>\n )}\n </Show>\n <h2>{props.title}</h2>\n <Show when={props.subtitle}>\n <p>{props.subtitle}</p>\n </Show>\n </div>\n <Show when={props.actions}>\n <div class=\"k2b-panel-dialog__actions\">{props.actions}</div>\n </Show>\n <Show when={props.close}>\n <button\n type=\"button\"\n class=\"k2b-dialog__close\"\n aria-label={props.closeLabel ?? messages().closeDialog}\n disabled={props.closeDisabled}\n onClick={props.close}\n >\n <i class=\"ti ti-x\" aria-hidden=\"true\" />\n </button>\n </Show>\n </header>\n );\n};\n\nconst PanelDialogBody = (props: PanelDialogBodyProps): JSX.Element => {\n let body: HTMLDivElement | undefined;\n createScrollFade(\n () => body,\n () => props.scrollFade !== false,\n );\n return (\n <div\n ref={body}\n class=\"k2b-panel-dialog__body\"\n data-scroll-preserve={props.scrollPreserveKey}\n data-surface={usePanelDialogSurface()}\n data-scroll-fade-mode={props.scrollFade !== false ? \"both\" : undefined}\n >\n {props.children}\n </div>\n );\n};\n\nconst PanelDialogFooter = (props: PanelDialogFooterProps): JSX.Element => (\n <footer class=\"k2b-panel-dialog__footer\" data-surface={usePanelDialogSurface()}>\n {props.children}\n </footer>\n);\n\nconst PanelDialogSection = (props: PanelDialogSectionProps): JSX.Element => {\n const id = `k2b-panel-dialog-section-${createUniqueId()}`;\n const [internalOpen, setInternalOpen] = createSignal(props.defaultOpen ?? false);\n const open = () => !props.hideable || (props.open ?? internalOpen());\n let section: HTMLElement | undefined;\n let expand: HTMLButtonElement | undefined;\n let collapse: HTMLButtonElement | undefined;\n const toggle = (next: boolean) => {\n if (props.disabled) return;\n if (props.open === undefined) setInternalOpen(next);\n props.onOpenChange?.(next);\n };\n createEffect(() => {\n if (!props.hideable) return;\n const expanded = open();\n queueMicrotask(() => {\n if (expanded !== open()) return;\n const active = section?.ownerDocument.activeElement;\n if (expanded && active === expand) collapse?.focus();\n if (!expanded && active && active !== expand && section?.contains(active)) expand?.focus();\n });\n });\n\n return (\n <section\n ref={section}\n class=\"k2b-panel-dialog__section\"\n data-surface={usePanelDialogSurface()}\n data-hideable={props.hideable || undefined}\n data-open={props.hideable ? open() : undefined}\n aria-labelledby={open() ? id : `${id}-closed`}\n >\n <Show when={props.hideable}>\n <div hidden={open()}>\n <Button\n ref={expand}\n variant=\"ghost\"\n class=\"k2b-panel-dialog__section-summary\"\n disabled={props.disabled}\n aria-expanded={false}\n aria-controls={`${id}-body`}\n onClick={() => toggle(true)}\n >\n <Show when={props.icon}>{(icon) => <i class={icon()} aria-hidden=\"true\" />}</Show>\n <span class=\"k2b-panel-dialog__section-copy\">\n <span id={`${id}-closed`} class=\"k2b-panel-dialog__section-title\">\n {props.title}\n </span>\n <Show when={props.subtitle}>\n <span class=\"k2b-panel-dialog__section-subtitle\">{props.subtitle}</span>\n </Show>\n </span>\n <i class=\"ti ti-eye\" aria-hidden=\"true\" />\n </Button>\n </div>\n </Show>\n <header hidden={!open()}>\n <Show when={props.icon}>\n {(icon) => (\n <span class=\"k2b-panel-dialog__section-icon\">\n <i class={icon()} aria-hidden=\"true\" />\n </span>\n )}\n </Show>\n <div>\n <h3 id={id}>{props.title}</h3>\n <Show when={props.subtitle}>\n <p class=\"k2b-panel-dialog__section-subtitle\">{props.subtitle}</p>\n </Show>\n </div>\n <Show when={props.actions}>\n <div class=\"k2b-panel-dialog__actions\">{props.actions}</div>\n </Show>\n <Show when={props.hideable}>\n <Button\n ref={collapse}\n variant=\"ghost\"\n size=\"sm\"\n class=\"k2b-icon-button\"\n disabled={props.disabled}\n aria-labelledby={id}\n aria-expanded={true}\n aria-controls={`${id}-body`}\n onClick={() => toggle(false)}\n >\n <i class=\"ti ti-eye-off\" aria-hidden=\"true\" />\n </Button>\n </Show>\n </header>\n <div id={`${id}-body`} class=\"k2b-panel-dialog__section-body\" hidden={!open()}>\n {props.children}\n </div>\n </section>\n );\n};\n\nconst PanelDialogTabs = <T extends string>(props: PanelDialogTabsProps<T>): JSX.Element => {\n const panelDialogMessages = usePanelDialogMessages();\n return (\n <Tabs\n class=\"k2b-panel-dialog__tabs\"\n value={props.value}\n onValueChange={props.onValueChange}\n ariaLabel={props.ariaLabel ?? props.label ?? panelDialogMessages().dialogTabs}\n options={props.options}\n />\n );\n};\n\nconst PanelDialog = ((props: PanelDialogProps): JSX.Element => {\n const surface = props.surface ?? \"contained\";\n return (\n <PanelDialogSurfaceContext.Provider value={surface}>\n <PanelDialogToneContext.Provider value={() => props.tone}>\n <div class=\"k2b-panel-dialog\" data-surface={surface} data-tone={props.tone}>\n {props.children}\n </div>\n </PanelDialogToneContext.Provider>\n </PanelDialogSurfaceContext.Provider>\n );\n}) as PanelDialogComponent;\n\nPanelDialog.Header = PanelDialogHeader;\nPanelDialog.Body = PanelDialogBody;\nPanelDialog.Footer = PanelDialogFooter;\nPanelDialog.Section = PanelDialogSection;\nPanelDialog.Tabs = PanelDialogTabs;\n\nexport default PanelDialog;\n"],"mappings":"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","ignoreList":[]}
|
|
1
|
+
{"version":3,"names":[],"sources":["layout/PanelDialog.tsx"],"sourcesContent":["import { createContext, createEffect, createSignal, createUniqueId, type JSX, Show, useContext } from \"solid-js\";\nimport { Button } from \"../actions/Button\";\nimport { Tabs } from \"../actions/Tabs\";\nimport type { OpenDialogOptions } from \"../feedback/dialog-core\";\nimport { type DialogTone, dialogToneIcon, dialogToneLabel } from \"../feedback/dialog-tone\";\nimport { sharedPrompts } from \"../feedback/prompt-confirm\";\nimport { resolvePromptMessages } from \"../feedback/prompt-messages\";\nimport { useUiMessages } from \"../intl/messages\";\nimport { usePanelDialogMessages } from \"./panel-dialog-messages\";\nimport { createScrollFade } from \"./scroll-fade\";\n\nexport type PanelDialogSurface = \"contained\" | \"floating\";\n\nexport type PanelDialogProps = {\n children: JSX.Element;\n surface?: PanelDialogSurface;\n /** A 2 px edge in the tone's colour inside the dialog frame; the header shows the tone's icon instead of its own. */\n tone?: DialogTone;\n /**\n * The body shows a picture or a video edge to edge, and the header floats over it as glass chips: the title and\n * subtitle in one chip, the actions in a group, and the close button. For documents, text, and tables leave it off.\n */\n media?: boolean;\n};\n\nexport type PanelDialogHeaderProps = {\n title: JSX.Element;\n subtitle?: JSX.Element;\n icon?: string;\n actions?: JSX.Element;\n close?: () => void;\n closeDisabled?: boolean;\n closeLabel?: string;\n};\n\nexport type PanelDialogBodyProps = {\n children: JSX.Element;\n scrollPreserveKey?: string;\n scrollFade?: boolean;\n};\n\nexport type PanelDialogFooterProps = {\n children: JSX.Element;\n};\n\nexport type PanelDialogSectionProps = {\n title: JSX.Element;\n subtitle?: JSX.Element;\n icon?: string;\n actions?: JSX.Element;\n children: JSX.Element;\n} & (\n | { hideable?: false; open?: never; defaultOpen?: never; onOpenChange?: never; disabled?: never }\n | { hideable: true; open?: boolean; defaultOpen?: boolean; onOpenChange?: (open: boolean) => void; disabled?: boolean }\n);\n\nexport type PanelDialogTabOption<T extends string = string> = {\n value: T;\n label: JSX.Element;\n icon?: string;\n disabled?: boolean;\n};\n\nexport type PanelDialogTabsProps<T extends string = string> = {\n options: readonly PanelDialogTabOption<T>[];\n value: T | (() => T);\n onValueChange: (value: T) => void;\n ariaLabel?: string;\n label?: string;\n};\n\ntype PanelDialogComponent = ((props: PanelDialogProps) => JSX.Element) & {\n Header: (props: PanelDialogHeaderProps) => JSX.Element;\n Body: (props: PanelDialogBodyProps) => JSX.Element;\n Footer: (props: PanelDialogFooterProps) => JSX.Element;\n Section: (props: PanelDialogSectionProps) => JSX.Element;\n Tabs: <T extends string>(props: PanelDialogTabsProps<T>) => JSX.Element;\n};\n\nconst PanelDialogSurfaceContext = createContext<PanelDialogSurface>(\"contained\");\nconst usePanelDialogSurface = () => useContext(PanelDialogSurfaceContext);\nconst PanelDialogToneContext = createContext<() => DialogTone | undefined>(() => undefined);\nconst PanelDialogMediaContext = createContext(false);\n\nconst panelDialogBasePanelClass = \"k2b-dialog k2b-panel-dialog-frame\";\n\nexport const panelDialogPanelClass = `${panelDialogBasePanelClass} is-standard`;\nexport const panelDialogOptions = {\n panelClassName: panelDialogPanelClass,\n contentClassName: \"k2b-panel-dialog-viewport\",\n} satisfies OpenDialogOptions;\n\nexport const panelDialogWidePanelClass = `${panelDialogBasePanelClass} is-wide`;\nexport const panelDialogWideOptions = {\n panelClassName: panelDialogWidePanelClass,\n contentClassName: \"k2b-panel-dialog-viewport\",\n} satisfies OpenDialogOptions;\n\nexport const panelDialogFixedPanelClass = `${panelDialogBasePanelClass} is-fixed`;\nexport const panelDialogFixedOptions = {\n panelClassName: panelDialogFixedPanelClass,\n contentClassName: \"k2b-panel-dialog-viewport is-fixed\",\n} satisfies OpenDialogOptions;\n\nexport const panelDialogWorkspacePanelClass = `${panelDialogBasePanelClass} is-workspace`;\nexport const panelDialogWorkspaceOptions = {\n panelClassName: panelDialogWorkspacePanelClass,\n contentClassName: \"k2b-panel-dialog-viewport is-workspace\",\n} satisfies OpenDialogOptions;\n\nexport const confirmDiscardIfDirty = async (dirty: boolean | (() => boolean)): Promise<boolean> => {\n const hasChanges = typeof dirty === \"function\" ? dirty() : dirty;\n if (!hasChanges) return true;\n return Boolean(\n await sharedPrompts.confirm(resolvePromptMessages().discardUnsavedChanges, {\n title: resolvePromptMessages().unsavedChangesTitle,\n variant: \"danger\",\n confirmText: resolvePromptMessages().discard,\n }),\n );\n};\n\nconst PanelDialogHeader = (props: PanelDialogHeaderProps): JSX.Element => {\n const messages = useUiMessages();\n const tone = useContext(PanelDialogToneContext);\n const icon = () => {\n const value = tone();\n return value ? dialogToneIcon(value) : props.icon;\n };\n // Over a picture the header's parts are glass layers of their own; the dialog owns them, so it sets the surface.\n const media = useContext(PanelDialogMediaContext);\n const layer = media ? \" k2b-overlay-surface\" : \"\";\n return (\n <header class=\"k2b-panel-dialog__header\" data-surface={usePanelDialogSurface()} data-has-subtitle={Boolean(props.subtitle)}>\n <Show when={icon() && !media}>\n <span class=\"k2b-panel-dialog__icon k2b-icon-tile\" data-tone={tone()} aria-hidden=\"true\">\n <i class={icon()} />\n </span>\n </Show>\n <div class={`k2b-panel-dialog__heading${layer}`}>\n <Show when={tone()}>\n {(value) => (\n <span class=\"k2b-sr-only\" data-dialog-tone-label>\n {dialogToneLabel(messages(), value())}\n </span>\n )}\n </Show>\n <h2 class={media ? \"k2b-truncate-fade\" : undefined}>{props.title}</h2>\n <Show when={props.subtitle}>\n <p>{props.subtitle}</p>\n </Show>\n </div>\n <Show when={props.actions}>\n <div class={`k2b-panel-dialog__actions${layer}`}>{props.actions}</div>\n </Show>\n <Show when={props.close}>\n <button\n type=\"button\"\n class={`k2b-dialog__close${layer}`}\n aria-label={props.closeLabel ?? messages().closeDialog}\n disabled={props.closeDisabled}\n onClick={props.close}\n >\n <i class=\"ti ti-x\" aria-hidden=\"true\" />\n </button>\n </Show>\n </header>\n );\n};\n\nconst PanelDialogBody = (props: PanelDialogBodyProps): JSX.Element => {\n let body: HTMLDivElement | undefined;\n createScrollFade(\n () => body,\n () => props.scrollFade !== false,\n );\n return (\n <div\n ref={body}\n class=\"k2b-panel-dialog__body\"\n data-scroll-preserve={props.scrollPreserveKey}\n data-surface={usePanelDialogSurface()}\n data-scroll-fade-mode={props.scrollFade !== false ? \"both\" : undefined}\n >\n {props.children}\n </div>\n );\n};\n\nconst PanelDialogFooter = (props: PanelDialogFooterProps): JSX.Element => (\n <footer class=\"k2b-panel-dialog__footer\" data-surface={usePanelDialogSurface()}>\n {props.children}\n </footer>\n);\n\nconst PanelDialogSection = (props: PanelDialogSectionProps): JSX.Element => {\n const id = `k2b-panel-dialog-section-${createUniqueId()}`;\n const [internalOpen, setInternalOpen] = createSignal(props.defaultOpen ?? false);\n const open = () => !props.hideable || (props.open ?? internalOpen());\n let section: HTMLElement | undefined;\n let expand: HTMLButtonElement | undefined;\n let collapse: HTMLButtonElement | undefined;\n const toggle = (next: boolean) => {\n if (props.disabled) return;\n if (props.open === undefined) setInternalOpen(next);\n props.onOpenChange?.(next);\n };\n createEffect(() => {\n if (!props.hideable) return;\n const expanded = open();\n queueMicrotask(() => {\n if (expanded !== open()) return;\n const active = section?.ownerDocument.activeElement;\n if (expanded && active === expand) collapse?.focus();\n if (!expanded && active && active !== expand && section?.contains(active)) expand?.focus();\n });\n });\n\n return (\n <section\n ref={section}\n class=\"k2b-panel-dialog__section\"\n data-surface={usePanelDialogSurface()}\n data-hideable={props.hideable || undefined}\n data-open={props.hideable ? open() : undefined}\n aria-labelledby={open() ? id : `${id}-closed`}\n >\n <Show when={props.hideable}>\n <div hidden={open()}>\n <Button\n ref={expand}\n variant=\"ghost\"\n class=\"k2b-panel-dialog__section-summary\"\n disabled={props.disabled}\n aria-expanded={false}\n aria-controls={`${id}-body`}\n onClick={() => toggle(true)}\n >\n <Show when={props.icon}>{(icon) => <i class={icon()} aria-hidden=\"true\" />}</Show>\n <span class=\"k2b-panel-dialog__section-copy\">\n <span id={`${id}-closed`} class=\"k2b-panel-dialog__section-title\">\n {props.title}\n </span>\n <Show when={props.subtitle}>\n <span class=\"k2b-panel-dialog__section-subtitle\">{props.subtitle}</span>\n </Show>\n </span>\n <i class=\"ti ti-eye\" aria-hidden=\"true\" />\n </Button>\n </div>\n </Show>\n <header hidden={!open()}>\n <Show when={props.icon}>\n {(icon) => (\n <span class=\"k2b-panel-dialog__section-icon\">\n <i class={icon()} aria-hidden=\"true\" />\n </span>\n )}\n </Show>\n <div>\n <h3 id={id}>{props.title}</h3>\n <Show when={props.subtitle}>\n <p class=\"k2b-panel-dialog__section-subtitle\">{props.subtitle}</p>\n </Show>\n </div>\n <Show when={props.actions}>\n <div class=\"k2b-panel-dialog__actions\">{props.actions}</div>\n </Show>\n <Show when={props.hideable}>\n <Button\n ref={collapse}\n variant=\"ghost\"\n size=\"sm\"\n class=\"k2b-icon-button\"\n disabled={props.disabled}\n aria-labelledby={id}\n aria-expanded={true}\n aria-controls={`${id}-body`}\n onClick={() => toggle(false)}\n >\n <i class=\"ti ti-eye-off\" aria-hidden=\"true\" />\n </Button>\n </Show>\n </header>\n <div id={`${id}-body`} class=\"k2b-panel-dialog__section-body\" hidden={!open()}>\n {props.children}\n </div>\n </section>\n );\n};\n\nconst PanelDialogTabs = <T extends string>(props: PanelDialogTabsProps<T>): JSX.Element => {\n const panelDialogMessages = usePanelDialogMessages();\n return (\n <Tabs\n class=\"k2b-panel-dialog__tabs\"\n value={props.value}\n onValueChange={props.onValueChange}\n ariaLabel={props.ariaLabel ?? props.label ?? panelDialogMessages().dialogTabs}\n options={props.options}\n />\n );\n};\n\nconst PanelDialog = ((props: PanelDialogProps): JSX.Element => {\n const surface = props.surface ?? \"contained\";\n return (\n <PanelDialogSurfaceContext.Provider value={surface}>\n <PanelDialogToneContext.Provider value={() => props.tone}>\n <PanelDialogMediaContext.Provider value={Boolean(props.media)}>\n <div class=\"k2b-panel-dialog\" data-surface={surface} data-tone={props.tone} data-media={props.media ? \"\" : undefined}>\n {props.children}\n </div>\n </PanelDialogMediaContext.Provider>\n </PanelDialogToneContext.Provider>\n </PanelDialogSurfaceContext.Provider>\n );\n}) as PanelDialogComponent;\n\nPanelDialog.Header = PanelDialogHeader;\nPanelDialog.Body = PanelDialogBody;\nPanelDialog.Footer = PanelDialogFooter;\nPanelDialog.Section = PanelDialogSection;\nPanelDialog.Tabs = PanelDialogTabs;\n\nexport default PanelDialog;\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -12,14 +12,15 @@ var _tmpl$ = ["<div class=\"k2b-stat-cell__head\">", "<span class=\"k2b-stat-cel
|
|
|
12
12
|
_tmpl$7 = ["<div class=\"k2b-stat-cell__support\">", "</div>"],
|
|
13
13
|
_tmpl$8 = ["<span class=\"k2b-stat-cell__icon k2b-icon-tile\"", " aria-hidden=\"true\"><i", "></i></span>"],
|
|
14
14
|
_tmpl$9 = ["<span class=\"", "\"", ">", "</span>"],
|
|
15
|
-
_tmpl$0 = ["<span
|
|
16
|
-
_tmpl$1 = ["<span class=\"k2b-stat-cell__sub\">", "</span>"],
|
|
17
|
-
_tmpl$10 = ["<
|
|
18
|
-
_tmpl$11 = ["<
|
|
19
|
-
_tmpl$12 = ["<span class=\"k2b-stat-
|
|
20
|
-
_tmpl$13 = ["<
|
|
21
|
-
_tmpl$14 = ["<
|
|
22
|
-
_tmpl$15 = ["<
|
|
15
|
+
_tmpl$0 = ["<span role=\"img\"", ">—</span>"],
|
|
16
|
+
_tmpl$1 = ["<span class=\"k2b-stat-cell__sub\">", " ", "</span>"],
|
|
17
|
+
_tmpl$10 = ["<span class=\"k2b-stat-cell__sub\">", "</span>"],
|
|
18
|
+
_tmpl$11 = ["<i class=\"", "\"", " aria-hidden=\"true\"></i>"],
|
|
19
|
+
_tmpl$12 = ["<span class=\"k2b-stat-cell__accent\"", "><i", " aria-hidden=\"true\"></i>", "</span>"],
|
|
20
|
+
_tmpl$13 = ["<span class=\"k2b-stat-cell__stale\"><i class=\"ti ti-clock-exclamation\" aria-hidden=\"true\"></i>", "</span>"],
|
|
21
|
+
_tmpl$14 = ["<button type=\"button\" class=\"k2b-stat-cell__retry\">", "</button>"],
|
|
22
|
+
_tmpl$15 = ["<a", " class=\"k2b-stat-cell k2b-stat-cell--link\"", "><i class=\"ti ti-external-link k2b-stat-cell__link-icon\" aria-hidden=\"true\"></i>", "</a>"],
|
|
23
|
+
_tmpl$16 = ["<div class=\"k2b-stat-cell\"", ">", "</div>"];
|
|
23
24
|
import { Match, Show, Switch } from "solid-js";
|
|
24
25
|
import { ChartSparkline } from "../content/ChartSparkline";
|
|
25
26
|
import { useLocale } from "../intl/locale";
|
|
@@ -66,7 +67,17 @@ function Body(props) {
|
|
|
66
67
|
children: icon => _$ssr(_tmpl$8, _$ssrAttribute("data-tone", _$escape(props.tone ?? "zinc", true), false), _$ssrAttribute("class", _$escape(icon(), true), false))
|
|
67
68
|
})), _$ssrAttribute("data-size", _$escape(size(), true), false), _$escape(props.label)), _$ssr(_tmpl$5, _$escape(_$createComponent(Switch, {
|
|
68
69
|
get fallback() {
|
|
69
|
-
return [_$ssr(_tmpl$9, `k2b-stat-cell__value ${_$escape(props.valueClass ?? "", true)}`, _$ssrAttribute("data-size", _$escape(size(), true), false) + _$ssrAttribute("data-empty", _$escape(empty() || undefined, true), false) + _$ssrAttribute("title", _$escape(props.title, true), false),
|
|
70
|
+
return [_$ssr(_tmpl$9, `k2b-stat-cell__value ${_$escape(props.valueClass ?? "", true)}`, _$ssrAttribute("data-size", _$escape(size(), true), false) + _$ssrAttribute("data-empty", _$escape(empty() || undefined, true), false) + _$ssrAttribute("title", _$escape(props.title, true), false), _$escape(_$createComponent(Show, {
|
|
71
|
+
get when() {
|
|
72
|
+
return !empty();
|
|
73
|
+
},
|
|
74
|
+
get fallback() {
|
|
75
|
+
return _$ssr(_tmpl$0, _$ssrAttribute("aria-label", _$escape(t().noValue, true), false));
|
|
76
|
+
},
|
|
77
|
+
get children() {
|
|
78
|
+
return props.value;
|
|
79
|
+
}
|
|
80
|
+
}))), _$createComponent(Show, {
|
|
70
81
|
get when() {
|
|
71
82
|
return _$memo(() => !!!empty())() && props.delta;
|
|
72
83
|
},
|
|
@@ -108,12 +119,12 @@ function Body(props) {
|
|
|
108
119
|
get when() {
|
|
109
120
|
return props.compare;
|
|
110
121
|
},
|
|
111
|
-
children: compare => _$ssr(_tmpl$
|
|
122
|
+
children: compare => _$ssr(_tmpl$1, _$escape(compare().label), _$escape(compareValue()))
|
|
112
123
|
}), _$createComponent(Show, {
|
|
113
124
|
get when() {
|
|
114
125
|
return props.sub;
|
|
115
126
|
},
|
|
116
|
-
children: sub => _$ssr(_tmpl$
|
|
127
|
+
children: sub => _$ssr(_tmpl$10, _$escape(sub()))
|
|
117
128
|
}), _$createComponent(Show, {
|
|
118
129
|
get when() {
|
|
119
130
|
return accent();
|
|
@@ -123,9 +134,9 @@ function Body(props) {
|
|
|
123
134
|
return value().text;
|
|
124
135
|
},
|
|
125
136
|
get fallback() {
|
|
126
|
-
return _$ssr(_tmpl$
|
|
137
|
+
return _$ssr(_tmpl$11, `${_$escape(value().icon, true)} k2b-stat-cell__accent-icon`, _$ssrAttribute("data-tone", _$escape(value().tone, true), false));
|
|
127
138
|
},
|
|
128
|
-
children: text => _$ssr(_tmpl$
|
|
139
|
+
children: text => _$ssr(_tmpl$12, _$ssrAttribute("data-tone", _$escape(value().tone, true), false), _$ssrAttribute("class", _$escape(value().icon, true), false), _$escape(text()))
|
|
129
140
|
})
|
|
130
141
|
}), _$createComponent(Show, {
|
|
131
142
|
get when() {
|
|
@@ -150,11 +161,11 @@ function Body(props) {
|
|
|
150
161
|
}
|
|
151
162
|
})];
|
|
152
163
|
},
|
|
153
|
-
children: stale => [_$ssr(_tmpl$
|
|
164
|
+
children: stale => [_$ssr(_tmpl$13, _$escape(stale())), _$createComponent(Show, {
|
|
154
165
|
get when() {
|
|
155
166
|
return props.onRetry;
|
|
156
167
|
},
|
|
157
|
-
children: retry => _$ssr(_tmpl$
|
|
168
|
+
children: retry => _$ssr(_tmpl$14, _$escape(t().reload))
|
|
158
169
|
})]
|
|
159
170
|
});
|
|
160
171
|
},
|
|
@@ -175,7 +186,7 @@ function Body(props) {
|
|
|
175
186
|
get when() {
|
|
176
187
|
return props.onRetry;
|
|
177
188
|
},
|
|
178
|
-
children: retry => _$ssr(_tmpl$
|
|
189
|
+
children: retry => _$ssr(_tmpl$14, _$escape(t().retry))
|
|
179
190
|
});
|
|
180
191
|
}
|
|
181
192
|
})];
|
|
@@ -198,10 +209,10 @@ export function StatCell(props) {
|
|
|
198
209
|
return _$memo(() => !!(props.href && !props.status))() && !(props.stale && props.onRetry);
|
|
199
210
|
},
|
|
200
211
|
get fallback() {
|
|
201
|
-
return _$ssr(_tmpl$
|
|
212
|
+
return _$ssr(_tmpl$16, _$ssrAttribute("data-size", _$escape(size(), true), false) + _$ssrAttribute("data-surface", _$escape(surface, true), false) + _$ssrAttribute("data-wrap", _$escape(props.wrap || undefined, true), false) + _$ssrAttribute("data-delta-placement", _$escape(props.deltaPlacement, true), false) + _$ssrAttribute("data-status", _$escape(props.status, true), false) + _$ssrAttribute("aria-busy", _$escape(props.status === "loading" || undefined, true), false), _$escape(_$createComponent(Body, props)));
|
|
202
213
|
},
|
|
203
214
|
get children() {
|
|
204
|
-
return _$ssr(_tmpl$
|
|
215
|
+
return _$ssr(_tmpl$15, _$ssrAttribute("href", _$escape(props.href, true), false), _$ssrAttribute("data-size", _$escape(size(), true), false) + _$ssrAttribute("data-surface", _$escape(surface, true), false) + _$ssrAttribute("data-wrap", _$escape(props.wrap || undefined, true), false) + _$ssrAttribute("data-delta-placement", _$escape(props.deltaPlacement, true), false), _$escape(_$createComponent(Body, props)));
|
|
205
216
|
}
|
|
206
217
|
});
|
|
207
218
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["surfaces/StatCell.tsx"],"sourcesContent":["import { type JSX, Match, Show, Switch } from \"solid-js\";\nimport type { ChartNumberFormat } from \"../charts/description\";\nimport { ChartSparkline } from \"../content/ChartSparkline\";\nimport type { ChartTooltipFormatter } from \"../content/chart-inspection-core\";\nimport { useLocale } from \"../intl/locale\";\nimport type { AccentColor } from \"../semantics\";\nimport { DeltaBadge } from \"./delta-badge\";\nimport { type StatGridSize, useStatGridSize, useStatGridSurface } from \"./StatGrid\";\nimport { useStatCellMessages } from \"./stat-cell-messages\";\n\nexport type StatCellTone = AccentColor;\n\nexport type StatCellAccent = {\n tone: StatCellTone;\n icon: string;\n text?: string;\n};\n\n/**\n * The change against a comparison period. `unit: \"ratio\"` (default) reads `0.082` as `+8.2 %`; `\"points\"` is the\n * difference of two shares in ratio units, so `0.031` reads `+3.1 pts`. Only with `better` does the badge carry a tone\n * and say \"better\" or \"worse\"; without it the change stays unrated.\n */\nexport type StatCellDelta = {\n value: number;\n unit?: \"ratio\" | \"points\" | \"absolute\";\n /** Existing measures can express a change in their own unit instead of a ratio. */\n format?: ChartNumberFormat;\n better?: \"up\" | \"down\";\n};\n\n/** The value the change compares against, shown under the figure, such as \"Last month 44,560\". */\nexport type StatCellCompare = {\n label: string;\n value: string | number;\n};\n\nexport type StatCellSize = StatGridSize;\n\nexport type StatCellProps = {\n label: string;\n /** The figure. `null` shows the empty dash; `sub` then says why. */\n value: string | number | JSX.Element | null;\n sub?: string;\n valueClass?: string;\n /** An icon in a chip before the label, in `tone`. `\"in\"` and `\"out\"` are the money colours of `FlowAmount`. */\n icon?: string;\n /** The chip colour of `icon`. Defaults to zinc. */\n tone?: StatCellTone | \"in\" | \"out\";\n accent?: StatCellAccent;\n delta?: StatCellDelta;\n /** Keep the figure and change on separate rows, including while loading. Defaults to beside the figure. */\n deltaPlacement?: \"below\";\n compare?: StatCellCompare;\n href?: string;\n title?: string;\n trend?: readonly number[];\n /**\n * Replaces the default trend tooltip in browser code, for example with a period title or a unit.\n * `selection.datum.index` is the source index into `trend`.\n */\n trendTooltip?: ChartTooltipFormatter;\n size?: StatCellSize;\n /**\n * Wraps the label, value and support line instead of truncating them. Use it for a cell whose height nothing\n * reserves, such as one figure on its own; cells compared in a row keep one line each.\n */\n wrap?: boolean;\n /** `\"loading\"` keeps the tile's size with placeholders; `\"error\"` says the figure did not load. */\n status?: \"loading\" | \"error\";\n /** Offers \"Try again\" after an error and \"Reload\" beside `stale`. */\n onRetry?: () => void;\n /** The figure is not current: a short note such as \"As of 09:12 · not current\" replaces the support line. */\n stale?: string;\n};\n\nfunction Body(props: StatCellProps): JSX.Element {\n const gridSize = useStatGridSize();\n const size = () => props.size ?? gridSize;\n const accent = () => props.accent;\n const locale = useLocale();\n const t = useStatCellMessages();\n const defaultTrendTooltip: ChartTooltipFormatter = ({ datum }) => {\n const y = datum.values.find((field) => field.key === \"y\")?.value ?? \"\";\n return {\n rows: [\n { label: props.label, value: typeof y === \"number\" ? new Intl.NumberFormat(locale(), { maximumFractionDigits: 6 }).format(y) : y },\n ],\n };\n };\n const compareValue = () => {\n const value = props.compare?.value;\n return typeof value === \"number\" ? new Intl.NumberFormat(locale()).format(value) : value;\n };\n const empty = () => props.value === null || props.value === undefined || props.value === \"\";\n return (\n <>\n <div class=\"k2b-stat-cell__head\">\n <Show when={props.icon}>\n {(icon) => (\n <span class=\"k2b-stat-cell__icon k2b-icon-tile\" data-tone={props.tone ?? \"zinc\"} aria-hidden=\"true\">\n <i class={icon()} />\n </span>\n )}\n </Show>\n <span class=\"k2b-stat-cell__label\" data-size={size()}>\n {props.label}\n </span>\n </div>\n <div class=\"k2b-stat-cell__main\">\n <Switch\n fallback={\n <>\n <span\n class={`k2b-stat-cell__value ${props.valueClass ?? \"\"}`}\n data-size={size()}\n data-empty={empty() || undefined}\n title={props.title}\n >\n {empty() ? \"–\" : props.value}\n </span>\n <Show when={!empty() && props.delta}>{(delta) => <DeltaBadge delta={delta()} compare={props.compare} />}</Show>\n </>\n }\n >\n <Match when={props.status === \"loading\"}>\n <span class=\"k2b-stat-cell__skeleton k2b-skeleton\" data-part=\"value\" aria-hidden=\"true\" />\n <span class=\"k2b-sr-only\">{t().loading}</span>\n </Match>\n <Match when={props.status === \"error\"}>\n <span class=\"k2b-stat-cell__error\">\n <i class=\"ti ti-alert-circle\" aria-hidden=\"true\" />\n {t().notLoaded}\n </span>\n </Match>\n </Switch>\n </div>\n <div class=\"k2b-stat-cell__support\">\n <Switch\n fallback={\n <Show\n when={props.stale}\n fallback={\n <>\n <Show when={props.compare}>\n {(compare) => (\n <span class=\"k2b-stat-cell__sub\">\n {compare().label} {compareValue()}\n </span>\n )}\n </Show>\n <Show when={props.sub}>{(sub) => <span class=\"k2b-stat-cell__sub\">{sub()}</span>}</Show>\n <Show when={accent()}>\n {(value) => (\n <Show\n when={value().text}\n fallback={<i class={`${value().icon} k2b-stat-cell__accent-icon`} data-tone={value().tone} aria-hidden=\"true\" />}\n >\n {(text) => (\n <span class=\"k2b-stat-cell__accent\" data-tone={value().tone}>\n <i class={value().icon} aria-hidden=\"true\" />\n {text()}\n </span>\n )}\n </Show>\n )}\n </Show>\n {/* No figure, no trend: an empty tile says why in `sub` and keeps the size of its other states. */}\n <Show when={!empty() && props.trend && props.trend.length > 1}>\n <ChartSparkline\n labels={{ interactiveChart: props.label }}\n tooltip={props.trendTooltip ?? defaultTrendTooltip}\n class=\"k2b-stat-cell__trend\"\n data={Array.from(props.trend ?? [])}\n showLast\n />\n </Show>\n </>\n }\n >\n {(stale) => (\n <>\n <span class=\"k2b-stat-cell__stale\">\n <i class=\"ti ti-clock-exclamation\" aria-hidden=\"true\" />\n {stale()}\n </span>\n <Show when={props.onRetry}>\n {(retry) => (\n <button type=\"button\" class=\"k2b-stat-cell__retry\" onClick={() => retry()()}>\n {t().reload}\n </button>\n )}\n </Show>\n </>\n )}\n </Show>\n }\n >\n <Match when={props.status === \"loading\"}>\n <span class=\"k2b-stat-cell__skeleton k2b-skeleton\" data-part=\"support\" aria-hidden=\"true\" />\n </Match>\n <Match when={props.status === \"error\"}>\n <Show when={props.onRetry}>\n {(retry) => (\n <button type=\"button\" class=\"k2b-stat-cell__retry\" onClick={() => retry()()}>\n {t().retry}\n </button>\n )}\n </Show>\n </Match>\n </Switch>\n </div>\n </>\n );\n}\n\n/**\n * One key figure as a framed tile: icon and label, the figure with its change, and a support line with the comparison\n * and the trend. Each state (loading, error, stale, empty) keeps the tile's place and size.\n */\nexport function StatCell(props: StatCellProps): JSX.Element {\n const gridSize = useStatGridSize();\n const size = () => props.size ?? gridSize;\n const surface = useStatGridSurface();\n return (\n <Show\n // A tile that offers a retry is no link: the button must not sit inside it.\n when={props.href && !props.status && !(props.stale && props.onRetry)}\n fallback={\n <div\n class=\"k2b-stat-cell\"\n data-size={size()}\n data-surface={surface}\n data-wrap={props.wrap || undefined}\n data-delta-placement={props.deltaPlacement}\n data-status={props.status}\n aria-busy={props.status === \"loading\" || undefined}\n >\n <Body {...props} />\n </div>\n }\n >\n <a\n href={props.href}\n class=\"k2b-stat-cell k2b-stat-cell--link\"\n data-size={size()}\n data-surface={surface}\n data-wrap={props.wrap || undefined}\n data-delta-placement={props.deltaPlacement}\n >\n <i class=\"ti ti-external-link k2b-stat-cell__link-icon\" aria-hidden=\"true\" />\n <Body {...props} />\n </a>\n </Show>\n );\n}\n\nexport default StatCell;\n"],"mappings":"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","ignoreList":[]}
|
|
1
|
+
{"version":3,"names":[],"sources":["surfaces/StatCell.tsx"],"sourcesContent":["import { type JSX, Match, Show, Switch } from \"solid-js\";\nimport type { ChartNumberFormat } from \"../charts/description\";\nimport { ChartSparkline } from \"../content/ChartSparkline\";\nimport type { ChartTooltipFormatter } from \"../content/chart-inspection-core\";\nimport { useLocale } from \"../intl/locale\";\nimport type { AccentColor } from \"../semantics\";\nimport { DeltaBadge } from \"./delta-badge\";\nimport { type StatGridSize, useStatGridSize, useStatGridSurface } from \"./StatGrid\";\nimport { useStatCellMessages } from \"./stat-cell-messages\";\n\nexport type StatCellTone = AccentColor;\n\nexport type StatCellAccent = {\n tone: StatCellTone;\n icon: string;\n text?: string;\n};\n\n/**\n * The change against a comparison period. `unit: \"ratio\"` (default) reads `0.082` as `+8.2 %`; `\"points\"` is the\n * difference of two shares in ratio units, so `0.031` reads `+3.1 pts`. Only with `better` does the badge carry a tone\n * and say \"better\" or \"worse\"; without it the change stays unrated.\n */\nexport type StatCellDelta = {\n value: number;\n unit?: \"ratio\" | \"points\" | \"absolute\";\n /** Existing measures can express a change in their own unit instead of a ratio. */\n format?: ChartNumberFormat;\n better?: \"up\" | \"down\";\n};\n\n/** The value the change compares against, shown under the figure, such as \"Last month 44,560\". */\nexport type StatCellCompare = {\n label: string;\n value: string | number;\n};\n\nexport type StatCellSize = StatGridSize;\n\nexport type StatCellProps = {\n label: string;\n /** The figure. `null` shows the empty dash; `sub` then says why. */\n value: string | number | JSX.Element | null;\n sub?: string;\n valueClass?: string;\n /** An icon in a chip before the label, in `tone`. `\"in\"` and `\"out\"` are the money colours of `FlowAmount`. */\n icon?: string;\n /** The chip colour of `icon`. Defaults to zinc. */\n tone?: StatCellTone | \"in\" | \"out\";\n accent?: StatCellAccent;\n delta?: StatCellDelta;\n /** Keep the figure and change on separate rows, including while loading. Defaults to beside the figure. */\n deltaPlacement?: \"below\";\n compare?: StatCellCompare;\n href?: string;\n title?: string;\n trend?: readonly number[];\n /**\n * Replaces the default trend tooltip in browser code, for example with a period title or a unit.\n * `selection.datum.index` is the source index into `trend`.\n */\n trendTooltip?: ChartTooltipFormatter;\n size?: StatCellSize;\n /**\n * Wraps the label, value and support line instead of truncating them. Use it for a cell whose height nothing\n * reserves, such as one figure on its own; cells compared in a row keep one line each.\n */\n wrap?: boolean;\n /** `\"loading\"` keeps the tile's size with placeholders; `\"error\"` says the figure did not load. */\n status?: \"loading\" | \"error\";\n /** Offers \"Try again\" after an error and \"Reload\" beside `stale`. */\n onRetry?: () => void;\n /** The figure is not current: a short note such as \"As of 09:12 · not current\" replaces the support line. */\n stale?: string;\n};\n\nfunction Body(props: StatCellProps): JSX.Element {\n const gridSize = useStatGridSize();\n const size = () => props.size ?? gridSize;\n const accent = () => props.accent;\n const locale = useLocale();\n const t = useStatCellMessages();\n const defaultTrendTooltip: ChartTooltipFormatter = ({ datum }) => {\n const y = datum.values.find((field) => field.key === \"y\")?.value ?? \"\";\n return {\n rows: [\n { label: props.label, value: typeof y === \"number\" ? new Intl.NumberFormat(locale(), { maximumFractionDigits: 6 }).format(y) : y },\n ],\n };\n };\n const compareValue = () => {\n const value = props.compare?.value;\n return typeof value === \"number\" ? new Intl.NumberFormat(locale()).format(value) : value;\n };\n const empty = () => props.value === null || props.value === undefined || props.value === \"\";\n return (\n <>\n <div class=\"k2b-stat-cell__head\">\n <Show when={props.icon}>\n {(icon) => (\n <span class=\"k2b-stat-cell__icon k2b-icon-tile\" data-tone={props.tone ?? \"zinc\"} aria-hidden=\"true\">\n <i class={icon()} />\n </span>\n )}\n </Show>\n <span class=\"k2b-stat-cell__label\" data-size={size()}>\n {props.label}\n </span>\n </div>\n <div class=\"k2b-stat-cell__main\">\n <Switch\n fallback={\n <>\n <span\n class={`k2b-stat-cell__value ${props.valueClass ?? \"\"}`}\n data-size={size()}\n data-empty={empty() || undefined}\n title={props.title}\n >\n {/* A missing figure is the shared empty dash, named for screen readers instead of read as a dash. */}\n <Show\n when={!empty()}\n fallback={\n <span role=\"img\" aria-label={t().noValue}>\n —\n </span>\n }\n >\n {props.value}\n </Show>\n </span>\n <Show when={!empty() && props.delta}>{(delta) => <DeltaBadge delta={delta()} compare={props.compare} />}</Show>\n </>\n }\n >\n <Match when={props.status === \"loading\"}>\n <span class=\"k2b-stat-cell__skeleton k2b-skeleton\" data-part=\"value\" aria-hidden=\"true\" />\n <span class=\"k2b-sr-only\">{t().loading}</span>\n </Match>\n <Match when={props.status === \"error\"}>\n <span class=\"k2b-stat-cell__error\">\n <i class=\"ti ti-alert-circle\" aria-hidden=\"true\" />\n {t().notLoaded}\n </span>\n </Match>\n </Switch>\n </div>\n <div class=\"k2b-stat-cell__support\">\n <Switch\n fallback={\n <Show\n when={props.stale}\n fallback={\n <>\n <Show when={props.compare}>\n {(compare) => (\n <span class=\"k2b-stat-cell__sub\">\n {compare().label} {compareValue()}\n </span>\n )}\n </Show>\n <Show when={props.sub}>{(sub) => <span class=\"k2b-stat-cell__sub\">{sub()}</span>}</Show>\n <Show when={accent()}>\n {(value) => (\n <Show\n when={value().text}\n fallback={<i class={`${value().icon} k2b-stat-cell__accent-icon`} data-tone={value().tone} aria-hidden=\"true\" />}\n >\n {(text) => (\n <span class=\"k2b-stat-cell__accent\" data-tone={value().tone}>\n <i class={value().icon} aria-hidden=\"true\" />\n {text()}\n </span>\n )}\n </Show>\n )}\n </Show>\n {/* No figure, no trend: an empty tile says why in `sub` and keeps the size of its other states. */}\n <Show when={!empty() && props.trend && props.trend.length > 1}>\n <ChartSparkline\n labels={{ interactiveChart: props.label }}\n tooltip={props.trendTooltip ?? defaultTrendTooltip}\n class=\"k2b-stat-cell__trend\"\n data={Array.from(props.trend ?? [])}\n showLast\n />\n </Show>\n </>\n }\n >\n {(stale) => (\n <>\n <span class=\"k2b-stat-cell__stale\">\n <i class=\"ti ti-clock-exclamation\" aria-hidden=\"true\" />\n {stale()}\n </span>\n <Show when={props.onRetry}>\n {(retry) => (\n <button type=\"button\" class=\"k2b-stat-cell__retry\" onClick={() => retry()()}>\n {t().reload}\n </button>\n )}\n </Show>\n </>\n )}\n </Show>\n }\n >\n <Match when={props.status === \"loading\"}>\n <span class=\"k2b-stat-cell__skeleton k2b-skeleton\" data-part=\"support\" aria-hidden=\"true\" />\n </Match>\n <Match when={props.status === \"error\"}>\n <Show when={props.onRetry}>\n {(retry) => (\n <button type=\"button\" class=\"k2b-stat-cell__retry\" onClick={() => retry()()}>\n {t().retry}\n </button>\n )}\n </Show>\n </Match>\n </Switch>\n </div>\n </>\n );\n}\n\n/**\n * One key figure as a framed tile: icon and label, the figure with its change, and a support line with the comparison\n * and the trend. Each state (loading, error, stale, empty) keeps the tile's place and size.\n */\nexport function StatCell(props: StatCellProps): JSX.Element {\n const gridSize = useStatGridSize();\n const size = () => props.size ?? gridSize;\n const surface = useStatGridSurface();\n return (\n <Show\n // A tile that offers a retry is no link: the button must not sit inside it.\n when={props.href && !props.status && !(props.stale && props.onRetry)}\n fallback={\n <div\n class=\"k2b-stat-cell\"\n data-size={size()}\n data-surface={surface}\n data-wrap={props.wrap || undefined}\n data-delta-placement={props.deltaPlacement}\n data-status={props.status}\n aria-busy={props.status === \"loading\" || undefined}\n >\n <Body {...props} />\n </div>\n }\n >\n <a\n href={props.href}\n class=\"k2b-stat-cell k2b-stat-cell--link\"\n data-size={size()}\n data-surface={surface}\n data-wrap={props.wrap || undefined}\n data-delta-placement={props.deltaPlacement}\n >\n <i class=\"ti ti-external-link k2b-stat-cell__link-icon\" aria-hidden=\"true\" />\n <Body {...props} />\n </a>\n </Show>\n );\n}\n\nexport default StatCell;\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -13,7 +13,8 @@ const statCellMessages = i18n.define({
|
|
|
13
13
|
notLoaded: "Not loaded",
|
|
14
14
|
retry: "Try again",
|
|
15
15
|
reload: "Reload",
|
|
16
|
-
loading: "Loading"
|
|
16
|
+
loading: "Loading",
|
|
17
|
+
noValue: "No value"
|
|
17
18
|
},
|
|
18
19
|
de: {
|
|
19
20
|
points: "Pkt.",
|
|
@@ -25,7 +26,8 @@ const statCellMessages = i18n.define({
|
|
|
25
26
|
notLoaded: "Nicht geladen",
|
|
26
27
|
retry: "Erneut versuchen",
|
|
27
28
|
reload: "Neu laden",
|
|
28
|
-
loading: "Wird geladen"
|
|
29
|
+
loading: "Wird geladen",
|
|
30
|
+
noValue: "Kein Wert"
|
|
29
31
|
}
|
|
30
32
|
}
|
|
31
33
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["surfaces/stat-cell-messages.ts"],"sourcesContent":["import { i18n } from \"@k2b/stdlib\";\nimport { useLocale } from \"../intl/locale\";\n\nconst statCellMessages = i18n.define({\n baseLocale: \"en\",\n messages: {\n en: {\n points: \"pts\",\n better: \"better\",\n worse: \"worse\",\n comparedWith: ({ label }: { label: string }) => `compared with ${label}`,\n notLoaded: \"Not loaded\",\n retry: \"Try again\",\n reload: \"Reload\",\n loading: \"Loading\",\n },\n de: {\n points: \"Pkt.\",\n better: \"besser\",\n worse: \"schlechter\",\n comparedWith: ({ label }: { label: string }) => `gegenüber ${label}`,\n notLoaded: \"Nicht geladen\",\n retry: \"Erneut versuchen\",\n reload: \"Neu laden\",\n loading: \"Wird geladen\",\n },\n },\n});\n\nexport type StatCellMessages = ReturnType<(typeof statCellMessages)[\"resolve\"]>[\"t\"];\n\n/** Resolved from the inherited render locale. */\nexport const useStatCellMessages = (): (() => StatCellMessages) => {\n const locale = useLocale();\n return () => statCellMessages.resolve([locale()]).t;\n};\n\n/** For a caller that already holds the locale, such as table text for search and copy. */\nexport const resolveStatCellMessages = (locale: string): StatCellMessages => statCellMessages.resolve([locale]).t;\n\nexport const checkStatCellMessages = () => statCellMessages.check();\n"],"mappings":"AAAA,SAAS,IAAI,QAAQ,aAAa;AAClC,SAAS,SAAS,QAAQ,gBAAgB;AAE1C,MAAM,gBAAgB,GAAG,IAAI,CAAC,MAAM,CAAC;EACnC,UAAU,EAAE,IAAI;EAChB,QAAQ,EAAE;IACR,EAAE,EAAE;MACF,MAAM,EAAE,KAAK;MACb,MAAM,EAAE,QAAQ;MAChB,KAAK,EAAE,OAAO;MACd,YAAY,EAAE,CAAC;QAAE;MAAyB,CAAC,KAAK,iBAAiB,KAAK,EAAE;MACxE,SAAS,EAAE,YAAY;MACvB,KAAK,EAAE,WAAW;MAClB,MAAM,EAAE,QAAQ;MAChB,OAAO,EAAE;IACX,CAAC;IACD,EAAE,EAAE;MACF,MAAM,EAAE,MAAM;MACd,MAAM,EAAE,QAAQ;MAChB,KAAK,EAAE,YAAY;MACnB,YAAY,EAAE,CAAC;QAAE;MAAyB,CAAC,KAAK,aAAa,KAAK,EAAE;MACpE,SAAS,EAAE,eAAe;MAC1B,KAAK,EAAE,kBAAkB;MACzB,MAAM,EAAE,WAAW;MACnB,OAAO,EAAE;IACX;EACF;AACF,CAAC,CAAC;AAIF;AACA,OAAO,MAAM,mBAAmB,GAAG,MAAgC;EACjE,MAAM,MAAM,GAAG,SAAS,CAAC,CAAC;EAC1B,OAAO,MAAM,gBAAgB,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AACrD,CAAC;;AAED;AACA,OAAO,MAAM,uBAAuB,GAAI,MAAc,IAAuB,gBAAgB,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;AAEjH,OAAO,MAAM,qBAAqB,GAAG,MAAM,gBAAgB,CAAC,KAAK,CAAC,CAAC","ignoreList":[]}
|
|
1
|
+
{"version":3,"names":[],"sources":["surfaces/stat-cell-messages.ts"],"sourcesContent":["import { i18n } from \"@k2b/stdlib\";\nimport { useLocale } from \"../intl/locale\";\n\nconst statCellMessages = i18n.define({\n baseLocale: \"en\",\n messages: {\n en: {\n points: \"pts\",\n better: \"better\",\n worse: \"worse\",\n comparedWith: ({ label }: { label: string }) => `compared with ${label}`,\n notLoaded: \"Not loaded\",\n retry: \"Try again\",\n reload: \"Reload\",\n loading: \"Loading\",\n noValue: \"No value\",\n },\n de: {\n points: \"Pkt.\",\n better: \"besser\",\n worse: \"schlechter\",\n comparedWith: ({ label }: { label: string }) => `gegenüber ${label}`,\n notLoaded: \"Nicht geladen\",\n retry: \"Erneut versuchen\",\n reload: \"Neu laden\",\n loading: \"Wird geladen\",\n noValue: \"Kein Wert\",\n },\n },\n});\n\nexport type StatCellMessages = ReturnType<(typeof statCellMessages)[\"resolve\"]>[\"t\"];\n\n/** Resolved from the inherited render locale. */\nexport const useStatCellMessages = (): (() => StatCellMessages) => {\n const locale = useLocale();\n return () => statCellMessages.resolve([locale()]).t;\n};\n\n/** For a caller that already holds the locale, such as table text for search and copy. */\nexport const resolveStatCellMessages = (locale: string): StatCellMessages => statCellMessages.resolve([locale]).t;\n\nexport const checkStatCellMessages = () => statCellMessages.check();\n"],"mappings":"AAAA,SAAS,IAAI,QAAQ,aAAa;AAClC,SAAS,SAAS,QAAQ,gBAAgB;AAE1C,MAAM,gBAAgB,GAAG,IAAI,CAAC,MAAM,CAAC;EACnC,UAAU,EAAE,IAAI;EAChB,QAAQ,EAAE;IACR,EAAE,EAAE;MACF,MAAM,EAAE,KAAK;MACb,MAAM,EAAE,QAAQ;MAChB,KAAK,EAAE,OAAO;MACd,YAAY,EAAE,CAAC;QAAE;MAAyB,CAAC,KAAK,iBAAiB,KAAK,EAAE;MACxE,SAAS,EAAE,YAAY;MACvB,KAAK,EAAE,WAAW;MAClB,MAAM,EAAE,QAAQ;MAChB,OAAO,EAAE,SAAS;MAClB,OAAO,EAAE;IACX,CAAC;IACD,EAAE,EAAE;MACF,MAAM,EAAE,MAAM;MACd,MAAM,EAAE,QAAQ;MAChB,KAAK,EAAE,YAAY;MACnB,YAAY,EAAE,CAAC;QAAE;MAAyB,CAAC,KAAK,aAAa,KAAK,EAAE;MACpE,SAAS,EAAE,eAAe;MAC1B,KAAK,EAAE,kBAAkB;MACzB,MAAM,EAAE,WAAW;MACnB,OAAO,EAAE,cAAc;MACvB,OAAO,EAAE;IACX;EACF;AACF,CAAC,CAAC;AAIF;AACA,OAAO,MAAM,mBAAmB,GAAG,MAAgC;EACjE,MAAM,MAAM,GAAG,SAAS,CAAC,CAAC;EAC1B,OAAO,MAAM,gBAAgB,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AACrD,CAAC;;AAED;AACA,OAAO,MAAM,uBAAuB,GAAI,MAAc,IAAuB,gBAAgB,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;AAEjH,OAAO,MAAM,qBAAqB,GAAG,MAAM,gBAAgB,CAAC,KAAK,CAAC,CAAC","ignoreList":[]}
|
|
@@ -6,9 +6,9 @@ import { ssr as _$ssr } from "solid-js/web";
|
|
|
6
6
|
import { escape as _$escape } from "solid-js/web";
|
|
7
7
|
var _tmpl$ = ["<button type=\"button\" class=\"k2b-dashboard-frame__link\">", "</button>"],
|
|
8
8
|
_tmpl$2 = ["<div class=\"k2b-dashboard-frame__tools\">", "</div>"],
|
|
9
|
-
_tmpl$3 = ["<header class=\"k2b-dashboard-frame__header\"><div>", "<p role=\"status\"", ">", "
|
|
9
|
+
_tmpl$3 = ["<header class=\"k2b-dashboard-frame__header\"><div>", "<p role=\"status\"", ">", "</p></div>", "</header>"],
|
|
10
10
|
_tmpl$4 = ["<div class=\"k2b-dashboard-frame__content\">", "</div>"],
|
|
11
|
-
_tmpl$5 = ["<div class=\"k2b-dashboard-frame__stack\"", "><div class=\"k2b-dashboard-frame__reserve\" aria-hidden=\"true\" inert>", "</div>", "</div>"],
|
|
11
|
+
_tmpl$5 = ["<div class=\"k2b-dashboard-frame__stack\"", " style=\"", "\"", "><div class=\"k2b-dashboard-frame__reserve\" aria-hidden=\"true\" inert>", "</div>", "</div>"],
|
|
12
12
|
_tmpl$6 = "<div class=\"k2b-dashboard-frame__skeleton\" aria-hidden=\"true\"><span></span><span></span></div>",
|
|
13
13
|
_tmpl$7 = ["<p class=\"k2b-dashboard-frame__inline-state\"", "><i", " aria-hidden=\"true\"></i>", "", "", "</p>"],
|
|
14
14
|
_tmpl$8 = ["<div class=\"k2b-dashboard-frame__body\" style=\"", "\"", ">", "</div>"],
|
|
@@ -82,14 +82,7 @@ export function DashboardFrame(props) {
|
|
|
82
82
|
get children() {
|
|
83
83
|
return props.title;
|
|
84
84
|
}
|
|
85
|
-
})), _$ssrAttribute("class", state() === "stale" ? "k2b-dashboard-frame__stale" : _$escape(undefined, true), false), _$escape(status()), _$escape(_$createComponent(Show, {
|
|
86
|
-
get when() {
|
|
87
|
-
return _$memo(() => state() === "stale")() && props.onRetry;
|
|
88
|
-
},
|
|
89
|
-
get children() {
|
|
90
|
-
return [" · ", retryLink()];
|
|
91
|
-
}
|
|
92
|
-
})), _$escape(_$createComponent(Show, {
|
|
85
|
+
})), _$ssrAttribute("class", state() === "stale" ? "k2b-dashboard-frame__stale" : _$escape(undefined, true), false), state() === "stale" && props.onRetry ? _$escape([status(), " · ", retryLink()]) : _$escape(status()), _$escape(_$createComponent(Show, {
|
|
93
86
|
get when() {
|
|
94
87
|
return tools() !== undefined;
|
|
95
88
|
},
|
|
@@ -148,7 +141,9 @@ export function DashboardFrame(props) {
|
|
|
148
141
|
})));
|
|
149
142
|
},
|
|
150
143
|
get children() {
|
|
151
|
-
return _$ssr(_tmpl$5, _$ssrAttribute("
|
|
144
|
+
return _$ssr(_tmpl$5, _$ssrAttribute("data-height", props.height ? "" : _$escape(undefined, true), false), _$ssrStyle(props.height ? {
|
|
145
|
+
height: props.height
|
|
146
|
+
} : undefined), _$ssrAttribute("aria-busy", _$escape(busy(), true), false), _$escape(reserve()), _$escape(_$createComponent(Show, {
|
|
152
147
|
get when() {
|
|
153
148
|
return shown();
|
|
154
149
|
},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["widgets/DashboardFrame.tsx"],"sourcesContent":["import { children, type JSX, Match, Show, Switch } from \"solid-js\";\nimport { Dynamic } from \"solid-js/web\";\nimport { Button } from \"../actions/Button\";\nimport { useChartMessages } from \"../content/chart-messages\";\nimport { useUiMessages } from \"../intl/messages\";\nimport { Paper } from \"../surfaces/Paper\";\nimport type { DashboardWidth } from \"./Dashboard\";\n\n/**\n * What the host's read shows: its content (`ready`), the first read in flight (`loading`), nothing to show (`empty`),\n * a failed first read (`error`), or content whose refresh failed (`stale`).\n */\nexport type DashboardFrameState = \"ready\" | \"loading\" | \"empty\" | \"error\" | \"stale\";\n\nexport type DashboardFrameProps = {\n /**\n * Heading of the frame. Without it the frame is only the surface, for content that brings its own head and states,\n * such as `ChartExplorer` with `inset=\"1rem\"`.\n */\n title?: string;\n /** One line under the title; loading and stale notes take its place, so nothing moves. */\n subtitle?: JSX.Element;\n /** Level of the title heading; defaults to 3. */\n headingLevel?: 2 | 3 | 4 | 5 | 6;\n /** Controls at the right of the head, such as a search field or a grouping chip. */\n tools?: JSX.Element;\n /** Defaults to `ready`. */\n state?: DashboardFrameState;\n /** When the shown content was read, formatted by the host (\"09:12\"); a stale note names it. */\n asOf?: string;\n /** Try again after a failure; without it a failure has no button. */\n onRetry?: () => void;\n /** The empty sentence, such as \"No campaign in this period.\" */\n empty?: JSX.Element;\n /** Tabler icon of the empty state; defaults to `ti ti-chart-bar-off`. */\n emptyIcon?: string;\n /** An action under the empty sentence, such as \"Clear search\". */\n emptyAction?: JSX.Element;\n /**\n * The content has nothing to show right now although the read succeeded, such as a search without matches: the body\n * shows the empty sentence and action while the head keeps its state, so a stale note stays.\n */\n emptyContent?: boolean;\n /** Height of the body, a CSS length. Every state keeps it. */\n height?: string;\n /**\n * A hidden copy of the full content that holds the body's height in every state, such as every row of a table. The\n * body then reaches the frame's left, right and bottom edges, like a table that brings its own rows.\n */\n reserve?: JSX.Element;\n /** States as one quiet line instead of a centred message, for short content such as an amount or one bar. */\n compact?: boolean;\n /**\n * Share of a `DashboardSection`'s six columns, like `DashboardPanel`: the frame is the grid cell itself, so it never\n * sits in a second frame. Defaults to a third there; ignored elsewhere.\n */\n width?: DashboardWidth;\n class?: string;\n children?: JSX.Element;\n};\n\n/**\n * One framed dashboard panel: title, subtitle, tools and the content the host passes, with loading, empty, failure and\n * stale in the same place and at the same height.\n */\nexport function DashboardFrame(props: DashboardFrameProps): JSX.Element {\n const ui = useUiMessages();\n const chart = useChartMessages();\n const state = () => props.state ?? \"ready\";\n const failed = () => state() === \"error\";\n const read = () => state() === \"ready\" || state() === \"stale\";\n const shown = () => read() && !props.emptyContent;\n const empty = () => state() === \"empty\" || (read() && props.emptyContent === true);\n // Slots resolve once: checking a slot and then rendering it must not mount its components twice.\n const tools = children(() => props.tools);\n const reserve = children(() => props.reserve);\n const busy = () => (state() === \"loading\" ? \"true\" : undefined);\n const className = () => (props.class ? `k2b-dashboard-frame ${props.class}` : \"k2b-dashboard-frame\");\n const retryLink = () => (\n <button type=\"button\" class=\"k2b-dashboard-frame__link\" onClick={() => props.onRetry?.()}>\n {ui().tryAgain}\n </button>\n );\n const status = () =>\n state() === \"loading\"\n ? chart().chartLoading\n : state() === \"stale\"\n ? [props.asOf ? chart().chartAsOf({ time: props.asOf }) : undefined, chart().chartRefreshFailed].filter(Boolean).join(\" · \")\n : props.subtitle;\n const sentence = () => props.empty ?? ui().noData;\n return (\n <Show\n when={props.title !== undefined}\n fallback={\n <Paper class={className()} data-width={props.width ?? \"third\"}>\n {props.children}\n </Paper>\n }\n >\n <Paper class={className()} data-width={props.width ?? \"third\"}>\n <header class=\"k2b-dashboard-frame__header\">\n <div>\n <Dynamic component={`h${props.headingLevel ?? 3}`}>{props.title}</Dynamic>\n {/* One reserved line and a polite live region: loading and stale replace the subtitle without moving. */}\n <p role=\"status\" class={state() === \"stale\" ? \"k2b-dashboard-frame__stale\" : undefined}>\n {status()}\n <Show when={state() === \"stale\" && props.onRetry}>\n {\" · \"}\n {retryLink()}\n </Show>\n </p>\n </div>\n <Show when={tools() !== undefined}>\n <div class=\"k2b-dashboard-frame__tools\">{tools()}</div>\n </Show>\n </header>\n <Show\n when={reserve() !== undefined}\n fallback={\n <div class=\"k2b-dashboard-frame__body\" style={props.height ? { height: props.height } : undefined} aria-busy={busy()}>\n <Switch fallback={props.children}>\n <Match when={state() === \"loading\" && props.compact}>\n <div class=\"k2b-dashboard-frame__skeleton\" aria-hidden=\"true\">\n <span />\n <span />\n </div>\n </Match>\n <Match when={(failed() || empty()) && props.compact}>\n <p class=\"k2b-dashboard-frame__inline-state\" role={failed() ? \"alert\" : undefined}>\n <i class={failed() ? \"ti ti-alert-circle\" : (props.emptyIcon ?? \"ti ti-chart-bar-off\")} aria-hidden=\"true\" />\n {failed() ? chart().chartLoadFailed : sentence()}\n <Show when={failed() && props.onRetry}>{retryLink()}</Show>\n <Show when={empty()}>{props.emptyAction}</Show>\n </p>\n </Match>\n <Match when={!shown()}>\n <Message />\n </Match>\n </Switch>\n </div>\n }\n >\n <div class=\"k2b-dashboard-frame__stack\" aria-busy={busy()}>\n {/* The full content, hidden: the body's height in every state. */}\n <div class=\"k2b-dashboard-frame__reserve\" aria-hidden=\"true\" inert>\n {reserve()}\n </div>\n <Show when={shown()} fallback={<Message />}>\n <div class=\"k2b-dashboard-frame__content\">{props.children}</div>\n </Show>\n </div>\n </Show>\n </Paper>\n </Show>\n );\n\n function Message(): JSX.Element {\n return (\n <div class=\"k2b-chart-explorer__state\" data-state={state()} role={failed() ? \"alert\" : undefined}>\n <Show when={state() !== \"loading\"}>\n <span class=\"k2b-chart-explorer__state-icon\" aria-hidden=\"true\">\n <i class={failed() ? \"ti ti-alert-circle\" : (props.emptyIcon ?? \"ti ti-chart-bar-off\")} />\n </span>\n </Show>\n <p>{failed() ? chart().chartLoadFailed : state() === \"loading\" ? \"\" : sentence()}</p>\n <Show when={failed() && props.onRetry}>\n <Button variant=\"secondary\" size=\"sm\" onClick={() => props.onRetry?.()}>\n <i class=\"ti ti-refresh\" aria-hidden=\"true\" />\n {ui().tryAgain}\n </Button>\n </Show>\n <Show when={empty()}>{props.emptyAction}</Show>\n </div>\n );\n }\n}\n"],"mappings":"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","ignoreList":[]}
|
|
1
|
+
{"version":3,"names":[],"sources":["widgets/DashboardFrame.tsx"],"sourcesContent":["import { children, type JSX, Match, Show, Switch } from \"solid-js\";\nimport { Dynamic } from \"solid-js/web\";\nimport { Button } from \"../actions/Button\";\nimport { useChartMessages } from \"../content/chart-messages\";\nimport { useUiMessages } from \"../intl/messages\";\nimport { Paper } from \"../surfaces/Paper\";\nimport type { DashboardWidth } from \"./Dashboard\";\n\n/**\n * What the host's read shows: its content (`ready`), the first read in flight (`loading`), nothing to show (`empty`),\n * a failed first read (`error`), or content whose refresh failed (`stale`).\n */\nexport type DashboardFrameState = \"ready\" | \"loading\" | \"empty\" | \"error\" | \"stale\";\n\nexport type DashboardFrameProps = {\n /**\n * Heading of the frame. Without it the frame is only the surface, for content that brings its own head and states,\n * such as `ChartExplorer` with `inset=\"1rem\"`.\n */\n title?: string;\n /** One line under the title; loading and stale notes take its place, so nothing moves. */\n subtitle?: JSX.Element;\n /** Level of the title heading; defaults to 3. */\n headingLevel?: 2 | 3 | 4 | 5 | 6;\n /** Controls at the right of the head, such as a search field or a grouping chip. */\n tools?: JSX.Element;\n /** Defaults to `ready`. */\n state?: DashboardFrameState;\n /** When the shown content was read, formatted by the host (\"09:12\"); a stale note names it. */\n asOf?: string;\n /** Try again after a failure; without it a failure has no button. */\n onRetry?: () => void;\n /** The empty sentence, such as \"No campaign in this period.\" */\n empty?: JSX.Element;\n /** Tabler icon of the empty state; defaults to `ti ti-chart-bar-off`. */\n emptyIcon?: string;\n /** An action under the empty sentence, such as \"Clear search\". */\n emptyAction?: JSX.Element;\n /**\n * The content has nothing to show right now although the read succeeded, such as a search without matches: the body\n * shows the empty sentence and action while the head keeps its state, so a stale note stays.\n */\n emptyContent?: boolean;\n /**\n * Height of the body, a CSS length. Every state keeps it. With `reserve`, the content fills it and scrolls inside, so\n * a table keeps its header in view; without it, the hidden copy sets the height.\n */\n height?: string;\n /**\n * A hidden copy of the full content that holds the body's height in every state, such as every row of a table. The\n * body then reaches the frame's left, right and bottom edges, like a table that brings its own rows.\n */\n reserve?: JSX.Element;\n /** States as one quiet line instead of a centred message, for short content such as an amount or one bar. */\n compact?: boolean;\n /**\n * Share of a `DashboardSection`'s six columns, like `DashboardPanel`: the frame is the grid cell itself, so it never\n * sits in a second frame. Defaults to a third there; ignored elsewhere.\n */\n width?: DashboardWidth;\n class?: string;\n children?: JSX.Element;\n};\n\n/**\n * One framed dashboard panel: title, subtitle, tools and the content the host passes, with loading, empty, failure and\n * stale in the same place and at the same height.\n */\nexport function DashboardFrame(props: DashboardFrameProps): JSX.Element {\n const ui = useUiMessages();\n const chart = useChartMessages();\n const state = () => props.state ?? \"ready\";\n const failed = () => state() === \"error\";\n const read = () => state() === \"ready\" || state() === \"stale\";\n const shown = () => read() && !props.emptyContent;\n const empty = () => state() === \"empty\" || (read() && props.emptyContent === true);\n // Slots resolve once: checking a slot and then rendering it must not mount its components twice.\n const tools = children(() => props.tools);\n const reserve = children(() => props.reserve);\n const busy = () => (state() === \"loading\" ? \"true\" : undefined);\n const className = () => (props.class ? `k2b-dashboard-frame ${props.class}` : \"k2b-dashboard-frame\");\n const retryLink = () => (\n <button type=\"button\" class=\"k2b-dashboard-frame__link\" onClick={() => props.onRetry?.()}>\n {ui().tryAgain}\n </button>\n );\n const status = () =>\n state() === \"loading\"\n ? chart().chartLoading\n : state() === \"stale\"\n ? [props.asOf ? chart().chartAsOf({ time: props.asOf }) : undefined, chart().chartRefreshFailed].filter(Boolean).join(\" · \")\n : props.subtitle;\n const sentence = () => props.empty ?? ui().noData;\n return (\n <Show\n when={props.title !== undefined}\n fallback={\n <Paper class={className()} data-width={props.width ?? \"third\"}>\n {props.children}\n </Paper>\n }\n >\n <Paper class={className()} data-width={props.width ?? \"third\"}>\n <header class=\"k2b-dashboard-frame__header\">\n <div>\n <Dynamic component={`h${props.headingLevel ?? 3}`}>{props.title}</Dynamic>\n {/* One reserved line and a polite live region: loading and stale replace the subtitle without moving. The\n line is one expression: a trailing conditional anchor would change WebKit's rendered text after the\n first client render. */}\n <p role=\"status\" class={state() === \"stale\" ? \"k2b-dashboard-frame__stale\" : undefined}>\n {state() === \"stale\" && props.onRetry ? [status(), \" · \", retryLink()] : status()}\n </p>\n </div>\n <Show when={tools() !== undefined}>\n <div class=\"k2b-dashboard-frame__tools\">{tools()}</div>\n </Show>\n </header>\n <Show\n when={reserve() !== undefined}\n fallback={\n <div class=\"k2b-dashboard-frame__body\" style={props.height ? { height: props.height } : undefined} aria-busy={busy()}>\n <Switch fallback={props.children}>\n <Match when={state() === \"loading\" && props.compact}>\n <div class=\"k2b-dashboard-frame__skeleton\" aria-hidden=\"true\">\n <span />\n <span />\n </div>\n </Match>\n <Match when={(failed() || empty()) && props.compact}>\n <p class=\"k2b-dashboard-frame__inline-state\" role={failed() ? \"alert\" : undefined}>\n <i class={failed() ? \"ti ti-alert-circle\" : (props.emptyIcon ?? \"ti ti-chart-bar-off\")} aria-hidden=\"true\" />\n {failed() ? chart().chartLoadFailed : sentence()}\n <Show when={failed() && props.onRetry}>{retryLink()}</Show>\n <Show when={empty()}>{props.emptyAction}</Show>\n </p>\n </Match>\n <Match when={!shown()}>\n <Message />\n </Match>\n </Switch>\n </div>\n }\n >\n <div\n class=\"k2b-dashboard-frame__stack\"\n data-height={props.height ? \"\" : undefined}\n style={props.height ? { height: props.height } : undefined}\n aria-busy={busy()}\n >\n {/* The full content, hidden: the body's height in every state. */}\n <div class=\"k2b-dashboard-frame__reserve\" aria-hidden=\"true\" inert>\n {reserve()}\n </div>\n <Show when={shown()} fallback={<Message />}>\n <div class=\"k2b-dashboard-frame__content\">{props.children}</div>\n </Show>\n </div>\n </Show>\n </Paper>\n </Show>\n );\n\n function Message(): JSX.Element {\n return (\n <div class=\"k2b-chart-explorer__state\" data-state={state()} role={failed() ? \"alert\" : undefined}>\n <Show when={state() !== \"loading\"}>\n <span class=\"k2b-chart-explorer__state-icon\" aria-hidden=\"true\">\n <i class={failed() ? \"ti ti-alert-circle\" : (props.emptyIcon ?? \"ti ti-chart-bar-off\")} />\n </span>\n </Show>\n <p>{failed() ? chart().chartLoadFailed : state() === \"loading\" ? \"\" : sentence()}</p>\n <Show when={failed() && props.onRetry}>\n <Button variant=\"secondary\" size=\"sm\" onClick={() => props.onRetry?.()}>\n <i class=\"ti ti-refresh\" aria-hidden=\"true\" />\n {ui().tryAgain}\n </Button>\n </Show>\n <Show when={empty()}>{props.emptyAction}</Show>\n </div>\n );\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;AAAA,SAAS,QAAQ,EAAY,KAAK,EAAE,IAAI,EAAE,MAAM,QAAQ,UAAU;AAClE,SAAS,OAAO,QAAQ,cAAc;AACtC,SAAS,MAAM,QAAQ,mBAAmB;AAC1C,SAAS,gBAAgB,QAAQ,2BAA2B;AAC5D,SAAS,aAAa,QAAQ,kBAAkB;AAChD,SAAS,KAAK,QAAQ,mBAAmB;;AAGzC;AACA;AACA;AACA;;AAqDA;AACA;AACA;AACA;AACA,OAAO,SAAS,cAAc,CAAC,KAA0B,EAAe;EACtE,MAAM,EAAE,GAAG,aAAa,CAAC,CAAC;EAC1B,MAAM,KAAK,GAAG,gBAAgB,CAAC,CAAC;EAChC,MAAM,KAAK,GAAG,MAAM,KAAK,CAAC,KAAK,IAAI,OAAO;EAC1C,MAAM,MAAM,GAAG,MAAM,KAAK,CAAC,CAAC,KAAK,OAAO;EACxC,MAAM,IAAI,GAAG,MAAM,KAAK,CAAC,CAAC,KAAK,OAAO,IAAI,KAAK,CAAC,CAAC,KAAK,OAAO;EAC7D,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,YAAY;EACjD,MAAM,KAAK,GAAG,MAAM,KAAK,CAAC,CAAC,KAAK,OAAO,IAAK,IAAI,CAAC,CAAC,IAAI,KAAK,CAAC,YAAY,KAAK,IAAK;EAClF;EACA,MAAM,KAAK,GAAG,QAAQ,CAAC,MAAM,KAAK,CAAC,KAAK,CAAC;EACzC,MAAM,OAAO,GAAG,QAAQ,CAAC,MAAM,KAAK,CAAC,OAAO,CAAC;EAC7C,MAAM,IAAI,GAAG,MAAO,KAAK,CAAC,CAAC,KAAK,SAAS,GAAG,MAAM,GAAG,SAAU;EAC/D,MAAM,SAAS,GAAG,MAAO,KAAK,CAAC,KAAK,GAAG,uBAAuB,KAAK,CAAC,KAAK,EAAE,GAAG,qBAAsB;EACpG,MAAM,SAAS,GAAG,6BAEb,EAAE,CAAC,CAAC,CAAC,QAAQ,EAEjB;EACD,MAAM,MAAM,GAAG,MACb,KAAK,CAAC,CAAC,KAAK,SAAS,GACjB,KAAK,CAAC,CAAC,CAAC,YAAY,GACpB,KAAK,CAAC,CAAC,KAAK,OAAO,GACjB,CAAC,KAAK,CAAC,IAAI,GAAG,KAAK,CAAC,CAAC,CAAC,SAAS,CAAC;IAAE,IAAI,EAAE,KAAK,CAAC;EAAK,CAAC,CAAC,GAAG,SAAS,EAAE,KAAK,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,GAC1H,KAAK,CAAC,QAAQ;EACtB,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC,CAAC,MAAM;EACjD,yBACG,IAAI;IAAA,IACH,IAAI;MAAA,OAAE,KAAK,CAAC,KAAK,KAAK,SAAS;IAAA;IAAA,IAC/B,QAAQ;MAAA,yBACL,KAAK;QAAA;UAAA,OAAQ,SAAS,CAAC,CAAC;QAAA;QAAA;UAAA,OAAc,KAAK,CAAC,KAAK,IAAI,OAAO;QAAA;QAAA;UAAA,OAC1D,KAAK,CAAC,QAAQ;QAAA;MAAA;IAAA;IAAA;MAAA,yBAIlB,KAAK;QAAA;UAAA,OAAQ,SAAS,CAAC,CAAC;QAAA;QAAA;UAAA,OAAc,KAAK,CAAC,KAAK,IAAI,OAAO;QAAA;QAAA;UAAA,kDAGtD,OAAO;YAAA,IAAC,SAAS;cAAA,OAAE,IAAI,KAAK,CAAC,YAAY,IAAI,CAAC,EAAE;YAAA;YAAA;cAAA,OAAG,KAAK,CAAC,KAAK;YAAA;UAAA,6BAIvC,KAAK,CAAC,CAAC,KAAK,OAAO,GAAG,4BAA4B,YAAG,SAAS,iBACnF,KAAK,CAAC,CAAC,KAAK,OAAO,IAAI,KAAK,CAAC,OAAO,YAAG,CAAC,MAAM,CAAC,CAAC,EAAE,KAAK,EAAE,SAAS,CAAC,CAAC,CAAC,aAAG,MAAM,CAAC,CAAC,8BAGpF,IAAI;YAAA,IAAC,IAAI;cAAA,OAAE,KAAK,CAAC,CAAC,KAAK,SAAS;YAAA;YAAA;cAAA,+BACU,KAAK,CAAC,CAAC;YAAA;UAAA,wBAGnD,IAAI;YAAA,IACH,IAAI;cAAA,OAAE,OAAO,CAAC,CAAC,KAAK,SAAS;YAAA;YAAA,IAC7B,QAAQ;cAAA,iCACwC,KAAK,CAAC,MAAM,GAAG;gBAAE,MAAM,EAAE,KAAK,CAAC;cAAO,CAAC,GAAG,SAAS,wCAAa,IAAI,CAAC,CAAC,4CACjH,MAAM;gBAAA,IAAC,QAAQ;kBAAA,OAAE,KAAK,CAAC,QAAQ;gBAAA;gBAAA;kBAAA,0BAC7B,KAAK;oBAAA,IAAC,IAAI;sBAAA,OAAE,kBAAK,CAAC,CAAC,KAAK,SAAS,OAAI,KAAK,CAAC,OAAO;oBAAA;oBAAA;sBAAA;oBAAA;kBAAA,sBAMlD,KAAK;oBAAA,IAAC,IAAI;sBAAA,OAAE,gBAAC,MAAM,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,QAAK,KAAK,CAAC,OAAO;oBAAA;oBAAA;sBAAA,6CACE,MAAM,CAAC,CAAC,GAAG,OAAO,YAAG,SAAS,yCACrE,MAAM,CAAC,CAAC,GAAG,oBAAoB,YAAI,KAAK,CAAC,SAAS,IAAI,qBAAqB,OAAC,UACrF,MAAM,CAAC,CAAC,YAAG,KAAK,CAAC,CAAC,CAAC,eAAe,aAAG,QAAQ,CAAC,CAAC,8BAC/C,IAAI;wBAAA,IAAC,IAAI;0BAAA,OAAE,qBAAM,CAAC,CAAC,OAAI,KAAK,CAAC,OAAO;wBAAA;wBAAA;0BAAA,OAAG,SAAS,CAAC,CAAC;wBAAA;sBAAA,gCAClD,IAAI;wBAAA,IAAC,IAAI;0BAAA,OAAE,KAAK,CAAC,CAAC;wBAAA;wBAAA;0BAAA,OAAG,KAAK,CAAC,WAAW;wBAAA;sBAAA;oBAAA;kBAAA,sBAG1C,KAAK;oBAAA,IAAC,IAAI;sBAAA,OAAE,CAAC,KAAK,CAAC,CAAC;oBAAA;oBAAA;sBAAA,yBAClB,OAAO;oBAAA;kBAAA;gBAAA;cAAA;YAAA;YAAA;cAAA,oDAQD,KAAK,CAAC,MAAM,GAAG,EAAE,YAAG,SAAS,4BACnC,KAAK,CAAC,MAAM,GAAG;gBAAE,MAAM,EAAE,KAAK,CAAC;cAAO,CAAC,GAAG,SAAS,wCAC/C,IAAI,CAAC,CAAC,0BAId,OAAO,CAAC,CAAC,8BAEX,IAAI;gBAAA,IAAC,IAAI;kBAAA,OAAE,KAAK,CAAC,CAAC;gBAAA;gBAAA,IAAE,QAAQ;kBAAA,yBAAG,OAAO;gBAAA;gBAAA;kBAAA,+BACM,KAAK,CAAC,QAAQ;gBAAA;cAAA;YAAA;UAAA;QAAA;MAAA;IAAA;EAAA;EAQrE,SAAS,OAAO,GAAgB;IAC9B,4DACqD,KAAK,CAAC,CAAC,yCAAQ,MAAM,CAAC,CAAC,GAAG,OAAO,YAAG,SAAS,4CAC7F,IAAI;MAAA,IAAC,IAAI;QAAA,OAAE,KAAK,CAAC,CAAC,KAAK,SAAS;MAAA;MAAA;QAAA,8CAEnB,MAAM,CAAC,CAAC,GAAG,oBAAoB,YAAI,KAAK,CAAC,SAAS,IAAI,qBAAqB,OAAC;MAAA;IAAA,KAGtF,MAAM,CAAC,CAAC,YAAG,KAAK,CAAC,CAAC,CAAC,eAAe,IAAG,KAAK,CAAC,CAAC,KAAK,SAAS,GAAG,EAAE,YAAG,QAAQ,CAAC,CAAC,8BAC/E,IAAI;MAAA,IAAC,IAAI;QAAA,OAAE,qBAAM,CAAC,CAAC,OAAI,KAAK,CAAC,OAAO;MAAA;MAAA;QAAA,yBAClC,MAAM;UAAC,OAAO;UAAa,IAAI;UAAM,OAAO,EAAE,MAAM,KAAK,CAAC,OAAO,GAAG,CAAC;UAAA;YAAA,wBAEnE,EAAE,CAAC,CAAC,CAAC,QAAQ;UAAA;QAAA;MAAA;IAAA,gCAGjB,IAAI;MAAA,IAAC,IAAI;QAAA,OAAE,KAAK,CAAC,CAAC;MAAA;MAAA;QAAA,OAAG,KAAK,CAAC,WAAW;MAAA;IAAA;EAG7C;AACF","ignoreList":[]}
|