@crewlethq/ui 0.21.0 → 0.22.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -203,6 +203,18 @@ places:
203
203
  - A surface that pans or zooms dispatches `LAYER_REPOSITION_EVENT` on its host
204
204
  when the content beneath it moves, and every panel anchored inside follows.
205
205
 
206
+ ## Changes in 0.22.0
207
+
208
+ **`Menu` takes `width`** (`'content'`, the default, or `'trigger'`). `'trigger'` keeps the panel no narrower than its trigger, so a trigger that spans a column opens a menu that covers it edge to edge, and still lets it grow past the trigger when a row needs the room.
209
+
210
+ **`Menu` takes `trailingIcon`**, a glyph after a text trigger's words, such as a picker's chevron. It is drawn as the button's trailing icon, a gap away from the words, where a glyph written into `trigger` sat flush against them.
211
+
212
+ **`Menu` reads more easily.** A header's name and value share one line (`Access … Admin`), and a row's description is one type step under its label rather than two.
213
+
214
+ **`AppShell.AccountRow`'s menu covers the row.** Pressing who you are opens a menu at least as wide as the row itself.
215
+
216
+ What to change: nothing.
217
+
206
218
  ## Changes in 0.21.0
207
219
 
208
220
  **`AppShell.AccountRow` takes `menu`** (`AccountRowMenu`: `label`, `header`, `items`): pressing who you are opens the reader's own menu instead of linking anywhere, which is where a reader looks for their account and for signing out. The row becomes the menu button, ending in the up-and-down chevron a menu's trigger draws, keeps the account page's current-row lift (`data-current`), and the menu's header holds the facts the row does not already say, such as the reader's access. Given, `menu` takes the place of `href`.
@@ -1,6 +1,6 @@
1
- export { AccountRow, AppShell, AppShellRail, AppShellRailRow, AppShellToggle, AppShellTopbar, useAppShell } from '../chunk-G5TAKMEA.js';
1
+ export { AccountRow, AppShell, AppShellRail, AppShellRailRow, AppShellToggle, AppShellTopbar, useAppShell } from '../chunk-BFQK7CYJ.js';
2
2
  import '../chunk-IG75YMUN.js';
3
- import '../chunk-4MIM356A.js';
3
+ import '../chunk-UFKUWVMV.js';
4
4
  import '../chunk-OG6CL3EB.js';
5
5
  import '../chunk-HMPFGIWM.js';
6
6
  import '../chunk-R25RGPUB.js';
@@ -1,4 +1,4 @@
1
- export { ALL_ITEMS, CopyableCell, DATA_TABLE_LABELS, DataTable, RowActionsMenu } from '../chunk-LG244LY7.js';
1
+ export { ALL_ITEMS, CopyableCell, DATA_TABLE_LABELS, DataTable, RowActionsMenu } from '../chunk-BXSGT3YC.js';
2
2
  import '../chunk-STJ7QBC3.js';
3
3
  import '../chunk-DTIW4CHZ.js';
4
4
  import '../chunk-F4DPAJCN.js';
@@ -7,7 +7,7 @@ import '../chunk-Q55TXPA3.js';
7
7
  import '../chunk-EUCC37WY.js';
8
8
  import '../chunk-AV2DXAEL.js';
9
9
  import '../chunk-PQADV6P6.js';
10
- import '../chunk-4MIM356A.js';
10
+ import '../chunk-UFKUWVMV.js';
11
11
  import '../chunk-OG6CL3EB.js';
12
12
  import '../chunk-HMPFGIWM.js';
13
13
  import '../chunk-R25RGPUB.js';
@@ -1,8 +1,8 @@
1
- export { DATA_VIEW_TOOLBAR_LABELS, DataView, DataViewToolbar, FILTER_AXIS_LABELS, FilterAxisBar, FilterAxisChip, applyColumnFilters, applyFilters, blankFilterValue, defaultOperator, filterDefsFromColumns, filterHasValue, filterPredicate, formatFilterValue, operatorOf, tableColumns } from '../chunk-AV6YX4GZ.js';
1
+ export { DATA_VIEW_TOOLBAR_LABELS, DataView, DataViewToolbar, FILTER_AXIS_LABELS, FilterAxisBar, FilterAxisChip, applyColumnFilters, applyFilters, blankFilterValue, defaultOperator, filterDefsFromColumns, filterHasValue, filterPredicate, formatFilterValue, operatorOf, tableColumns } from '../chunk-KYEXTEJ3.js';
2
2
  import '../chunk-HOXGBLEY.js';
3
3
  import '../chunk-PGRPNDWM.js';
4
4
  import '../chunk-RE6ED5TO.js';
5
- import '../chunk-LG244LY7.js';
5
+ import '../chunk-BXSGT3YC.js';
6
6
  import '../chunk-STJ7QBC3.js';
7
7
  import '../chunk-DTIW4CHZ.js';
8
8
  import '../chunk-F4DPAJCN.js';
@@ -17,7 +17,7 @@ import '../chunk-BWRGFKJP.js';
17
17
  import '../chunk-AV2DXAEL.js';
18
18
  import '../chunk-PQADV6P6.js';
19
19
  import '../chunk-BHHIIK3M.js';
20
- import '../chunk-4MIM356A.js';
20
+ import '../chunk-UFKUWVMV.js';
21
21
  import '../chunk-OG6CL3EB.js';
22
22
  import '../chunk-HMPFGIWM.js';
23
23
  import '../chunk-R25RGPUB.js';
@@ -1,6 +1,6 @@
1
- export { LinkInterstitial, openExternal } from '../chunk-ZM7HLFOA.js';
2
- import '../chunk-5CLW2CXT.js';
1
+ export { LinkInterstitial, openExternal } from '../chunk-L2OQRPXJ.js';
3
2
  import '../chunk-F4DPAJCN.js';
3
+ import '../chunk-5CLW2CXT.js';
4
4
  import '../chunk-SVSCLHHI.js';
