entangle-ui 0.11.0 → 0.12.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/CHANGELOG.md +73 -0
- package/dist/esm/assets/src/components/controls/Slider/{Slider.css.ts.vanilla-Cqm3fQ0S.css → Slider.css.ts.vanilla-CLf_RC0A.css} +50 -47
- package/dist/esm/assets/src/components/navigation/Menu/{Menu.css.ts.vanilla-B5iVe5S2.css → Menu.css.ts.vanilla-Bhh1L5yl.css} +14 -11
- package/dist/esm/assets/src/components/primitives/Tooltip/{Tooltip.css.ts.vanilla-CrEFoLBX.css → Tooltip.css.ts.vanilla-BqaiGrFQ.css} +12 -9
- package/dist/esm/assets/src/components/shell/AppShell/{AppShell.css.ts.vanilla-BYmtU0O_.css → AppShell.css.ts.vanilla-BLK2-DRL.css} +1 -0
- package/dist/esm/assets/src/components/shell/MenuBar/{MenuBar.css.ts.vanilla-TgPcl4yA.css → MenuBar.css.ts.vanilla-Dt3w4f-q.css} +18 -6
- package/dist/esm/components/controls/Slider/Slider.css.js +10 -11
- package/dist/esm/components/controls/Slider/Slider.css.js.map +1 -1
- package/dist/esm/components/controls/Slider/Slider.js +40 -7
- package/dist/esm/components/controls/Slider/Slider.js.map +1 -1
- package/dist/esm/components/feedback/Spinner/Spinner.js +12 -3
- package/dist/esm/components/feedback/Spinner/Spinner.js.map +1 -1
- package/dist/esm/components/navigation/ContextMenu/ContextMenu.js +2 -2
- package/dist/esm/components/navigation/ContextMenu/ContextMenu.js.map +1 -1
- package/dist/esm/components/navigation/Menu/Menu.css.js +11 -10
- package/dist/esm/components/navigation/Menu/Menu.css.js.map +1 -1
- package/dist/esm/components/navigation/Menu/Menu.js +2 -2
- package/dist/esm/components/navigation/Menu/Menu.js.map +1 -1
- package/dist/esm/components/primitives/IconButton/IconButton.js +4 -2
- package/dist/esm/components/primitives/IconButton/IconButton.js.map +1 -1
- package/dist/esm/components/primitives/Tooltip/Tooltip.css.js +6 -5
- package/dist/esm/components/primitives/Tooltip/Tooltip.css.js.map +1 -1
- package/dist/esm/components/primitives/Tooltip/Tooltip.js +12 -2
- package/dist/esm/components/primitives/Tooltip/Tooltip.js.map +1 -1
- package/dist/esm/components/primitives/viewport/Viewport.js +5 -2
- package/dist/esm/components/primitives/viewport/Viewport.js.map +1 -1
- package/dist/esm/components/shell/AppShell/AppShell.css.js +1 -1
- package/dist/esm/components/shell/MenuBar/MenuBar.css.js +7 -6
- package/dist/esm/components/shell/MenuBar/MenuBar.css.js.map +1 -1
- package/dist/esm/components/shell/MenuBar/MenuBar.js +52 -3
- package/dist/esm/components/shell/MenuBar/MenuBar.js.map +1 -1
- package/dist/esm/{styles.js → styles.css.js} +1 -1
- package/dist/esm/styles.css.js.map +1 -0
- package/dist/tokens/tokens.dark.css +1 -1
- package/dist/tokens/tokens.json +1 -1
- package/dist/tokens/tokens.light.css +1 -1
- package/dist/types/components/controls/Slider/Slider.d.ts +7 -0
- package/dist/types/components/feedback/Spinner/Spinner.d.ts +6 -1
- package/dist/types/components/feedback/Spinner/Spinner.types.d.ts +8 -0
- package/dist/types/components/primitives/IconButton/IconButton.d.ts +2 -1
- package/dist/types/components/primitives/viewport/Viewport.d.ts +5 -2
- package/dist/types/components/shell/MenuBar/MenuBar.d.ts +862 -0
- package/package.json +2 -2
- package/dist/esm/styles.js.map +0 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,78 @@
|
|
|
1
1
|
# entangle-ui
|
|
2
2
|
|
|
3
|
+
## 0.12.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **E1 — AppShell top-chrome + MenuBar fill/inset.** `AppShell.MenuBar` now paints
|
|
8
|
+
the menu-bar chrome background (`--etui-shell-menubar-bg`) on the slot, and
|
|
9
|
+
`MenuBar` stretches to fill its host slot so the top chrome reads as one
|
|
10
|
+
continuous strip instead of a lighter content-width block. MenuBar triggers now
|
|
11
|
+
inset their hover/active fill (rounded, vertically centered) from the chrome
|
|
12
|
+
edges. Docs clarify that side toolbar slots (`AppShell.Toolbar position="left|right"`)
|
|
13
|
+
are the intended home for docked panels. Visual default change — no API change.
|
|
14
|
+
|
|
15
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **G1 — Align `Button` / `IconButton` icon API.** `IconButton` now accepts an
|
|
16
|
+
optional `icon` prop mirroring `Button`'s `icon`, so `<IconButton icon={…} />`
|
|
17
|
+
type-checks and the two components share one API. `children` still works for
|
|
18
|
+
back-compat (now optional); when both are set, `icon` wins. Additive.
|
|
19
|
+
|
|
20
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **E2 — MenuBar checkable / radio items.** Add `MenuBar.CheckboxItem`
|
|
21
|
+
(`checked` / `defaultChecked` / `onCheckedChange`) and `MenuBar.RadioGroup` +
|
|
22
|
+
`MenuBar.RadioItem` (`value` / `defaultValue` / `onValueChange`), mirroring the
|
|
23
|
+
navigation `Menu` API. Items reserve a leading check-mark gutter so checked and
|
|
24
|
+
unchecked rows align, use `role="menuitemcheckbox"` / `role="menuitemradio"` with
|
|
25
|
+
`aria-checked`, participate in arrow-key navigation, and keep the menu open on
|
|
26
|
+
activation by default (`closeOnClick={false}`). Additive.
|
|
27
|
+
|
|
28
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **F1 — Slider value tooltip → portal.** The drag value tooltip was an
|
|
29
|
+
absolutely-positioned child of the slider wrapper, so any ancestor `overflow`
|
|
30
|
+
(e.g. a `PropertySection` header) clipped it. It now renders in a portal to
|
|
31
|
+
`document.body` with fixed viewport coordinates anchored to the thumb, so it can
|
|
32
|
+
never be clipped. Added `tooltipPlacement?: 'top' | 'bottom'` (default `'top'`).
|
|
33
|
+
The portal is only mounted while dragging, so the idle/drag hot path is
|
|
34
|
+
unchanged. Default visual placement (above the thumb) is unchanged.
|
|
35
|
+
|
|
36
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **G2 — `Spinner` `decorative` (live-region opt-out).** Add `decorative?: boolean`
|
|
37
|
+
to `Spinner`. When set, the spinner renders `role="presentation"` + `aria-hidden`
|
|
38
|
+
with no `aria-live`, for use inside an existing live region (e.g. `StatusBar`,
|
|
39
|
+
which is itself `role="status"`) so activity isn't announced twice. Default
|
|
40
|
+
behavior (`role="status"` + `aria-live="polite"`) is unchanged. Additive.
|
|
41
|
+
|
|
42
|
+
### Patch Changes
|
|
43
|
+
|
|
44
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **F2 — Tooltip z-index on the Positioner (renders under panels).** The tooltip
|
|
45
|
+
z-index (`--etui-z-tooltip`) was set on the inner `Popup`, trapped inside the
|
|
46
|
+
portaled `Positioner`'s own `position: fixed` stacking context, so a positioned
|
|
47
|
+
sibling at a lower z-index (e.g. an `AppShell` slot at `--etui-z-base`) painted
|
|
48
|
+
over the tooltip. The token now lives on the `Positioner`. Audited the other Base
|
|
49
|
+
UI `Positioner`/`Popup` pairs and applied the same fix to the navigation `Menu`
|
|
50
|
+
and `ContextMenu` (dropdown z-index now on their positioners). `HoverCard`,
|
|
51
|
+
`Select` and `Popover` were already correct (z-index on the positioned element).
|
|
52
|
+
|
|
53
|
+
- [#109](https://github.com/SebastianWebdev/entangle-ui/pull/109) [`b61bfbd`](https://github.com/SebastianWebdev/entangle-ui/commit/b61bfbda7608652cdbcc68c7235980c6a113a9b4) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - **G3 — `Viewport` docs lead with "2D only".** The `Viewport` JSDoc, docs page,
|
|
54
|
+
and skill reference now lead with the 2D-only boundary (it owns a 2D pan/zoom
|
|
55
|
+
transform, not a 3D camera) and point to hosting your own WebGL/WebGPU canvas
|
|
56
|
+
for 3D. Docs-only; no API change.
|
|
57
|
+
|
|
58
|
+
- [#111](https://github.com/SebastianWebdev/entangle-ui/pull/111) [`f933917`](https://github.com/SebastianWebdev/entangle-ui/commit/f933917f99da18ce70ed08bbfb103d03250346c2) Thanks [@SebastianWebdev](https://github.com/SebastianWebdev)! - Fix `entangle-ui/styles.css` being tree-shaken out of production builds.
|
|
59
|
+
|
|
60
|
+
The `./styles.css` export resolved to `dist/esm/styles.js` — a JS shim whose
|
|
61
|
+
only job is to `import` the dark-theme tokens + global-scrollbar stylesheets for
|
|
62
|
+
their side effects. But the package's `sideEffects` allowlist only matches
|
|
63
|
+
`*.css`, `*.css.ts`, and `*.css.js`, so a plain `styles.js` (which exports
|
|
64
|
+
nothing) was flagged side-effect-free and dropped by production bundlers. The
|
|
65
|
+
canonical `import 'entangle-ui/styles.css'` setup then shipped **zero** `--etui-*`
|
|
66
|
+
token definitions: no colours, no fonts, and menu/tooltip popups with no
|
|
67
|
+
background or stacking. Dev was unaffected because dev servers don't tree-shake,
|
|
68
|
+
so the failure only surfaced in `build`/`preview`.
|
|
69
|
+
|
|
70
|
+
The stylesheet entry is now emitted as `dist/esm/styles.css.js`, which matches
|
|
71
|
+
the existing `*.css.js` side-effect glob (the same bucket as every component's
|
|
72
|
+
compiled style module), so the import survives production tree-shaking and the
|
|
73
|
+
dark theme lands on `:root` in dev and prod alike. No source or API change is
|
|
74
|
+
required in consumer apps.
|
|
75
|
+
|
|
3
76
|
## 0.11.0
|
|
4
77
|
|
|
5
78
|
### Minor Changes
|
|
@@ -1,15 +1,15 @@
|
|
|
1
|
-
.
|
|
1
|
+
.Slider_sliderContainerRecipe__t8kxxs2 {
|
|
2
2
|
display: flex;
|
|
3
3
|
flex-direction: column;
|
|
4
4
|
gap: var(--etui-spacing-xs);
|
|
5
5
|
width: 100%;
|
|
6
6
|
min-width: 0;
|
|
7
7
|
}
|
|
8
|
-
.
|
|
8
|
+
.Slider_sliderContainerRecipe_disabled_true__t8kxxs3 {
|
|
9
9
|
opacity: 0.5;
|
|
10
10
|
pointer-events: none;
|
|
11
11
|
}
|
|
12
|
-
.
|
|
12
|
+
.Slider_sliderWrapperStyle__t8kxxs5 {
|
|
13
13
|
position: relative;
|
|
14
14
|
display: flex;
|
|
15
15
|
align-items: center;
|
|
@@ -18,56 +18,56 @@
|
|
|
18
18
|
padding: 0px 0;
|
|
19
19
|
width: 100%;
|
|
20
20
|
}
|
|
21
|
-
.
|
|
21
|
+
.Slider_trackRecipe__t8kxxs6 {
|
|
22
22
|
position: relative;
|
|
23
23
|
flex: 1;
|
|
24
24
|
border-radius: var(--etui-radius-sm);
|
|
25
25
|
overflow: hidden;
|
|
26
26
|
border: 1px solid;
|
|
27
27
|
}
|
|
28
|
-
.
|
|
28
|
+
.Slider_trackRecipe_size_sm__t8kxxs7 {
|
|
29
29
|
height: 4px;
|
|
30
30
|
}
|
|
31
|
-
.
|
|
31
|
+
.Slider_trackRecipe_size_md__t8kxxs8 {
|
|
32
32
|
height: 6px;
|
|
33
33
|
}
|
|
34
|
-
.
|
|
34
|
+
.Slider_trackRecipe_size_lg__t8kxxs9 {
|
|
35
35
|
height: 8px;
|
|
36
36
|
}
|
|
37
|
-
.
|
|
37
|
+
.Slider_trackRecipe_error_true__t8kxxsa {
|
|
38
38
|
background: var(--etui-color-accent-error);
|
|
39
39
|
border-color: var(--etui-color-border-error);
|
|
40
40
|
}
|
|
41
|
-
.
|
|
41
|
+
.Slider_trackRecipe_error_true__t8kxxsa:hover {
|
|
42
42
|
border-color: var(--etui-color-border-error);
|
|
43
43
|
}
|
|
44
|
-
.
|
|
44
|
+
.Slider_trackRecipe_error_false__t8kxxsb {
|
|
45
45
|
background: var(--etui-color-surface-default);
|
|
46
46
|
border-color: var(--etui-color-border-default);
|
|
47
47
|
}
|
|
48
|
-
.
|
|
48
|
+
.Slider_trackRecipe_error_false__t8kxxsb:hover {
|
|
49
49
|
border-color: var(--etui-color-border-focus);
|
|
50
50
|
}
|
|
51
|
-
.
|
|
51
|
+
.Slider_fillRecipe__t8kxxsc {
|
|
52
52
|
position: absolute;
|
|
53
53
|
left: 0;
|
|
54
54
|
top: 0;
|
|
55
55
|
bottom: 0;
|
|
56
56
|
width: var(--fillPercentageVar__t8kxxs0);
|
|
57
57
|
}
|
|
58
|
-
.
|
|
58
|
+
.Slider_fillRecipe_error_true__t8kxxsd {
|
|
59
59
|
background: var(--etui-color-accent-error);
|
|
60
60
|
}
|
|
61
|
-
.
|
|
61
|
+
.Slider_fillRecipe_error_false__t8kxxse {
|
|
62
62
|
background: var(--etui-color-accent-primary);
|
|
63
63
|
}
|
|
64
|
-
.
|
|
64
|
+
.Slider_fillRecipe_isDragging_true__t8kxxsf {
|
|
65
65
|
transition: none;
|
|
66
66
|
}
|
|
67
|
-
.
|
|
67
|
+
.Slider_fillRecipe_isDragging_false__t8kxxsg {
|
|
68
68
|
transition: width 0.1s ease-out;
|
|
69
69
|
}
|
|
70
|
-
.
|
|
70
|
+
.Slider_thumbRecipe__t8kxxsh {
|
|
71
71
|
position: absolute;
|
|
72
72
|
top: 50%;
|
|
73
73
|
left: var(--thumbPercentageVar__t8kxxs1);
|
|
@@ -77,38 +77,38 @@
|
|
|
77
77
|
cursor: grab;
|
|
78
78
|
box-shadow: var(--etui-shadow-sm);
|
|
79
79
|
}
|
|
80
|
-
.
|
|
80
|
+
.Slider_thumbRecipe__t8kxxsh:hover {
|
|
81
81
|
transform: translate(-50%, -50%) scale(1.1);
|
|
82
82
|
box-shadow: var(--etui-shadow-md);
|
|
83
83
|
}
|
|
84
|
-
.
|
|
84
|
+
.Slider_thumbRecipe_size_sm__t8kxxsi {
|
|
85
85
|
width: 12px;
|
|
86
86
|
height: 12px;
|
|
87
87
|
}
|
|
88
|
-
.
|
|
88
|
+
.Slider_thumbRecipe_size_md__t8kxxsj {
|
|
89
89
|
width: 16px;
|
|
90
90
|
height: 16px;
|
|
91
91
|
}
|
|
92
|
-
.
|
|
92
|
+
.Slider_thumbRecipe_size_lg__t8kxxsk {
|
|
93
93
|
width: 20px;
|
|
94
94
|
height: 20px;
|
|
95
95
|
}
|
|
96
|
-
.
|
|
96
|
+
.Slider_thumbRecipe_error_true__t8kxxsl {
|
|
97
97
|
background: var(--etui-color-accent-error);
|
|
98
98
|
}
|
|
99
|
-
.
|
|
99
|
+
.Slider_thumbRecipe_error_false__t8kxxsm {
|
|
100
100
|
background: var(--etui-color-accent-primary);
|
|
101
101
|
}
|
|
102
|
-
.
|
|
102
|
+
.Slider_thumbRecipe_isDragging_true__t8kxxsn {
|
|
103
103
|
cursor: grabbing;
|
|
104
104
|
transform: translate(-50%, -50%) scale(1.15);
|
|
105
105
|
box-shadow: var(--etui-shadow-lg);
|
|
106
106
|
transition: none;
|
|
107
107
|
}
|
|
108
|
-
.
|
|
108
|
+
.Slider_thumbRecipe_isDragging_false__t8kxxso {
|
|
109
109
|
transition: all var(--etui-transition-fast);
|
|
110
110
|
}
|
|
111
|
-
.
|
|
111
|
+
.Slider_ticksStyle__t8kxxsp {
|
|
112
112
|
position: absolute;
|
|
113
113
|
top: 100%;
|
|
114
114
|
left: 0;
|
|
@@ -119,7 +119,7 @@
|
|
|
119
119
|
align-items: flex-start;
|
|
120
120
|
pointer-events: none;
|
|
121
121
|
}
|
|
122
|
-
.
|
|
122
|
+
.Slider_ticksStyle__t8kxxsp::before {
|
|
123
123
|
content: "";
|
|
124
124
|
position: absolute;
|
|
125
125
|
top: 2px;
|
|
@@ -128,17 +128,14 @@
|
|
|
128
128
|
height: 1px;
|
|
129
129
|
background: var(--etui-color-border-default);
|
|
130
130
|
}
|
|
131
|
-
.
|
|
131
|
+
.Slider_tickStyle__t8kxxsq {
|
|
132
132
|
width: 1px;
|
|
133
133
|
height: 4px;
|
|
134
134
|
background: var(--etui-color-text-muted);
|
|
135
135
|
margin-top: 2px;
|
|
136
136
|
}
|
|
137
|
-
.
|
|
138
|
-
position:
|
|
139
|
-
bottom: calc(100% + 8px);
|
|
140
|
-
left: var(--tooltipPercentageVar__t8kxxs2);
|
|
141
|
-
transform: translateX(-50%);
|
|
137
|
+
.Slider_sliderTooltipRecipe__t8kxxsr {
|
|
138
|
+
position: fixed;
|
|
142
139
|
background: var(--etui-color-bg-elevated);
|
|
143
140
|
color: var(--etui-color-text-primary);
|
|
144
141
|
border: 1px solid var(--etui-color-border-default);
|
|
@@ -149,9 +146,11 @@
|
|
|
149
146
|
white-space: nowrap;
|
|
150
147
|
pointer-events: none;
|
|
151
148
|
z-index: var(--etui-z-tooltip);
|
|
152
|
-
transition: all var(--etui-transition-fast);
|
|
153
149
|
}
|
|
154
|
-
.
|
|
150
|
+
.Slider_sliderTooltipRecipe_placement_top__t8kxxss {
|
|
151
|
+
transform: translate(-50%, calc(-100% - 8px));
|
|
152
|
+
}
|
|
153
|
+
.Slider_sliderTooltipRecipe_placement_top__t8kxxss::after {
|
|
155
154
|
content: "";
|
|
156
155
|
position: absolute;
|
|
157
156
|
top: 100%;
|
|
@@ -163,25 +162,29 @@
|
|
|
163
162
|
border-right: 4px solid transparent;
|
|
164
163
|
border-top: 4px solid var(--etui-color-border-default);
|
|
165
164
|
}
|
|
166
|
-
.
|
|
167
|
-
|
|
168
|
-
transform: translateX(-50%) translateY(0);
|
|
165
|
+
.Slider_sliderTooltipRecipe_placement_bottom__t8kxxst {
|
|
166
|
+
transform: translate(-50%, 8px);
|
|
169
167
|
}
|
|
170
|
-
.
|
|
171
|
-
|
|
172
|
-
|
|
168
|
+
.Slider_sliderTooltipRecipe_placement_bottom__t8kxxst::after {
|
|
169
|
+
content: "";
|
|
170
|
+
position: absolute;
|
|
171
|
+
bottom: 100%;
|
|
172
|
+
left: 50%;
|
|
173
|
+
transform: translateX(-50%);
|
|
174
|
+
width: 0;
|
|
175
|
+
height: 0;
|
|
176
|
+
border-left: 4px solid transparent;
|
|
177
|
+
border-right: 4px solid transparent;
|
|
178
|
+
border-bottom: 4px solid var(--etui-color-border-default);
|
|
173
179
|
}
|
|
174
180
|
@media (prefers-reduced-motion: reduce) {
|
|
175
|
-
.
|
|
181
|
+
.Slider_thumbRecipe__t8kxxsh {
|
|
176
182
|
transition: none;
|
|
177
183
|
}
|
|
178
|
-
.
|
|
184
|
+
.Slider_thumbRecipe__t8kxxsh:hover {
|
|
179
185
|
transform: translate(-50%, -50%);
|
|
180
186
|
}
|
|
181
|
-
.
|
|
182
|
-
transition: none;
|
|
183
|
-
}
|
|
184
|
-
.Slider_tooltipRecipe__t8kxxss {
|
|
187
|
+
.Slider_thumbRecipe_isDragging_false__t8kxxso {
|
|
185
188
|
transition: none;
|
|
186
189
|
}
|
|
187
190
|
}
|
|
@@ -1,4 +1,7 @@
|
|
|
1
|
-
.
|
|
1
|
+
.Menu_menuPositionerStyle__1pkkb710 {
|
|
2
|
+
z-index: var(--etui-z-dropdown);
|
|
3
|
+
}
|
|
4
|
+
.Menu_menuContentStyle__1pkkb711 {
|
|
2
5
|
min-width: 200px;
|
|
3
6
|
max-width: 360px;
|
|
4
7
|
background: var(--etui-color-bg-elevated);
|
|
@@ -13,11 +16,11 @@
|
|
|
13
16
|
transform-origin: var(--transform-origin);
|
|
14
17
|
transition: opacity var(--etui-transition-fast), transform var(--etui-transition-fast);
|
|
15
18
|
}
|
|
16
|
-
.
|
|
19
|
+
.Menu_menuContentStyle__1pkkb711[data-starting-style], .Menu_menuContentStyle__1pkkb711[data-ending-style] {
|
|
17
20
|
opacity: 0;
|
|
18
21
|
transform: scale(0.96);
|
|
19
22
|
}
|
|
20
|
-
.
|
|
23
|
+
.Menu_menuItemStyle__1pkkb712 {
|
|
21
24
|
display: flex;
|
|
22
25
|
align-items: center;
|
|
23
26
|
gap: var(--etui-spacing-sm);
|
|
@@ -33,15 +36,15 @@
|
|
|
33
36
|
font-size: var(--etui-font-size-md);
|
|
34
37
|
font-family: var(--etui-font-family-sans);
|
|
35
38
|
}
|
|
36
|
-
.
|
|
39
|
+
.Menu_menuItemStyle__1pkkb712[data-highlighted] {
|
|
37
40
|
background: var(--etui-color-surface-hover);
|
|
38
41
|
}
|
|
39
|
-
.
|
|
42
|
+
.Menu_menuItemStyle__1pkkb712[data-disabled] {
|
|
40
43
|
color: var(--etui-color-text-disabled);
|
|
41
44
|
cursor: not-allowed;
|
|
42
45
|
pointer-events: none;
|
|
43
46
|
}
|
|
44
|
-
.
|
|
47
|
+
.Menu_itemStartSlotStyle__1pkkb713 {
|
|
45
48
|
display: inline-flex;
|
|
46
49
|
align-items: center;
|
|
47
50
|
justify-content: center;
|
|
@@ -50,14 +53,14 @@
|
|
|
50
53
|
flex-shrink: 0;
|
|
51
54
|
color: var(--etui-color-text-secondary);
|
|
52
55
|
}
|
|
53
|
-
.
|
|
56
|
+
.Menu_itemLabelStyle__1pkkb714 {
|
|
54
57
|
flex: 1;
|
|
55
58
|
min-width: 0;
|
|
56
59
|
overflow: hidden;
|
|
57
60
|
text-overflow: ellipsis;
|
|
58
61
|
white-space: nowrap;
|
|
59
62
|
}
|
|
60
|
-
.
|
|
63
|
+
.Menu_itemEndSlotStyle__1pkkb715 {
|
|
61
64
|
display: inline-flex;
|
|
62
65
|
align-items: center;
|
|
63
66
|
gap: var(--etui-spacing-xs);
|
|
@@ -66,13 +69,13 @@
|
|
|
66
69
|
flex-shrink: 0;
|
|
67
70
|
color: var(--etui-color-text-muted);
|
|
68
71
|
}
|
|
69
|
-
.
|
|
72
|
+
.Menu_shortcutStyle__1pkkb716 {
|
|
70
73
|
font-size: var(--etui-font-size-xs);
|
|
71
74
|
color: var(--etui-color-text-muted);
|
|
72
75
|
letter-spacing: 0.03em;
|
|
73
76
|
white-space: nowrap;
|
|
74
77
|
}
|
|
75
|
-
.
|
|
78
|
+
.Menu_groupLabelStyle__1pkkb717 {
|
|
76
79
|
display: block;
|
|
77
80
|
padding: var(--etui-spacing-xs) var(--etui-spacing-sm);
|
|
78
81
|
font-size: var(--etui-font-size-xs);
|
|
@@ -81,7 +84,7 @@
|
|
|
81
84
|
font-family: var(--etui-font-family-sans);
|
|
82
85
|
color: var(--etui-color-text-muted);
|
|
83
86
|
}
|
|
84
|
-
.
|
|
87
|
+
.Menu_separatorStyle__1pkkb718 {
|
|
85
88
|
margin: var(--etui-spacing-xs) 0;
|
|
86
89
|
border-top: 1px solid var(--etui-color-border-default);
|
|
87
90
|
height: 0;
|
|
@@ -24,7 +24,10 @@
|
|
|
24
24
|
opacity: 0;
|
|
25
25
|
transform: scale(0.96);
|
|
26
26
|
}
|
|
27
|
-
.
|
|
27
|
+
.Tooltip_tooltipPositionerStyle__u81kis1 {
|
|
28
|
+
z-index: var(--etui-z-tooltip);
|
|
29
|
+
}
|
|
30
|
+
.Tooltip_tooltipTriggerStyle__u81kis2 {
|
|
28
31
|
display: inline-block;
|
|
29
32
|
cursor: pointer;
|
|
30
33
|
width: fit-content;
|
|
@@ -33,17 +36,17 @@
|
|
|
33
36
|
z-index: 1;
|
|
34
37
|
pointer-events: none;
|
|
35
38
|
}
|
|
36
|
-
.
|
|
39
|
+
.Tooltip_tooltipTriggerStyle__u81kis2:focus {
|
|
37
40
|
outline: none;
|
|
38
41
|
box-shadow: var(--etui-shadow-focus);
|
|
39
42
|
}
|
|
40
|
-
.
|
|
43
|
+
.Tooltip_tooltipTriggerStyle__u81kis2 > * {
|
|
41
44
|
pointer-events: auto;
|
|
42
45
|
}
|
|
43
|
-
.
|
|
46
|
+
.Tooltip_arrowFillStyle__u81kis3 {
|
|
44
47
|
fill: var(--etui-color-bg-elevated);
|
|
45
48
|
}
|
|
46
|
-
.
|
|
49
|
+
.Tooltip_tooltipArrowStyle__u81kis4 {
|
|
47
50
|
display: flex;
|
|
48
51
|
transform-style: preserve-3d;
|
|
49
52
|
backface-visibility: hidden;
|
|
@@ -53,19 +56,19 @@
|
|
|
53
56
|
-moz-osx-font-smoothing: grayscale;
|
|
54
57
|
will-change: transform;
|
|
55
58
|
}
|
|
56
|
-
.
|
|
59
|
+
.Tooltip_tooltipArrowStyle__u81kis4[data-side="top"] {
|
|
57
60
|
bottom: -8px;
|
|
58
61
|
rotate: 180deg;
|
|
59
62
|
}
|
|
60
|
-
.
|
|
63
|
+
.Tooltip_tooltipArrowStyle__u81kis4[data-side="bottom"] {
|
|
61
64
|
top: -8px;
|
|
62
65
|
rotate: 0deg;
|
|
63
66
|
}
|
|
64
|
-
.
|
|
67
|
+
.Tooltip_tooltipArrowStyle__u81kis4[data-side="left"] {
|
|
65
68
|
right: -13px;
|
|
66
69
|
rotate: 90deg;
|
|
67
70
|
}
|
|
68
|
-
.
|
|
71
|
+
.Tooltip_tooltipArrowStyle__u81kis4[data-side="right"] {
|
|
69
72
|
left: -13px;
|
|
70
73
|
rotate: -90deg;
|
|
71
74
|
}
|
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
padding: 0 var(--etui-spacing-sm);
|
|
9
9
|
user-select: none;
|
|
10
10
|
flex-shrink: 0;
|
|
11
|
+
width: 100%;
|
|
11
12
|
}
|
|
12
13
|
.MenuBar_menuBarRoot_size_sm__1h81mxv1 {
|
|
13
14
|
height: 24px;
|
|
@@ -17,13 +18,15 @@
|
|
|
17
18
|
}
|
|
18
19
|
.MenuBar_menuContainer__1h81mxv3 {
|
|
19
20
|
position: relative;
|
|
21
|
+
display: flex;
|
|
22
|
+
align-items: center;
|
|
20
23
|
height: 100%;
|
|
21
24
|
}
|
|
22
25
|
.MenuBar_trigger__1h81mxv4 {
|
|
23
26
|
display: inline-flex;
|
|
24
27
|
align-items: center;
|
|
25
|
-
|
|
26
|
-
|
|
28
|
+
padding: var(--etui-spacing-xs) var(--etui-spacing-md);
|
|
29
|
+
border-radius: var(--etui-radius-sm);
|
|
27
30
|
border: none;
|
|
28
31
|
color: inherit;
|
|
29
32
|
font: inherit;
|
|
@@ -95,15 +98,24 @@
|
|
|
95
98
|
color: var(--etui-shell-menubar-shortcut-text);
|
|
96
99
|
font-size: var(--etui-font-size-xs);
|
|
97
100
|
}
|
|
98
|
-
.
|
|
101
|
+
.MenuBar_indicatorSlot__1h81mxva {
|
|
102
|
+
display: inline-flex;
|
|
103
|
+
align-items: center;
|
|
104
|
+
justify-content: center;
|
|
105
|
+
width: 16px;
|
|
106
|
+
height: 16px;
|
|
107
|
+
flex-shrink: 0;
|
|
108
|
+
color: var(--etui-color-text-secondary);
|
|
109
|
+
}
|
|
110
|
+
.MenuBar_separator__1h81mxvb {
|
|
99
111
|
height: 1px;
|
|
100
112
|
margin: var(--etui-spacing-xs) 0;
|
|
101
113
|
background: var(--etui-color-border-default);
|
|
102
114
|
}
|
|
103
|
-
.
|
|
115
|
+
.MenuBar_subTrigger__1h81mxvc {
|
|
104
116
|
justify-content: space-between;
|
|
105
117
|
}
|
|
106
|
-
.
|
|
118
|
+
.MenuBar_subDropdown__1h81mxvd {
|
|
107
119
|
position: absolute;
|
|
108
120
|
top: calc(-1 * var(--etui-spacing-xs));
|
|
109
121
|
left: 100%;
|
|
@@ -115,6 +127,6 @@
|
|
|
115
127
|
padding: var(--etui-spacing-xs) 0;
|
|
116
128
|
z-index: calc(var(--etui-z-dropdown) + 1);
|
|
117
129
|
}
|
|
118
|
-
.
|
|
130
|
+
.MenuBar_subContainer__1h81mxve {
|
|
119
131
|
position: relative;
|
|
120
132
|
}
|
|
@@ -1,17 +1,16 @@
|
|
|
1
|
-
import './../../../assets/src/components/controls/Slider/Slider.css.ts.vanilla-
|
|
1
|
+
import './../../../assets/src/components/controls/Slider/Slider.css.ts.vanilla-CLf_RC0A.css';
|
|
2
2
|
import { createRuntimeFn } from '@vanilla-extract/recipes/createRuntimeFn';
|
|
3
3
|
|
|
4
4
|
var fillPercentageVar = 'var(--fillPercentageVar__t8kxxs0)';
|
|
5
|
-
var fillRecipe = createRuntimeFn({defaultClassName:'
|
|
6
|
-
var sliderContainerRecipe = createRuntimeFn({defaultClassName:'
|
|
7
|
-
var
|
|
5
|
+
var fillRecipe = createRuntimeFn({defaultClassName:'Slider_fillRecipe__t8kxxsc',variantClassNames:{error:{true:'Slider_fillRecipe_error_true__t8kxxsd',false:'Slider_fillRecipe_error_false__t8kxxse'},isDragging:{true:'Slider_fillRecipe_isDragging_true__t8kxxsf',false:'Slider_fillRecipe_isDragging_false__t8kxxsg'}},defaultVariants:{error:false,isDragging:false},compoundVariants:[]});
|
|
6
|
+
var sliderContainerRecipe = createRuntimeFn({defaultClassName:'Slider_sliderContainerRecipe__t8kxxs2',variantClassNames:{disabled:{true:'Slider_sliderContainerRecipe_disabled_true__t8kxxs3',false:'Slider_sliderContainerRecipe_disabled_false__t8kxxs4'}},defaultVariants:{disabled:false},compoundVariants:[]});
|
|
7
|
+
var sliderTooltipRecipe = createRuntimeFn({defaultClassName:'Slider_sliderTooltipRecipe__t8kxxsr',variantClassNames:{placement:{top:'Slider_sliderTooltipRecipe_placement_top__t8kxxss',bottom:'Slider_sliderTooltipRecipe_placement_bottom__t8kxxst'}},defaultVariants:{placement:'top'},compoundVariants:[]});
|
|
8
|
+
var sliderWrapperStyle = 'Slider_sliderWrapperStyle__t8kxxs5';
|
|
8
9
|
var thumbPercentageVar = 'var(--thumbPercentageVar__t8kxxs1)';
|
|
9
|
-
var thumbRecipe = createRuntimeFn({defaultClassName:'
|
|
10
|
-
var tickStyle = '
|
|
11
|
-
var ticksStyle = '
|
|
12
|
-
var
|
|
13
|
-
var tooltipRecipe = createRuntimeFn({defaultClassName:'Slider_tooltipRecipe__t8kxxss',variantClassNames:{visible:{true:'Slider_tooltipRecipe_visible_true__t8kxxst',false:'Slider_tooltipRecipe_visible_false__t8kxxsu'}},defaultVariants:{visible:false},compoundVariants:[]});
|
|
14
|
-
var trackRecipe = createRuntimeFn({defaultClassName:'Slider_trackRecipe__t8kxxs7',variantClassNames:{size:{sm:'Slider_trackRecipe_size_sm__t8kxxs8',md:'Slider_trackRecipe_size_md__t8kxxs9',lg:'Slider_trackRecipe_size_lg__t8kxxsa'},error:{true:'Slider_trackRecipe_error_true__t8kxxsb',false:'Slider_trackRecipe_error_false__t8kxxsc'}},defaultVariants:{size:'md',error:false},compoundVariants:[]});
|
|
10
|
+
var thumbRecipe = createRuntimeFn({defaultClassName:'Slider_thumbRecipe__t8kxxsh',variantClassNames:{size:{sm:'Slider_thumbRecipe_size_sm__t8kxxsi',md:'Slider_thumbRecipe_size_md__t8kxxsj',lg:'Slider_thumbRecipe_size_lg__t8kxxsk'},error:{true:'Slider_thumbRecipe_error_true__t8kxxsl',false:'Slider_thumbRecipe_error_false__t8kxxsm'},isDragging:{true:'Slider_thumbRecipe_isDragging_true__t8kxxsn',false:'Slider_thumbRecipe_isDragging_false__t8kxxso'}},defaultVariants:{size:'md',error:false,isDragging:false},compoundVariants:[]});
|
|
11
|
+
var tickStyle = 'Slider_tickStyle__t8kxxsq';
|
|
12
|
+
var ticksStyle = 'Slider_ticksStyle__t8kxxsp';
|
|
13
|
+
var trackRecipe = createRuntimeFn({defaultClassName:'Slider_trackRecipe__t8kxxs6',variantClassNames:{size:{sm:'Slider_trackRecipe_size_sm__t8kxxs7',md:'Slider_trackRecipe_size_md__t8kxxs8',lg:'Slider_trackRecipe_size_lg__t8kxxs9'},error:{true:'Slider_trackRecipe_error_true__t8kxxsa',false:'Slider_trackRecipe_error_false__t8kxxsb'}},defaultVariants:{size:'md',error:false},compoundVariants:[]});
|
|
15
14
|
|
|
16
|
-
export { fillPercentageVar, fillRecipe, sliderContainerRecipe, sliderWrapperStyle, thumbPercentageVar, thumbRecipe, tickStyle, ticksStyle,
|
|
15
|
+
export { fillPercentageVar, fillRecipe, sliderContainerRecipe, sliderTooltipRecipe, sliderWrapperStyle, thumbPercentageVar, thumbRecipe, tickStyle, ticksStyle, trackRecipe };
|
|
17
16
|
//# sourceMappingURL=Slider.css.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Slider.css.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"Slider.css.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;"}
|
|
@@ -2,12 +2,13 @@
|
|
|
2
2
|
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
3
3
|
import { assignInlineVars } from '@vanilla-extract/dynamic';
|
|
4
4
|
import React, { useState, useRef, useCallback, useEffect } from 'react';
|
|
5
|
+
import { createPortal } from 'react-dom';
|
|
5
6
|
import { FormHelperText } from '../../form/FormHelperText.js';
|
|
6
7
|
import { FormLabel } from '../../form/FormLabel.js';
|
|
7
8
|
import { InputWrapper } from '../../form/InputWrapper.js';
|
|
8
9
|
import { useKeyboardContext } from '../../../context/KeyboardContext.js';
|
|
9
10
|
import { cx } from '../../../utils/cx.js';
|
|
10
|
-
import { sliderWrapperStyle, fillPercentageVar, fillRecipe, trackRecipe, thumbPercentageVar, thumbRecipe, ticksStyle, tickStyle,
|
|
11
|
+
import { sliderWrapperStyle, fillPercentageVar, fillRecipe, trackRecipe, thumbPercentageVar, thumbRecipe, ticksStyle, tickStyle, sliderTooltipRecipe, sliderContainerRecipe } from './Slider.css.js';
|
|
11
12
|
|
|
12
13
|
/**
|
|
13
14
|
* Clamps a value between min and max bounds
|
|
@@ -73,10 +74,13 @@ function roundToPrecision(value, precision) {
|
|
|
73
74
|
* />
|
|
74
75
|
* ```
|
|
75
76
|
*/
|
|
76
|
-
const Slider = ({ value, onChange, min = 0, max = 100, step = 1, precisionStep, largeStep, precision = 2, size = 'md', disabled = false, readOnly = false, label, helperText, errorMessage, error = false, required = false, unit, formatValue, showTooltip = true, showTicks = false, tickCount = 5, className, testId, onFocus, onBlur, onKeyDown, ref, ...props }) => {
|
|
77
|
+
const Slider = ({ value, onChange, min = 0, max = 100, step = 1, precisionStep, largeStep, precision = 2, size = 'md', disabled = false, readOnly = false, label, helperText, errorMessage, error = false, required = false, unit, formatValue, showTooltip = true, tooltipPlacement = 'top', showTicks = false, tickCount = 5, className, testId, onFocus, onBlur, onKeyDown, ref, ...props }) => {
|
|
77
78
|
const [isDragging, setIsDragging] = useState(false);
|
|
78
79
|
const [isFocused, setIsFocused] = useState(false);
|
|
79
80
|
const [showTooltipState, setShowTooltipState] = useState(false);
|
|
81
|
+
// Viewport coordinates of the portaled value tooltip (null until a drag
|
|
82
|
+
// starts). Updated only while dragging so the portal stays off the idle path.
|
|
83
|
+
const [tooltipPos, setTooltipPos] = useState(null);
|
|
80
84
|
const sliderRef = useRef(null);
|
|
81
85
|
const trackRef = useRef(null);
|
|
82
86
|
const dragStartRef = useRef(null);
|
|
@@ -135,6 +139,22 @@ const Slider = ({ value, onChange, min = 0, max = 100, step = 1, precisionStep,
|
|
|
135
139
|
const steps = Math.round((newValue - min) / currentStep);
|
|
136
140
|
return min + steps * currentStep;
|
|
137
141
|
}, [min, max, value, getStepSize]);
|
|
142
|
+
/**
|
|
143
|
+
* Computes the portaled tooltip's viewport position for a (snapped) value,
|
|
144
|
+
* anchored to the thumb. Reads the same track rect the drag math already
|
|
145
|
+
* reads, so it adds no extra layout pass per frame.
|
|
146
|
+
*/
|
|
147
|
+
const updateTooltipPos = useCallback((v) => {
|
|
148
|
+
const track = trackRef.current;
|
|
149
|
+
if (!track)
|
|
150
|
+
return;
|
|
151
|
+
const rect = track.getBoundingClientRect();
|
|
152
|
+
const pct = clamp((v - min) / (max - min), 0, 1);
|
|
153
|
+
setTooltipPos({
|
|
154
|
+
left: rect.left + pct * rect.width,
|
|
155
|
+
top: tooltipPlacement === 'bottom' ? rect.bottom : rect.top,
|
|
156
|
+
});
|
|
157
|
+
}, [min, max, tooltipPlacement]);
|
|
138
158
|
/**
|
|
139
159
|
* Handle mouse down on track or thumb
|
|
140
160
|
*/
|
|
@@ -147,11 +167,20 @@ const Slider = ({ value, onChange, min = 0, max = 100, step = 1, precisionStep,
|
|
|
147
167
|
// Use the current step size (depends on keyboard modifiers)
|
|
148
168
|
const newValue = positionToValue(event.clientX);
|
|
149
169
|
applyValue(newValue);
|
|
170
|
+
if (showTooltip)
|
|
171
|
+
updateTooltipPos(newValue);
|
|
150
172
|
dragStartRef.current = {
|
|
151
173
|
startX: event.clientX,
|
|
152
174
|
startValue: newValue,
|
|
153
175
|
};
|
|
154
|
-
}, [
|
|
176
|
+
}, [
|
|
177
|
+
disabled,
|
|
178
|
+
readOnly,
|
|
179
|
+
positionToValue,
|
|
180
|
+
applyValue,
|
|
181
|
+
showTooltip,
|
|
182
|
+
updateTooltipPos,
|
|
183
|
+
]);
|
|
155
184
|
/**
|
|
156
185
|
* Handle global mouse move during drag
|
|
157
186
|
*/
|
|
@@ -163,8 +192,10 @@ const Slider = ({ value, onChange, min = 0, max = 100, step = 1, precisionStep,
|
|
|
163
192
|
// Use the current step size (depends on keyboard modifiers)
|
|
164
193
|
const newValue = positionToValue(event.clientX);
|
|
165
194
|
applyValue(newValue);
|
|
195
|
+
if (showTooltip)
|
|
196
|
+
updateTooltipPos(newValue);
|
|
166
197
|
});
|
|
167
|
-
}, [isDragging, positionToValue, applyValue]);
|
|
198
|
+
}, [isDragging, positionToValue, applyValue, showTooltip, updateTooltipPos]);
|
|
168
199
|
/**
|
|
169
200
|
* Handle global mouse up to end drag
|
|
170
201
|
*/
|
|
@@ -254,9 +285,11 @@ const Slider = ({ value, onChange, min = 0, max = 100, step = 1, precisionStep,
|
|
|
254
285
|
[fillPercentageVar]: `${percentage}%`,
|
|
255
286
|
}) }) }), jsx("div", { className: thumbRecipe({ size, error, isDragging }), style: assignInlineVars({
|
|
256
287
|
[thumbPercentageVar]: `${percentage}%`,
|
|
257
|
-
}) }), showTicks && (jsx("div", { className: ticksStyle, children: ticks.map(i => (jsx("div", { className: tickStyle }, i))) })), showTooltip &&
|
|
258
|
-
|
|
259
|
-
|
|
288
|
+
}) }), showTicks && (jsx("div", { className: ticksStyle, children: ticks.map(i => (jsx("div", { className: tickStyle }, i))) })), showTooltip &&
|
|
289
|
+
showTooltipState &&
|
|
290
|
+
tooltipPos &&
|
|
291
|
+
typeof document !== 'undefined' &&
|
|
292
|
+
createPortal(jsx("div", { className: sliderTooltipRecipe({ placement: tooltipPlacement }), style: { left: tooltipPos.left, top: tooltipPos.top }, role: "presentation", "data-testid": testId ? `${testId}-tooltip` : undefined, children: displayValue }), document.body)] }) }), (helperText ?? (error && errorMessage)) && (jsx(FormHelperText, { error: error, children: error && errorMessage ? errorMessage : helperText }))] }));
|
|
260
293
|
};
|
|
261
294
|
Slider.displayName = 'Slider';
|
|
262
295
|
|