5
5
  import '../chunk-PQADV6P6.js';
6
6
  import '../chunk-OG6CL3EB.js';
@@ -58,6 +58,11 @@
58
58
  * menu itself rather than sitting beside a second button that does. The
59
59
  * caller spreads the props it is handed on its element, which keeps every
60
60
  * rule above, the focus coming back included.
61
+ * - IT CAN BE NO NARROWER THAN ITS TRIGGER (`width="trigger"`): a trigger
62
+ * that spans a column, such as the signed-in reader at the foot of the
63
+ * rail, opens a panel that covers it edge to edge, and that still grows
64
+ * past it when a row needs the room, so a description reads on one line
65
+ * rather than wrapping into a column of short lines.
61
66
  * - A HEADER SAYS WHAT THE ACTIONS ARE ABOUT (`header`): a line of facts
62
67
  * above the items, such as the access a signed-in reader carries. It is
63
68
  * not an item, so the arrows never stop on it, and the menu is described by
@@ -124,6 +129,12 @@ export interface MenuProps {
124
129
  icon?: ReactNode;
125
130
  /** Visible trigger text; without it the trigger is an icon button named by `label`. */
126
131
  trigger?: ReactNode;
132
+ /**
133
+ * A glyph after the trigger's text, such as the chevron of a picker. Drawn
134
+ * as the button's trailing icon, a gap away from the words; a glyph written
135
+ * into `trigger` instead sits flush against them. Read only with `trigger`.
136
+ */
137
+ trailingIcon?: ReactNode;
127
138
  triggerVariant?: ButtonVariant | undefined;
128
139
  /** -1 for a pointer-only trigger whose actions the keyboard reaches another way. */
129
140
  triggerTabIndex?: number | undefined;
@@ -131,6 +142,12 @@ export interface MenuProps {
131
142
  onOpenChange?: ((open: boolean) => void) | undefined;
132
143
  /** Which edge of the trigger the menu lines up with. */
133
144
  align?: 'start' | 'end' | undefined;
145
+ /**
146
+ * How wide the panel is: its longest row (`content`, the default), or its
147
+ * longest row but never narrower than its trigger (`trigger`), for a
148
+ * trigger that spans a column.
149
+ */
150
+ width?: 'content' | 'trigger' | undefined;
134
151
  /**
135
152
  * The caller's own trigger, in place of the menu's button: an element given
136
153
  * these props. `label` still names the menu; the trigger names itself.
@@ -140,5 +157,5 @@ export interface MenuProps {
140
157
  header?: ReactNode;
141
158
  className?: string | undefined;
142
159
  }
143
- export declare function Menu({ label, items, icon, trigger, triggerVariant, triggerTabIndex, open: controlled, onOpenChange, align, renderTrigger, header, className, }: MenuProps): import("react").JSX.Element;
160
+ export declare function Menu({ label, items, icon, trigger, trailingIcon, triggerVariant, triggerTabIndex, open: controlled, onOpenChange, align, width, renderTrigger, header, className, }: MenuProps): import("react").JSX.Element;
144
161
  export {};
@@ -1,4 +1,4 @@
1
- export { Menu } from '../chunk-4MIM356A.js';
1
+ export { Menu } from '../chunk-UFKUWVMV.js';
2
2
  import '../chunk-OG6CL3EB.js';
3
3
  import '../chunk-HMPFGIWM.js';
4
4
  import '../chunk-R25RGPUB.js';
@@ -34,9 +34,15 @@
34
34
  * however long that label was and the 320px was a number nothing read. A
35
35
  * width is clamped by the ceiling, and the label that no longer fits is the
36
36
  * one that truncates.
37
+ *
38
+ * A FLOOR, when the trigger sets one (`width="trigger"`, which writes
39
+ * --crewlet-menu-floor): the panel is never narrower than a trigger that
40
+ * spans a column. The ceiling is lifted to meet it, so the two never cross
41
+ * and the rule above still holds.
37
42
  */
38
43
  width: max-content;
39
- max-width: 320px;
44
+ min-width: var(--crewlet-menu-floor, 0px);
45
+ max-width: max(320px, var(--crewlet-menu-floor, 0px));
40
46
  max-height: min(360px, 60vh);
41
47
  overflow-y: auto;
42
48
  overscroll-behavior: contain;
@@ -193,6 +199,7 @@
193
199
  .crewlet-menu__text {
194
200
  display: flex;
195
201
  flex-direction: column;
202
+ gap: calc(var(--spacing-1) / 2);
196
203
  min-width: 0;
197
204
  }
198
205
 
@@ -202,9 +209,14 @@
202
209
  white-space: nowrap;
203
210
  }
204
211
 
212
+ /*
213
+ * ONE STEP UNDER THE LABEL, not two. At 11px under a 13px label the second
214
+ * line read as fine print; at 12px in the tertiary ink it is still plainly the
215
+ * lesser line, and it is legible at a glance.
216
+ */
205
217
  .crewlet-menu__description {
206
218
  color: var(--color-text-tertiary);
207
- font-size: var(--font-size-2xs);
219
+ font-size: var(--font-size-xs);
208
220
  white-space: normal;
209
221
  }
210
222
 
@@ -222,11 +234,17 @@
222
234
  /*
223
235
  * Facts above the items, across the panel's full width with a hairline under
224
236
  * them: what the actions below are about, read rather than pressed.
237
+ *
238
+ * A NAME AND ITS VALUE SHARE ONE LINE, the name at the start and the value at
239
+ * the end, as a property reads ("Access … Admin"). Stacked, the pair spent two
240
+ * lines on one fact. A value too long for the line wraps beneath its name.
225
241
  */
226
242
  .crewlet-menu__header {
227
243
  display: flex;
228
- flex-direction: column;
229
- gap: var(--spacing-1);
244
+ flex-wrap: wrap;
245
+ align-items: center;
246
+ justify-content: space-between;
247
+ gap: var(--spacing-1) var(--spacing-2);
230
248
  margin: calc(var(--spacing-1) * -1) calc(var(--spacing-1) * -1) var(--spacing-1);
231
249
  padding: var(--spacing-2) var(--spacing-3);
232
250
  border-bottom: 1px solid var(--color-border-default);
@@ -1,5 +1,5 @@
1
1
  import { useMediaMatch } from './chunk-IG75YMUN.js';
2
- import { Menu } from './chunk-4MIM356A.js';
2
+ import { Menu } from './chunk-UFKUWVMV.js';
3
3
  import { useModalLayer, focusables } from './chunk-R25RGPUB.js';
4
4
  import { IconButton } from './chunk-4FQT6ZAY.js';
5
5
  import { VisuallyHidden } from './chunk-BZFWDIV6.js';
@@ -40,6 +40,7 @@ function AccountRow({
40
40
  label: menu.label ?? "Your account",
41
41
  items: menu.items,
42
42
  header: menu.header,
43
+ width: "trigger",
43
44
  renderTrigger: (trigger) => /* @__PURE__ */ jsxs(
44
45
  "button",
45
46
  {
@@ -3,7 +3,7 @@ import { Modal } from './chunk-F4DPAJCN.js';
3
3
  import { Checkbox } from './chunk-I6NZKJGK.js';
4
4
  import { EmptyValue } from './chunk-EUCC37WY.js';
5
5
  import { useCardHeaderSlot } from './chunk-AV2DXAEL.js';
6
- import { Menu } from './chunk-4MIM356A.js';
6
+ import { Menu } from './chunk-UFKUWVMV.js';
7
7
  import { Button } from './chunk-OG6CL3EB.js';
8
8
  import { IconButton } from './chunk-4FQT6ZAY.js';
9
9
  import { VisuallyHidden } from './chunk-BZFWDIV6.js';
@@ -1,14 +1,14 @@
1
1
  import { PageHeader } from './chunk-HOXGBLEY.js';
2
2
  import { Toolbar } from './chunk-PGRPNDWM.js';
3
3
  import { DateTimePicker } from './chunk-RE6ED5TO.js';
4
- import { DataTable } from './chunk-LG244LY7.js';
4
+ import { DataTable } from './chunk-BXSGT3YC.js';
5
5
  import { useListbox, useOptionKeys } from './chunk-F73MC7EZ.js';
6
6
  import { Kbd } from './chunk-SMBKXWML.js';
7
7
  import { Input } from './chunk-Q55TXPA3.js';
8
8
  import { RelativeTime } from './chunk-3CZ7XAVY.js';
9
9
  import { Popover } from './chunk-BWRGFKJP.js';
10
10
  import { Count } from './chunk-BHHIIK3M.js';
11
- import { Menu } from './chunk-4MIM356A.js';
11
+ import { Menu } from './chunk-UFKUWVMV.js';
12
12
  import { Button } from './chunk-OG6CL3EB.js';
13
13
  import { IconButton } from './chunk-4FQT6ZAY.js';
14
14
  import { VisuallyHidden } from './chunk-BZFWDIV6.js';
@@ -3,7 +3,7 @@ import { useLayerContainer, viewportBounds, LAYER_GAP, outsideBounds, placePopup
3
3
  import { usePopupLayer } from './chunk-R25RGPUB.js';
4
4
  import { IconButton } from './chunk-4FQT6ZAY.js';
5
5
  import { cx } from './chunk-ODEQTPFM.js';
6
- import './Menu-XIJ4LQUT.css';
6
+ import './Menu-KEKAD3BZ.css';
7
7
  import { useId, useState, useRef, useCallback, useLayoutEffect, useEffect } from 'react';
8
8
  import { createPortal } from 'react-dom';
9
9
  import { EllipsisVerticalGlyph, CheckGlyph } from '@crewlethq/icons/glyphs';
@@ -29,11 +29,13 @@ function Menu({
29
29
  items,
30
30
  icon,
31
31
  trigger,
32
+ trailingIcon,
32
33
  triggerVariant = "ghost",
33
34
  triggerTabIndex,
34
35
  open: controlled,
35
36
  onOpenChange,
36
37
  align = "start",
38
+ width = "content",
37
39
  renderTrigger,
38
40
  header,
39
41
  className
@@ -88,7 +90,9 @@ function Menu({
88
90
  const inHost = container !== document.body;
89
91
  const host = inHost ? container.getBoundingClientRect() : viewportBounds();
90
92
  const rect = at.getBoundingClientRect();
91
- const own = box.getBoundingClientRect();
93
+ const measured = box.getBoundingClientRect();
94
+ const floor = width === "trigger" ? rect.width : void 0;
95
+ const own = { width: Math.max(measured.width, floor ?? 0), height: measured.height };
92
96
  const local = {
93
97
  x: (align === "end" ? rect.right - own.width : rect.left) - (inHost ? host.x : 0),
94
98
  y: rect.top - (inHost ? host.y : 0),
@@ -107,8 +111,10 @@ function Menu({
107
111
  return;
108
112
  }
109
113
  const spot = placePopup(local, { width: own.width, height: own.height }, bounds, LAYER_GAP);
110
- setPlace((was) => was && was.left === spot.left && was.top === spot.top ? was : { left: spot.left, top: spot.top });
111
- }, [align, close, container]);
114
+ setPlace(
115
+ (was) => was && was.left === spot.left && was.top === spot.top && was.floor === floor ? was : { left: spot.left, top: spot.top, floor }
116
+ );
117
+ }, [align, close, container, width]);
112
118
  useLayoutEffect(() => {
113
119
  if (!open) return;
114
120
  position();
@@ -233,7 +239,12 @@ function Menu({
233
239
  menu.current = el;
234
240
  popup.panelRef(el);
235
241
  },
236
- style: place ? { left: place.left, top: place.top, zIndex: popup.zIndex } : { visibility: "hidden" },
242
+ style: place ? {
243
+ left: place.left,
244
+ top: place.top,
245
+ zIndex: popup.zIndex,
246
+ ...place.floor === void 0 ? null : { "--crewlet-menu-floor": `${place.floor}px` }
247
+ } : { visibility: "hidden" },
237
248
  onKeyDown: onMenuKeyDown,
238
249
  onPointerDown: (event) => event.stopPropagation(),
239
250
  onClick: (event) => event.stopPropagation(),
@@ -269,7 +280,7 @@ function Menu({
269
280
  onKeyDown: onTriggerKeyDown
270
281
  };
271
282
  return /* @__PURE__ */ jsxs("span", { className: "crewlet-menu-anchor", children: [
272
- renderTrigger ? renderTrigger(shared) : trigger === void 0 ? /* @__PURE__ */ jsx(IconButton, { ...shared, label, icon: icon ?? /* @__PURE__ */ jsx(EllipsisVerticalGlyph, {}), size: "sm" }) : /* @__PURE__ */ jsx(Button, { ...shared, variant: triggerVariant, size: "small", leadingIcon: icon, children: trigger }),
283
+ renderTrigger ? renderTrigger(shared) : trigger === void 0 ? /* @__PURE__ */ jsx(IconButton, { ...shared, label, icon: icon ?? /* @__PURE__ */ jsx(EllipsisVerticalGlyph, {}), size: "sm" }) : /* @__PURE__ */ jsx(Button, { ...shared, variant: triggerVariant, size: "small", leadingIcon: icon, trailingIcon, children: trigger }),
273
284
  list && container ? createPortal(list, container) : null
274
285
  ] });
275
286
  }
@@ -9,10 +9,10 @@ export { applyStoredPreferences, resolveTheme, useDensityPreference, useSystemTh
9
9
  export { DEFAULT_TIME_WINDOW_LABELS, TIME_WINDOW_SPANS, TimeWindowPicker, describeTimeWindow, isTimeWindowSet, parseTimeWindowDuration, resolveTimeWindow, timeWindowMatchesPreset } from '../chunk-NUZC6PJX.js';
10
10
  export { Timeline, TimelineItem } from '../chunk-AUQPBL4O.js';
11
11
  export { ToastProvider, Toaster, useToast } from '../chunk-QH3AKP2N.js';
12
+ export { Table } from '../chunk-V2N3BMOT.js';
12
13
  export { TABLE_TAGS_CELL_LABELS, TableDateCell, TableEntityCell, TableKeyCell, TableNumberCell, TableStatusCell, TableTagsCell, TableTextCell } from '../chunk-MUGM7SEG.js';
13
14
  export { TagGroup } from '../chunk-E6UWRXNM.js';
14
15
  export { TagsInput } from '../chunk-7ZNKEPLN.js';
15
- export { Table } from '../chunk-V2N3BMOT.js';
16
16
  export { Text } from '../chunk-IKBK4A5O.js';
17
17
  export { ThemeGallery } from '../chunk-KLIEPFEZ.js';
18
18
  export { ThemeSwatch } from '../chunk-MNFU2RNT.js';
@@ -28,8 +28,9 @@ export { Select } from '../chunk-FC4YTTFJ.js';
28
28
  export { CellDisplay, CellEditor, CheckboxCell, DateCell, LongTextCell, MultiSelectCell, NumberCell, PersonCell, RatingCell, SelectCell, SheetCell, SheetGrid, StatusCell, TextCell, UrlCell } from '../chunk-36CWC2NH.js';
29
29
  export { matchesShortcut, useShortcut } from '../chunk-2FPENTCF.js';
30
30
  export { Prose } from '../chunk-JCSA3XVH.js';
31
- export { ReadingPane, ReadingPaneByline, ReadingPaneLead, ReadingPaneOutcome, ReadingPaneQuote, ReadingPaneReasoning, ReadingPaneSection, ReadingPaneTitle } from '../chunk-ZAJHGDAW.js';
31
+ export { PrincipalPicker } from '../chunk-JEDWC3GI.js';
32
32
  export { QR_DARK, QR_LIGHT, QR_QUIET_ZONE, QrCode, qrModulePath, qrModules } from '../chunk-Y56FM3K4.js';
33
+ export { ReadingPane, ReadingPaneByline, ReadingPaneLead, ReadingPaneOutcome, ReadingPaneQuote, ReadingPaneReasoning, ReadingPaneSection, ReadingPaneTitle } from '../chunk-ZAJHGDAW.js';
33
34
  export { FRAME_HELLO_TIMEOUT_MS, SandboxedFrame } from '../chunk-VYDFB6PJ.js';
34
35
  export { Skeleton } from '../chunk-W5J7R5EB.js';
35
36
  export { SearchTrigger } from '../chunk-6DRDCT22.js';
@@ -40,7 +41,6 @@ import '../chunk-CENOOTAV.js';
40
41
  export { PricingCard } from '../chunk-DQSXWQMJ.js';
41
42
  export { Tag } from '../chunk-GFV4LJHH.js';
42
43
  export { StatusDot } from '../chunk-WIATRXEJ.js';
43
- export { PrincipalPicker } from '../chunk-JEDWC3GI.js';
44
44
  export { NewItemsNotice } from '../chunk-PXU6HOZB.js';
45
45
  export { Note } from '../chunk-63WJLRB2.js';
46
46
  export { FactLine, ObjectHeader, SetByLine } from '../chunk-I7WXZOWA.js';
@@ -58,7 +58,7 @@ import '../chunk-VYY56AMX.js';
58
58
  export { DEFAULT_METER_THRESHOLDS, METER_STATES, Meter, meterState, meterStateTone, meterTone, progressTone } from '../chunk-4PZ6FJKW.js';
59
59
  export { AutoGrid, Inline, Spacer, Stack } from '../chunk-ZAC7SKUN.js';
60
60
  export { Link } from '../chunk-FBSEJO2C.js';
61
- export { LinkInterstitial, openExternal } from '../chunk-ZM7HLFOA.js';
61
+ export { LinkInterstitial, openExternal } from '../chunk-L2OQRPXJ.js';
62
62
  export { DEFAULT_FRAME_THEME, EXTERNAL_URL_MAX, FRAME_BRIDGE, FRAME_MESSAGE, FRAME_ORIGIN_MODES, FRAME_SANDBOX_TOKENS, applyFrameTheme, checkFrameSandbox, externalUrl, frameFragment, frameOriginMatches, frameThemeMessage, httpOrigin, isFocusExit, isFrameNonce, negotiateBridge, parseFrameFragment, portTargetOrigin, readFrameHello, readFramePortMessage, readFrameTheme, readOpenLink } from '../chunk-F6V2PTN6.js';
63
63
  export { DENSITY_PREFERENCES, PALETTE_ID, THEME_PREFERENCES, applyDensity, applyPalette, applyTheme, isDensityPreference, isPaletteId, isThemePreference } from '../chunk-ZXXDZJQN.js';
64
64
  export { useFullscreen } from '../chunk-XDTYBF2F.js';
@@ -80,19 +80,17 @@ export { Disclosure } from '../chunk-S4RCG44T.js';
80
80
  export { Divider } from '../chunk-6KWNXIDE.js';
81
81
  export { DownloadButton } from '../chunk-BJCFNRGH.js';
82
82
  export { downloadText, safeFilename, useDownload } from '../chunk-F6NZOVWL.js';
83
- export { ConfirmField, confirmMatches } from '../chunk-YSY6UJ4F.js';
84
- export { InlineCode } from '../chunk-5CLW2CXT.js';
85
83
  export { CONFLICT_NOTE_LABELS, ConflictNote } from '../chunk-UO7JZVCO.js';
86
84
  export { Container } from '../chunk-QVE4GJAT.js';
85
+ export { ChoiceList } from '../chunk-QBXZLGK2.js';
87
86
  export { CursorFlag } from '../chunk-3BYIWOTV.js';
88
87
  export { PresenceRing, presenceHueClass } from '../chunk-I6POAB4V.js';
89
- export { DATA_VIEW_TOOLBAR_LABELS, DataView, DataViewToolbar, FILTER_AXIS_LABELS, FilterAxisBar, FilterAxisChip, applyColumnFilters, applyFilters, blankFilterValue, defaultOperator, filterDefsFromColumns, filterHasValue, filterPredicate, formatFilterValue, operatorOf, tableColumns } from '../chunk-AV6YX4GZ.js';
88
+ export { DATA_VIEW_TOOLBAR_LABELS, DataView, DataViewToolbar, FILTER_AXIS_LABELS, FilterAxisBar, FilterAxisChip, applyColumnFilters, applyFilters, blankFilterValue, defaultOperator, filterDefsFromColumns, filterHasValue, filterPredicate, formatFilterValue, operatorOf, tableColumns } from '../chunk-KYEXTEJ3.js';
90
89
  export { PageHeader } from '../chunk-HOXGBLEY.js';
91
90
  export { Toolbar, ToolbarOverflow, ToolbarWide } from '../chunk-PGRPNDWM.js';
92
91
  export { DEFAULT_DATE_TIME_PICKER_LABELS, DateTimePicker } from '../chunk-RE6ED5TO.js';
93
- export { ALL_ITEMS, CopyableCell, DATA_TABLE_LABELS, DataTable, RowActionsMenu } from '../chunk-LG244LY7.js';
92
+ export { ALL_ITEMS, CopyableCell, DATA_TABLE_LABELS, DataTable, RowActionsMenu } from '../chunk-BXSGT3YC.js';
94
93
  export { ChoiceButtons } from '../chunk-YSJC7AZC.js';
95
- export { ChoiceList } from '../chunk-QBXZLGK2.js';
96
94
  export { CodeBlock } from '../chunk-GDDE4UM7.js';
97
95
  export { CopyButton, Copyable } from '../chunk-W46LPU4R.js';
98
96
  export { useClipboard, writeClipboard } from '../chunk-STJ7QBC3.js';
@@ -105,6 +103,8 @@ export { COMMENT_THREAD_LABELS, CommentThread } from '../chunk-IC64IWOO.js';
105
103
  export { Document, DocumentTitle } from '../chunk-WI6K5M5X.js';
106
104
  export { COMPOSER_COUNTER_AT, Composer } from '../chunk-VJLYGPPE.js';
107
105
  export { Kbd, isApplePlatform, keyGlyph } from '../chunk-SMBKXWML.js';
106
+ export { ConfirmField, confirmMatches } from '../chunk-YSY6UJ4F.js';
107
+ export { InlineCode } from '../chunk-5CLW2CXT.js';
108
108
  export { CalendarGrid, compareDays, daysInMonth, sameDay, shiftDay, shiftMonth, today } from '../chunk-GXQ3B46I.js';
109
109
  export { Callout } from '../chunk-SVSCLHHI.js';
110
110
  export { CANVAS_COMPOSE_CONTEXT, CANVAS_FIT_MAX_ZOOM, CANVAS_FIT_PADDING, CANVAS_FOCUS_CONTEXT, CANVAS_MAX_ZOOM, CANVAS_MIN_ZOOM, CANVAS_PAN_MARGIN, CANVAS_PAN_STEP, CANVAS_REVEAL_PADDING, CANVAS_TAP_SLOP, CANVAS_WHEEL_LINE_PX, CANVAS_WHEEL_ZOOM_PER_PIXEL, CANVAS_ZOOM_CEILING, CANVAS_ZOOM_LIMITS, CANVAS_ZOOM_STEP, Canvas, IDENTITY_VIEW, anchorView, beyondSlop, clampPan, clampZoom, fitView, panBy, pinchView, regionView, revealView, screenRect, toScreen, toWorld, wheelPixels, wheelZoomFactor, zoomAt, zoomLimits } from '../chunk-TXAFKH2A.js';
@@ -148,9 +148,9 @@ export { DisclosureAnatomy } from '../chunk-ENJUPIND.js';
148
148
  export { HeadingLevelProvider, headingTag, nextHeadingLevel, useHeadingLevel } from '../chunk-PQADV6P6.js';
149
149
  export { Count } from '../chunk-BHHIIK3M.js';
150
150
  export { ADD_PILL_MS, AddPill } from '../chunk-TROLVEZY.js';
151
- export { AccountRow, AppShell, AppShellRail, AppShellRailRow, AppShellToggle, AppShellTopbar, useAppShell } from '../chunk-G5TAKMEA.js';
151
+ export { AccountRow, AppShell, AppShellRail, AppShellRailRow, AppShellToggle, AppShellTopbar, useAppShell } from '../chunk-BFQK7CYJ.js';
152
152
  import '../chunk-IG75YMUN.js';
153
- export { Menu } from '../chunk-4MIM356A.js';
153
+ export { Menu } from '../chunk-UFKUWVMV.js';
154
154
  export { Button, ButtonLink } from '../chunk-OG6CL3EB.js';
155
155
  export { LAYER_GAP, LAYER_REPOSITION_EVENT, LayerHost, outsideBounds, placePopup, useLayerContainer, viewportBounds } from '../chunk-HMPFGIWM.js';
156
156
  export { focusables, isComposing, isModalLayerOpen, layerCount, useBodyScrollLock, useModalLayer, usePopupLayer } from '../chunk-R25RGPUB.js';
package/dist/index.js CHANGED
@@ -9,10 +9,10 @@ export { applyStoredPreferences, resolveTheme, useDensityPreference, useSystemTh
9
9
  export { DEFAULT_TIME_WINDOW_LABELS, TIME_WINDOW_SPANS, TimeWindowPicker, describeTimeWindow, isTimeWindowSet, parseTimeWindowDuration, resolveTimeWindow, timeWindowMatchesPreset } from './chunk-NUZC6PJX.js';
10
10
  export { Timeline, TimelineItem } from './chunk-AUQPBL4O.js';
11
11
  export { ToastProvider, Toaster, useToast } from './chunk-QH3AKP2N.js';
12
+ export { Table } from './chunk-V2N3BMOT.js';
12
13
  export { TABLE_TAGS_CELL_LABELS, TableDateCell, TableEntityCell, TableKeyCell, TableNumberCell, TableStatusCell, TableTagsCell, TableTextCell } from './chunk-MUGM7SEG.js';
13
14
  export { TagGroup } from './chunk-E6UWRXNM.js';
14
15
  export { TagsInput } from './chunk-7ZNKEPLN.js';
15
- export { Table } from './chunk-V2N3BMOT.js';
16
16
  export { Text } from './chunk-IKBK4A5O.js';
17
17
  export { ThemeGallery } from './chunk-KLIEPFEZ.js';
18
18
  export { ThemeSwatch } from './chunk-MNFU2RNT.js';
@@ -28,8 +28,9 @@ export { Select } from './chunk-FC4YTTFJ.js';
28
28
  export { CellDisplay, CellEditor, CheckboxCell, DateCell, LongTextCell, MultiSelectCell, NumberCell, PersonCell, RatingCell, SelectCell, SheetCell, SheetGrid, StatusCell, TextCell, UrlCell } from './chunk-36CWC2NH.js';
29
29
  export { matchesShortcut, useShortcut } from './chunk-2FPENTCF.js';
30
30
  export { Prose } from './chunk-JCSA3XVH.js';
31
- export { ReadingPane, ReadingPaneByline, ReadingPaneLead, ReadingPaneOutcome, ReadingPaneQuote, ReadingPaneReasoning, ReadingPaneSection, ReadingPaneTitle } from './chunk-ZAJHGDAW.js';
31
+ export { PrincipalPicker } from './chunk-JEDWC3GI.js';
32
32
  export { QR_DARK, QR_LIGHT, QR_QUIET_ZONE, QrCode, qrModulePath, qrModules } from './chunk-Y56FM3K4.js';
33
+ export { ReadingPane, ReadingPaneByline, ReadingPaneLead, ReadingPaneOutcome, ReadingPaneQuote, ReadingPaneReasoning, ReadingPaneSection, ReadingPaneTitle } from './chunk-ZAJHGDAW.js';
33
34
  export { FRAME_HELLO_TIMEOUT_MS, SandboxedFrame } from './chunk-VYDFB6PJ.js';
34
35
  export { Skeleton } from './chunk-W5J7R5EB.js';
35
36
  export { SearchTrigger } from './chunk-6DRDCT22.js';
@@ -40,7 +41,6 @@ import './chunk-CENOOTAV.js';
40
41
  export { PricingCard } from './chunk-DQSXWQMJ.js';
41
42
  export { Tag } from './chunk-GFV4LJHH.js';
42
43
  export { StatusDot } from './chunk-WIATRXEJ.js';
43
- export { PrincipalPicker } from './chunk-JEDWC3GI.js';
44
44
  export { NewItemsNotice } from './chunk-PXU6HOZB.js';
45
45
  export { Note } from './chunk-63WJLRB2.js';
46
46
  export { FactLine, ObjectHeader, SetByLine } from './chunk-I7WXZOWA.js';
@@ -58,7 +58,7 @@ import './chunk-VYY56AMX.js';
58
58
  export { DEFAULT_METER_THRESHOLDS, METER_STATES, Meter, meterState, meterStateTone, meterTone, progressTone } from './chunk-4PZ6FJKW.js';
59
59
  export { AutoGrid, Inline, Spacer, Stack } from './chunk-ZAC7SKUN.js';
60
60
  export { Link } from './chunk-FBSEJO2C.js';
61
- export { LinkInterstitial, openExternal } from './chunk-ZM7HLFOA.js';
61
+ export { LinkInterstitial, openExternal } from './chunk-L2OQRPXJ.js';
62
62
  export { DEFAULT_FRAME_THEME, EXTERNAL_URL_MAX, FRAME_BRIDGE, FRAME_MESSAGE, FRAME_ORIGIN_MODES, FRAME_SANDBOX_TOKENS, applyFrameTheme, checkFrameSandbox, externalUrl, frameFragment, frameOriginMatches, frameThemeMessage, httpOrigin, isFocusExit, isFrameNonce, negotiateBridge, parseFrameFragment, portTargetOrigin, readFrameHello, readFramePortMessage, readFrameTheme, readOpenLink } from './chunk-F6V2PTN6.js';
63
63
  export { DENSITY_PREFERENCES, PALETTE_ID, THEME_PREFERENCES, applyDensity, applyPalette, applyTheme, isDensityPreference, isPaletteId, isThemePreference } from './chunk-ZXXDZJQN.js';
64
64
  export { useFullscreen } from './chunk-XDTYBF2F.js';
@@ -80,19 +80,17 @@ export { Disclosure } from './chunk-S4RCG44T.js';
80
80
  export { Divider } from './chunk-6KWNXIDE.js';
81
81
  export { DownloadButton } from './chunk-BJCFNRGH.js';
82
82
  export { downloadText, safeFilename, useDownload } from './chunk-F6NZOVWL.js';
83
- export { ConfirmField, confirmMatches } from './chunk-YSY6UJ4F.js';
84
- export { InlineCode } from './chunk-5CLW2CXT.js';
85
83
  export { CONFLICT_NOTE_LABELS, ConflictNote } from './chunk-UO7JZVCO.js';
86
84
  export { Container } from './chunk-QVE4GJAT.js';
85
+ export { ChoiceList } from './chunk-QBXZLGK2.js';
87
86
  export { CursorFlag } from './chunk-3BYIWOTV.js';
88
87
  export { PresenceRing, presenceHueClass } from './chunk-I6POAB4V.js';
89
- export { DATA_VIEW_TOOLBAR_LABELS, DataView, DataViewToolbar, FILTER_AXIS_LABELS, FilterAxisBar, FilterAxisChip, applyColumnFilters, applyFilters, blankFilterValue, defaultOperator, filterDefsFromColumns, filterHasValue, filterPredicate, formatFilterValue, operatorOf, tableColumns } from './chunk-AV6YX4GZ.js';
88
+ export { DATA_VIEW_TOOLBAR_LABELS, DataView, DataViewToolbar, FILTER_AXIS_LABELS, FilterAxisBar, FilterAxisChip, applyColumnFilters, applyFilters, blankFilterValue, defaultOperator, filterDefsFromColumns, filterHasValue, filterPredicate, formatFilterValue, operatorOf, tableColumns } from './chunk-KYEXTEJ3.js';
90
89
  export { PageHeader } from './chunk-HOXGBLEY.js';
91
90
  export { Toolbar, ToolbarOverflow, ToolbarWide } from './chunk-PGRPNDWM.js';
92
91
  export { DEFAULT_DATE_TIME_PICKER_LABELS, DateTimePicker } from './chunk-RE6ED5TO.js';
93
- export { ALL_ITEMS, CopyableCell, DATA_TABLE_LABELS, DataTable, RowActionsMenu } from './chunk-LG244LY7.js';
92
+ export { ALL_ITEMS, CopyableCell, DATA_TABLE_LABELS, DataTable, RowActionsMenu } from './chunk-BXSGT3YC.js';
94
93
  export { ChoiceButtons } from './chunk-YSJC7AZC.js';
95
- export { ChoiceList } from './chunk-QBXZLGK2.js';
96
94
  export { CodeBlock } from './chunk-GDDE4UM7.js';
97
95
  export { CopyButton, Copyable } from './chunk-W46LPU4R.js';
98
96
  export { useClipboard, writeClipboard } from './chunk-STJ7QBC3.js';
@@ -105,6 +103,8 @@ export { COMMENT_THREAD_LABELS, CommentThread } from './chunk-IC64IWOO.js';
105
103
  export { Document, DocumentTitle } from './chunk-WI6K5M5X.js';
106
104
  export { COMPOSER_COUNTER_AT, Composer } from './chunk-VJLYGPPE.js';
107
105
  export { Kbd, isApplePlatform, keyGlyph } from './chunk-SMBKXWML.js';
106
+ export { ConfirmField, confirmMatches } from './chunk-YSY6UJ4F.js';
107
+ export { InlineCode } from './chunk-5CLW2CXT.js';
108
108
  export { CalendarGrid, compareDays, daysInMonth, sameDay, shiftDay, shiftMonth, today } from './chunk-GXQ3B46I.js';
109
109
  export { Callout } from './chunk-SVSCLHHI.js';
110
110
  export { CANVAS_COMPOSE_CONTEXT, CANVAS_FIT_MAX_ZOOM, CANVAS_FIT_PADDING, CANVAS_FOCUS_CONTEXT, CANVAS_MAX_ZOOM, CANVAS_MIN_ZOOM, CANVAS_PAN_MARGIN, CANVAS_PAN_STEP, CANVAS_REVEAL_PADDING, CANVAS_TAP_SLOP, CANVAS_WHEEL_LINE_PX, CANVAS_WHEEL_ZOOM_PER_PIXEL, CANVAS_ZOOM_CEILING, CANVAS_ZOOM_LIMITS, CANVAS_ZOOM_STEP, Canvas, IDENTITY_VIEW, anchorView, beyondSlop, clampPan, clampZoom, fitView, panBy, pinchView, regionView, revealView, screenRect, toScreen, toWorld, wheelPixels, wheelZoomFactor, zoomAt, zoomLimits } from './chunk-TXAFKH2A.js';
@@ -148,9 +148,9 @@ export { DisclosureAnatomy } from './chunk-ENJUPIND.js';
148
148
  export { HeadingLevelProvider, headingTag, nextHeadingLevel, useHeadingLevel } from './chunk-PQADV6P6.js';
149
149
  export { Count } from './chunk-BHHIIK3M.js';
150
150
  export { ADD_PILL_MS, AddPill } from './chunk-TROLVEZY.js';
151
- export { AccountRow, AppShell, AppShellRail, AppShellRailRow, AppShellToggle, AppShellTopbar, useAppShell } from './chunk-G5TAKMEA.js';
151
+ export { AccountRow, AppShell, AppShellRail, AppShellRailRow, AppShellToggle, AppShellTopbar, useAppShell } from './chunk-BFQK7CYJ.js';
152
152
  import './chunk-IG75YMUN.js';
153
- export { Menu } from './chunk-4MIM356A.js';
153
+ export { Menu } from './chunk-UFKUWVMV.js';
154
154
  export { Button, ButtonLink } from './chunk-OG6CL3EB.js';
155
155
  export { LAYER_GAP, LAYER_REPOSITION_EVENT, LayerHost, outsideBounds, placePopup, useLayerContainer, viewportBounds } from './chunk-HMPFGIWM.js';
156
156
  export { focusables, isComposing, isModalLayerOpen, layerCount, useBodyScrollLock, useModalLayer, usePopupLayer } from './chunk-R25RGPUB.js';
package/dist/styles.css CHANGED
@@ -13304,7 +13304,7 @@ svg.crewlet-datetime__chevron {
13304
13304
  }
13305
13305
 
13306
13306
 
13307
- /* Menu-XIJ4LQUT.css */
13307
+ /* Menu-KEKAD3BZ.css */
13308
13308
  /*
13309
13309
  * The menu button's panel.
13310
13310
  *
@@ -13341,9 +13341,15 @@ svg.crewlet-datetime__chevron {
13341
13341
  * however long that label was and the 320px was a number nothing read. A
13342
13342
  * width is clamped by the ceiling, and the label that no longer fits is the
13343
13343
  * one that truncates.
13344
+ *
13345
+ * A FLOOR, when the trigger sets one (`width="trigger"`, which writes
13346
+ * --crewlet-menu-floor): the panel is never narrower than a trigger that
13347
+ * spans a column. The ceiling is lifted to meet it, so the two never cross
13348
+ * and the rule above still holds.
13344
13349
  */
13345
13350
  width: max-content;
13346
- max-width: 320px;
13351
+ min-width: var(--crewlet-menu-floor, 0px);
13352
+ max-width: max(320px, var(--crewlet-menu-floor, 0px));
13347
13353
  max-height: min(360px, 60vh);
13348
13354
  overflow-y: auto;
13349
13355
  overscroll-behavior: contain;
@@ -13500,6 +13506,7 @@ svg.crewlet-datetime__chevron {
13500
13506
  .crewlet-menu__text {
13501
13507
  display: flex;
13502
13508
  flex-direction: column;
13509
+ gap: calc(var(--spacing-1) / 2);
13503
13510
  min-width: 0;
13504
13511
  }
13505
13512
 
@@ -13509,9 +13516,14 @@ svg.crewlet-datetime__chevron {
13509
13516
  white-space: nowrap;
13510
13517
  }
13511
13518
 
13519
+ /*
13520
+ * ONE STEP UNDER THE LABEL, not two. At 11px under a 13px label the second
13521
+ * line read as fine print; at 12px in the tertiary ink it is still plainly the
13522
+ * lesser line, and it is legible at a glance.
13523
+ */
13512
13524
  .crewlet-menu__description {
13513
13525
  color: var(--color-text-tertiary);
13514
- font-size: var(--font-size-2xs);
13526
+ font-size: var(--font-size-xs);
13515
13527
  white-space: normal;
13516
13528
  }
13517
13529
 
@@ -13529,11 +13541,17 @@ svg.crewlet-datetime__chevron {
13529
13541
  /*
13530
13542
  * Facts above the items, across the panel's full width with a hairline under
13531
13543
  * them: what the actions below are about, read rather than pressed.
13544
+ *
13545
+ * A NAME AND ITS VALUE SHARE ONE LINE, the name at the start and the value at
13546
+ * the end, as a property reads ("Access … Admin"). Stacked, the pair spent two
13547
+ * lines on one fact. A value too long for the line wraps beneath its name.
13532
13548
  */
13533
13549
  .crewlet-menu__header {
13534
13550
  display: flex;
13535
- flex-direction: column;
13536
- gap: var(--spacing-1);
13551
+ flex-wrap: wrap;
13552
+ align-items: center;
13553
+ justify-content: space-between;
13554
+ gap: var(--spacing-1) var(--spacing-2);
13537
13555
  margin: calc(var(--spacing-1) * -1) calc(var(--spacing-1) * -1) var(--spacing-1);
13538
13556
  padding: var(--spacing-2) var(--spacing-3);
13539
13557
  border-bottom: 1px solid var(--color-border-default);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@crewlethq/ui",
3
- "version": "0.21.0",
3
+ "version": "0.22.0",
4
4
  "description": "Crewlet shared React components built on @crewlethq/tokens and @crewlethq/icons.",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -42,8 +42,8 @@
42
42
  "clean": "rm -rf dist src/generated"
43
43
  },
44
44
  "dependencies": {
45
- "@crewlethq/icons": "0.21.0",
46
- "@crewlethq/tokens": "0.21.0",
45
+ "@crewlethq/icons": "0.22.0",
46
+ "@crewlethq/tokens": "0.22.0",
47
47
  "uqr": "0.1.3"
48
48
  },
49
49
  "peerDependencies": {
@@ -1,5 +1,5 @@
1
- import { InlineCode } from './chunk-5CLW2CXT.js';
2
1
  import { ConfirmModal } from './chunk-F4DPAJCN.js';
2
+ import { InlineCode } from './chunk-5CLW2CXT.js';
3
3
  import { Callout } from './chunk-SVSCLHHI.js';
4
4
  import './LinkInterstitial-ET4MSVSV.css';
5
5
  import { jsx, jsxs } from 'react/jsx-runtime';