@astryxdesign/core 0.4.5-canary.e238799 → 0.4.5-canary.ffd05c4

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.
@@ -1 +1 @@
1
- {"version":3,"file":"BottomSheetPanel.d.ts","sourceRoot":"","sources":["../../src/BottomSheet/BottomSheetPanel.tsx"],"names":[],"mappings":"AAIA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,EAOL,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AAEf,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,cAAc,CAAC;AAY5C,OAAO,EAGL,KAAK,oBAAoB,EAC1B,MAAM,eAAe,CAAC;AAIvB,QAAA,MAAM,cAAc;;;;CAIV,CAAC;AAEX,MAAM,MAAM,iBAAiB,GAAG,MAAM,OAAO,cAAc,CAAC;AAC5D,YAAY,EAAC,oBAAoB,EAAC,CAAC;AAoHnC,MAAM,MAAM,sBAAsB,GAChC,UAAU,GAAG,UAAU,GAAG,QAAQ,GAAG,SAAS,CAAC;AAEjD,MAAM,MAAM,qBAAqB,GAC7B;IAAC,IAAI,EAAE,QAAQ,CAAA;CAAC,GAChB;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,OAAO,CAAA;CAAC,GACjC;IACE,IAAI,EAAE,UAAU,CAAC;IACjB,MAAM,EAAE,SAAS,GAAG,UAAU,GAAG,QAAQ,CAAC;IAC1C,eAAe,EAAE,MAAM,CAAC;CACzB,GACD;IAAC,IAAI,EAAE,SAAS,CAAA;CAAC,CAAC;AAEtB,UAAU,qBAAsB,SAAQ,SAAS,CAAC,cAAc,CAAC;IAC/D,+CAA+C;IAC/C,GAAG,CAAC,EAAE,KAAK,CAAC,GAAG,CAAC,cAAc,CAAC,CAAC;IAChC,KAAK,EAAE,qBAAqB,CAAC;IAC7B,MAAM,EAAE,iBAAiB,GAAG,MAAM,GAAG,MAAM,CAAC;IAC5C,QAAQ,EAAE,SAAS,CAAC;IACpB,UAAU,CAAC,EAAE,aAAa,CAAC,oBAAoB,CAAC,CAAC;IACjD,qBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,gFAAgF;IAChF,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,SAAS,EAAE,MAAM,IAAI,CAAC;IACtB,cAAc,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,eAAe,CAAC,EAAE,CAAC,OAAO,EAAE,cAAc,GAAG,IAAI,KAAK,IAAI,CAAC;IAC3D,aAAa,CAAC,EAAE,CAAC,MAAM,EAAE,sBAAsB,KAAK,IAAI,CAAC;IACzD,gBAAgB,CAAC,EAAE,CAAC,MAAM,EAAE,sBAAsB,KAAK,IAAI,CAAC;CAC7D;AA+GD,4EAA4E;AAC5E,wBAAgB,gBAAgB,CAAC,EAC/B,GAAG,EACH,KAAK,EACL,MAAM,EACN,QAAQ,EACR,UAAU,EACV,SAAS,EACT,KAAK,EACL,QAAQ,EACR,MAAM,EACN,qBAA4B,EAC5B,kBAA0B,EAC1B,SAAS,EACT,cAAc,EACd,eAAe,EACf,aAAa,EACb,gBAAgB,EAChB,GAAG,KAAK,EACT,EAAE,qBAAqB,+BAwQvB;yBA1Re,gBAAgB"}
1
+ {"version":3,"file":"BottomSheetPanel.d.ts","sourceRoot":"","sources":["../../src/BottomSheet/BottomSheetPanel.tsx"],"names":[],"mappings":"AAIA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,EAOL,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AAEf,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,cAAc,CAAC;AAY5C,OAAO,EAGL,KAAK,oBAAoB,EAC1B,MAAM,eAAe,CAAC;AAIvB,QAAA,MAAM,cAAc;;;;CAIV,CAAC;AAEX,MAAM,MAAM,iBAAiB,GAAG,MAAM,OAAO,cAAc,CAAC;AAC5D,YAAY,EAAC,oBAAoB,EAAC,CAAC;AA4InC,MAAM,MAAM,sBAAsB,GAChC,UAAU,GAAG,UAAU,GAAG,QAAQ,GAAG,SAAS,CAAC;AAEjD,MAAM,MAAM,qBAAqB,GAC7B;IAAC,IAAI,EAAE,QAAQ,CAAA;CAAC,GAChB;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,OAAO,CAAA;CAAC,GACjC;IACE,IAAI,EAAE,UAAU,CAAC;IACjB,MAAM,EAAE,SAAS,GAAG,UAAU,GAAG,QAAQ,CAAC;IAC1C,eAAe,EAAE,MAAM,CAAC;CACzB,GACD;IAAC,IAAI,EAAE,SAAS,CAAA;CAAC,CAAC;AAEtB,UAAU,qBAAsB,SAAQ,SAAS,CAAC,cAAc,CAAC;IAC/D,+CAA+C;IAC/C,GAAG,CAAC,EAAE,KAAK,CAAC,GAAG,CAAC,cAAc,CAAC,CAAC;IAChC,KAAK,EAAE,qBAAqB,CAAC;IAC7B,MAAM,EAAE,iBAAiB,GAAG,MAAM,GAAG,MAAM,CAAC;IAC5C,QAAQ,EAAE,SAAS,CAAC;IACpB,UAAU,CAAC,EAAE,aAAa,CAAC,oBAAoB,CAAC,CAAC;IACjD,qBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,gFAAgF;IAChF,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,SAAS,EAAE,MAAM,IAAI,CAAC;IACtB,cAAc,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,eAAe,CAAC,EAAE,CAAC,OAAO,EAAE,cAAc,GAAG,IAAI,KAAK,IAAI,CAAC;IAC3D,aAAa,CAAC,EAAE,CAAC,MAAM,EAAE,sBAAsB,KAAK,IAAI,CAAC;IACzD,gBAAgB,CAAC,EAAE,CAAC,MAAM,EAAE,sBAAsB,KAAK,IAAI,CAAC;CAC7D;AA+GD,4EAA4E;AAC5E,wBAAgB,gBAAgB,CAAC,EAC/B,GAAG,EACH,KAAK,EACL,MAAM,EACN,QAAQ,EACR,UAAU,EACV,SAAS,EACT,KAAK,EACL,QAAQ,EACR,MAAM,EACN,qBAA4B,EAC5B,kBAA0B,EAC1B,SAAS,EACT,cAAc,EACd,eAAe,EACf,aAAa,EACb,gBAAgB,EAChB,GAAG,KAAK,EACT,EAAE,qBAAqB,+BAwQvB;yBA1Re,gBAAgB"}
@@ -39,6 +39,11 @@ const HEIGHT_BUDGETS = {
39
39
  const OVERSCROLL_PADDING = 48;
40
40
  const MOBILE_KEYBOARD_BOTTOM_CLEARANCE = 48;
41
41
  const TRANSITION_BACKSTOP_BUFFER_MS = 50;
42
+ // The floating handle bar's height. The bar is out of flow, so this is not
43
+ // layout space the content pays for -- the pill (4px, centered) lands 10-14px
44
+ // from the sheet's top edge, inside the space a content wrapper's own top
45
+ // padding already provides.
46
+ const HANDLE_BAR_HEIGHT = spacingVars['--spacing-6'];
42
47
 
43
48
  // Measure the same viewport the height budgets are written against. Those are
44
49
  // `dvh`, which the virtual keyboard does not shrink, so reading
@@ -69,6 +74,7 @@ const styles = {
69
74
  sheet: {
70
75
  kfzvcC: "x67bb7w",
71
76
  kB7OPa: "x9f619",
77
+ kVAEAm: "x1n2onr6",
72
78
  k1xSpc: "x78zum5",
73
79
  kXwgrk: "xdt5ytf",
74
80
  kAzted: "x2lwn1j",
@@ -411,7 +417,7 @@ export function BottomSheetPanel({
411
417
  }),
412
418
  children: [/*#__PURE__*/_jsx("div", {
413
419
  ...{
414
- className: "x2lah0s x78zum5 x6s0dn4 xl56j7k x1k15mir x5ve5x3 x1jm3nie"
420
+ className: "x10l6tqk x13vifvy x1o0tod xtijo5x x1vjfegm x78zum5 x6s0dn4 xl56j7k xvpftlf xafqdz2 x5ve5x3 x1jm3nie"
415
421
  },
416
422
  ...handleProps,
417
423
  "aria-hidden": "true",
@@ -68,6 +68,14 @@ export interface ItemProps extends BaseProps<HTMLElement> {
68
68
  * and text-overflow: ellipsis is applied.
69
69
  */
70
70
  descriptionLines?: number;
71
+ /**
72
+ * How the label and description sit together. `stacked` puts the description
73
+ * on its own line below the label; `inline` keeps both on one line, with the
74
+ * description ellipsizing first, so the row fits a fixed-height host.
75
+ *
76
+ * @default 'stacked'
77
+ */
78
+ layout?: 'stacked' | 'inline';
71
79
  /**
72
80
  * Click handler. Makes the item clickable with button semantics.
73
81
  */
@@ -139,7 +147,7 @@ export interface ItemProps extends BaseProps<HTMLElement> {
139
147
  * />
140
148
  * ```
141
149
  */
142
- export declare function Item({ as: Component, marker, startContent, label, description, endContent, align, density, labelLines, descriptionLines, onClick, interactiveRef, href, target: targetFromProps, rel: relFromProps, isHighlighted, isSelected, isDisabled, xstyle, className, style, ref, role, ...restProps }: ItemProps): import("react").JSX.Element;
150
+ export declare function Item({ as: Component, marker, startContent, label, description, endContent, align, density, labelLines, descriptionLines, layout, onClick, interactiveRef, href, target: targetFromProps, rel: relFromProps, isHighlighted, isSelected, isDisabled, xstyle, className, style, ref, role, ...restProps }: ItemProps): import("react").JSX.Element;
143
151
  export declare namespace Item {
144
152
  var displayName: string;
145
153
  }
@@ -1 +1 @@
1
- {"version":3,"file":"Item.d.ts","sourceRoot":"","sources":["../../src/Item/Item.tsx"],"names":[],"mappings":"AAIA;;;;;;;;;;;;GAYG;AAEH,OAAO,EAAS,KAAK,SAAS,EAAC,MAAM,OAAO,CAAC;AAU7C,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,cAAc,CAAC;AAa5C,MAAM,MAAM,SAAS,GAAG,QAAQ,GAAG,OAAO,CAAC;AAC3C,MAAM,MAAM,WAAW,GAAG,SAAS,GAAG,UAAU,GAAG,UAAU,CAAC;AAE9D,MAAM,WAAW,SAAU,SAAQ,SAAS,CAAC,WAAW,CAAC;IACvD,yCAAyC;IACzC,GAAG,CAAC,EAAE,KAAK,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC;IAE7B;;;OAGG;IACH,EAAE,CAAC,EAAE,KAAK,GAAG,IAAI,GAAG,MAAM,CAAC;IAE3B;;;OAGG;IACH,MAAM,CAAC,EAAE,SAAS,CAAC;IAEnB;;;OAGG;IACH,YAAY,CAAC,EAAE,SAAS,CAAC;IAEzB;;;OAGG;IACH,KAAK,EAAE,SAAS,CAAC;IAEjB;;OAEG;IACH,WAAW,CAAC,EAAE,SAAS,CAAC;IAExB;;;OAGG;IACH,UAAU,CAAC,EAAE,SAAS,CAAC;IAEvB;;;OAGG;IACH,KAAK,CAAC,EAAE,SAAS,CAAC;IAElB;;;;OAIG;IACH,OAAO,CAAC,EAAE,WAAW,CAAC;IAEtB;;;OAGG;IACH,UAAU,CAAC,EAAE,MAAM,CAAC;IAEpB;;;OAGG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAE1B;;OAEG;IACH,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC,UAAU,KAAK,IAAI,CAAC;IAE5C;;;;;;;;;;;OAWG;IACH,cAAc,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAErD;;OAEG;IACH,IAAI,CAAC,EAAE,MAAM,CAAC;IAEd;;OAEG;IACH,MAAM,CAAC,EAAE,QAAQ,GAAG,OAAO,CAAC;IAE5B;;;OAGG;IACH,GAAG,CAAC,EAAE,MAAM,CAAC;IAEb;;;OAGG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;IAExB;;;;;;;;OAQG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IAErB;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IAErB;;OAEG;IACH,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB;AAmKD;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,IAAI,CAAC,EACnB,EAAE,EAAE,SAAiB,EACrB,MAAM,EACN,YAAY,EACZ,KAAK,EACL,WAAW,EACX,UAAU,EACV,KAAgB,EAChB,OAAoB,EACpB,UAAU,EACV,gBAAgB,EAChB,OAAO,EACP,cAAc,EACd,IAAI,EACJ,MAAM,EAAE,eAAe,EACvB,GAAG,EAAE,YAAY,EACjB,aAAqB,EACrB,UAAkB,EAClB,UAAkB,EAClB,MAAM,EACN,SAAS,EACT,KAAK,EACL,GAAG,EACH,IAAI,EACJ,GAAG,SAAS,EACb,EAAE,SAAS,+BA2MX;yBApOe,IAAI"}
1
+ {"version":3,"file":"Item.d.ts","sourceRoot":"","sources":["../../src/Item/Item.tsx"],"names":[],"mappings":"AAIA;;;;;;;;;;;;GAYG;AAEH,OAAO,EAAS,KAAK,SAAS,EAAC,MAAM,OAAO,CAAC;AAU7C,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,cAAc,CAAC;AAa5C,MAAM,MAAM,SAAS,GAAG,QAAQ,GAAG,OAAO,CAAC;AAC3C,MAAM,MAAM,WAAW,GAAG,SAAS,GAAG,UAAU,GAAG,UAAU,CAAC;AAE9D,MAAM,WAAW,SAAU,SAAQ,SAAS,CAAC,WAAW,CAAC;IACvD,yCAAyC;IACzC,GAAG,CAAC,EAAE,KAAK,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC;IAE7B;;;OAGG;IACH,EAAE,CAAC,EAAE,KAAK,GAAG,IAAI,GAAG,MAAM,CAAC;IAE3B;;;OAGG;IACH,MAAM,CAAC,EAAE,SAAS,CAAC;IAEnB;;;OAGG;IACH,YAAY,CAAC,EAAE,SAAS,CAAC;IAEzB;;;OAGG;IACH,KAAK,EAAE,SAAS,CAAC;IAEjB;;OAEG;IACH,WAAW,CAAC,EAAE,SAAS,CAAC;IAExB;;;OAGG;IACH,UAAU,CAAC,EAAE,SAAS,CAAC;IAEvB;;;OAGG;IACH,KAAK,CAAC,EAAE,SAAS,CAAC;IAElB;;;;OAIG;IACH,OAAO,CAAC,EAAE,WAAW,CAAC;IAEtB;;;OAGG;IACH,UAAU,CAAC,EAAE,MAAM,CAAC;IAEpB;;;OAGG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAE1B;;;;;;OAMG;IACH,MAAM,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;IAE9B;;OAEG;IACH,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC,UAAU,KAAK,IAAI,CAAC;IAE5C;;;;;;;;;;;OAWG;IACH,cAAc,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAErD;;OAEG;IACH,IAAI,CAAC,EAAE,MAAM,CAAC;IAEd;;OAEG;IACH,MAAM,CAAC,EAAE,QAAQ,GAAG,OAAO,CAAC;IAE5B;;;OAGG;IACH,GAAG,CAAC,EAAE,MAAM,CAAC;IAEb;;;OAGG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;IAExB;;;;;;;;OAQG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IAErB;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IAErB;;OAEG;IACH,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB;AAsLD;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,IAAI,CAAC,EACnB,EAAE,EAAE,SAAiB,EACrB,MAAM,EACN,YAAY,EACZ,KAAK,EACL,WAAW,EACX,UAAU,EACV,KAAgB,EAChB,OAAoB,EACpB,UAAU,EACV,gBAAgB,EAChB,MAAkB,EAClB,OAAO,EACP,cAAc,EACd,IAAI,EACJ,MAAM,EAAE,eAAe,EACvB,GAAG,EAAE,YAAY,EACjB,aAAqB,EACrB,UAAkB,EAClB,UAAkB,EAClB,MAAM,EACN,SAAS,EACT,KAAK,EACL,GAAG,EACH,IAAI,EACJ,GAAG,SAAS,EACb,EAAE,SAAS,+BAqNX;yBA/Oe,IAAI"}
package/dist/Item/Item.js CHANGED
@@ -82,6 +82,15 @@ const styles = {
82
82
  kfzvcC: "x47corl",
83
83
  $$css: true
84
84
  },
85
+ inlineLabel: {
86
+ kmuXW: "x2lah0s",
87
+ $$css: true
88
+ },
89
+ inlineDescription: {
90
+ kmuXW: "xs83m0k",
91
+ k7Eaqz: "xeuugli",
92
+ $$css: true
93
+ },
85
94
  label: {
86
95
  kMwMTN: "x5tbw38",
87
96
  kGuDYH: "xjm74w1",
@@ -174,6 +183,7 @@ export function Item({
174
183
  density = 'balanced',
175
184
  labelLines,
176
185
  descriptionLines,
186
+ layout = 'stacked',
177
187
  onClick,
178
188
  interactiveRef,
179
189
  href,
@@ -223,13 +233,17 @@ export function Item({
223
233
  const isStringLabel = typeof label === 'string';
224
234
  const isStringDescription = typeof description === 'string';
225
235
  const labelTruncateStyle = labelLines != null ? labelLines === 1 ? styles.labelSingleTruncate : styles.labelMultiTruncate : isStringLabel ? styles.labelSingleTruncate : null;
226
- const descriptionTruncateStyle = descriptionLines != null ? descriptionLines === 1 ? styles.descriptionSingleTruncate : styles.descriptionMultiTruncate : isStringDescription ? styles.descriptionSingleTruncate : null;
236
+
237
+ // Inline rows are one line by definition, so the description always
238
+ // ellipsizes there — a ReactNode description cannot wrap the row open.
239
+ const isInline = layout === 'inline' && description != null;
240
+ const descriptionTruncateStyle = descriptionLines != null ? descriptionLines === 1 ? styles.descriptionSingleTruncate : styles.descriptionMultiTruncate : isStringDescription || isInline ? styles.descriptionSingleTruncate : null;
227
241
  const labelAndDescription = /*#__PURE__*/_jsxs(_Fragment, {
228
242
  children: [/*#__PURE__*/_jsx("span", {
229
- ...stylex.props(styles.label, labelTruncateStyle, labelLines != null && labelLines > 1 && dynamicStyles.lineClamp(labelLines)),
243
+ ...stylex.props(styles.label, isInline && styles.inlineLabel, labelTruncateStyle, labelLines != null && labelLines > 1 && dynamicStyles.lineClamp(labelLines)),
230
244
  children: label
231
245
  }), description != null && /*#__PURE__*/_jsx("span", {
232
- ...stylex.props(styles.description, descriptionTruncateStyle, descriptionLines != null && descriptionLines > 1 && dynamicStyles.lineClamp(descriptionLines)),
246
+ ...stylex.props(styles.description, isInline && styles.inlineDescription, descriptionTruncateStyle, descriptionLines != null && descriptionLines > 1 && dynamicStyles.lineClamp(descriptionLines)),
233
247
  children: description
234
248
  })]
235
249
  });
@@ -259,10 +273,16 @@ export function Item({
259
273
  0: {
260
274
  className: "x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h"
261
275
  },
276
+ 2: {
277
+ className: "x78zum5 x98rzlu xeuugli x1yc453h x1q0g3np x6s0dn4 x1lfs0n9"
278
+ },
262
279
  1: {
263
280
  className: "x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h xbyyjgo"
281
+ },
282
+ 3: {
283
+ className: "x78zum5 x98rzlu xeuugli x1yc453h x1q0g3np x6s0dn4 x1lfs0n9 xbyyjgo"
264
284
  }
265
- }[!!isDisabled << 0],
285
+ }[!!isInline << 1 | !!isDisabled << 0],
266
286
  children: labelAndDescription
267
287
  }) : href != null ? /*#__PURE__*/_jsx(LinkComponent, {
268
288
  href: href,
@@ -274,10 +294,16 @@ export function Item({
274
294
  0: {
275
295
  className: "xmper1u xln7xf2 x1heor9g x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h x1hl2dhg x1a2a7pz"
276
296
  },
297
+ 2: {
298
+ className: "xmper1u xln7xf2 x1heor9g x78zum5 x98rzlu xeuugli x1yc453h x1hl2dhg x1a2a7pz x1q0g3np x6s0dn4 x1lfs0n9"
299
+ },
277
300
  1: {
278
301
  className: "xmper1u xln7xf2 x1heor9g x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h x1hl2dhg x1a2a7pz xbyyjgo"
302
+ },
303
+ 3: {
304
+ className: "xmper1u xln7xf2 x1heor9g x78zum5 x98rzlu xeuugli x1yc453h x1hl2dhg x1a2a7pz x1q0g3np x6s0dn4 x1lfs0n9 xbyyjgo"
279
305
  }
280
- }[!!isDisabled << 0],
306
+ }[!!isInline << 1 | !!isDisabled << 0],
281
307
  children: labelAndDescription
282
308
  }) : onClick != null ? /*#__PURE__*/_jsx("button", {
283
309
  type: "button",
@@ -287,20 +313,32 @@ export function Item({
287
313
  0: {
288
314
  className: "xmper1u xln7xf2 x1heor9g x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h x1a2a7pz"
289
315
  },
316
+ 2: {
317
+ className: "xmper1u xln7xf2 x1heor9g x78zum5 x98rzlu xeuugli x1yc453h x1a2a7pz x1q0g3np x6s0dn4 x1lfs0n9"
318
+ },
290
319
  1: {
291
320
  className: "xmper1u xln7xf2 x1heor9g x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h x1a2a7pz xbyyjgo"
321
+ },
322
+ 3: {
323
+ className: "xmper1u xln7xf2 x1heor9g x78zum5 x98rzlu xeuugli x1yc453h x1a2a7pz x1q0g3np x6s0dn4 x1lfs0n9 xbyyjgo"
292
324
  }
293
- }[!!isDisabled << 0],
325
+ }[!!isInline << 1 | !!isDisabled << 0],
294
326
  children: labelAndDescription
295
327
  }) : /*#__PURE__*/_jsx("span", {
296
328
  ...{
297
329
  0: {
298
330
  className: "x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h"
299
331
  },
332
+ 2: {
333
+ className: "x78zum5 x98rzlu xeuugli x1yc453h x1q0g3np x6s0dn4 x1lfs0n9"
334
+ },
300
335
  1: {
301
336
  className: "x78zum5 xdt5ytf x98rzlu xeuugli x1yc453h xbyyjgo"
337
+ },
338
+ 3: {
339
+ className: "x78zum5 x98rzlu xeuugli x1yc453h x1q0g3np x6s0dn4 x1lfs0n9 xbyyjgo"
302
340
  }
303
- }[!!isDisabled << 0],
341
+ }[!!isInline << 1 | !!isDisabled << 0],
304
342
  children: labelAndDescription
305
343
  }), endContent != null && /*#__PURE__*/_jsx("span", {
306
344
  ...{
@@ -137,7 +137,8 @@ interface SelectorPropsBase<T extends SelectorOptionType = SelectorOptionType> e
137
137
  */
138
138
  labelTooltip?: string;
139
139
  /**
140
- * Icon displayed at the start of the selector trigger.
140
+ * Icon displayed at the start of the selector trigger. Takes precedence over
141
+ * the selected option's own `icon`, which the trigger otherwise renders.
141
142
  */
142
143
  startIcon?: ReactNode | IconType;
143
144
  /**
@@ -145,6 +146,30 @@ interface SelectorPropsBase<T extends SelectorOptionType = SelectorOptionType> e
145
146
  * Only called for selectable options (not dividers/sections).
146
147
  */
147
148
  renderOption?: (option: SelectorOptionData) => ReactNode;
149
+ /**
150
+ * Custom render function for the selected option inside the closed trigger.
151
+ * Only called when something is selected; the placeholder is unaffected.
152
+ *
153
+ * Passing this does not change the trigger's height — what it draws does. A
154
+ * one-line value measures exactly the `size` token, so the control still
155
+ * lines up with the Buttons and inputs beside it; each further line of
156
+ * content adds one text line. Inside an `InputGroup` the group owns the row
157
+ * height: the trigger clamps its value box to that row, so a `SelectorOption`
158
+ * folds onto one line and ellipsizes, and anything taller than the row is cut
159
+ * off at it rather than bleeding over the rows above and below.
160
+ *
161
+ * @example
162
+ * ```
163
+ * renderValue={option => (
164
+ * <SelectorOption
165
+ * icon={option.icon}
166
+ * label={option.label}
167
+ * description={option.description}
168
+ * />
169
+ * )}
170
+ * ```
171
+ */
172
+ renderValue?: (option: SelectorOptionData) => ReactNode;
148
173
  /**
149
174
  * Which edge of the option row carries the selected mark. `start` reserves a
150
175
  * mark column ahead of every label so they stay aligned, the way a native
@@ -1 +1 @@
1
- {"version":3,"file":"Selector.d.ts","sourceRoot":"","sources":["../../src/Selector/Selector.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"Selector.d.ts","sourceRoot":"","sources":["../../src/Selector/Selector.tsx"],"names":[],"mappings":"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"}
@@ -35,6 +35,7 @@ import { useCombobox, useSelectedItemOffset } from "./hooks.js";
35
35
  import { useTypeahead } from "../hooks/useTypeahead.js";
36
36
  import { useResolvedRequired } from "../hooks/useResolvedRequired.js";
37
37
  import { SelectorOption } from "./SelectorOption.js";
38
+ import { SelectorRowLayoutContext } from "./SelectorRowLayoutContext.js";
38
39
  import { getInputARIA, isImeKeyEvent, mergeProps } from "../utils/index.js";
39
40
  import { useSize } from "../SizeContext/SizeContext.js";
40
41
  import { themeProps } from "../utils/themeProps.js";
@@ -57,7 +58,7 @@ const styles = {
57
58
  kg3NbH: "xrrkdod",
58
59
  kMv6JI: "x9ynric",
59
60
  kGuDYH: "xcr08ib xdk3u5w",
60
- kLWn49: "x1kq96og",
61
+ kLWn49: "x7acx1w",
61
62
  kMwMTN: "x1tgivj0",
62
63
  kkrTdU: "x1ypdohk",
63
64
  $$css: true
@@ -66,6 +67,11 @@ const styles = {
66
67
  kMwMTN: "xv1l7n4",
67
68
  $$css: true
68
69
  },
70
+ triggerInGroup: {
71
+ kAzted: "x2lwn1j",
72
+ k8WAf4: "xt970qd",
73
+ $$css: true
74
+ },
69
75
  triggerIcon: {
70
76
  kmuXW: "x2lah0s",
71
77
  $$css: true
@@ -155,17 +161,32 @@ const styles = {
155
161
  $$css: true
156
162
  }
157
163
  };
164
+
165
+ // The trigger is sized by PADDING, not by a fixed height, so it is the size
166
+ // token plus one text line for each extra line the value uses: 28/32/36 for
167
+ // one line, 48/52/56 for two. The token and a text line are both multiples of
168
+ // 4, so every trigger lands on the 4px rhythm and lines up with the Buttons
169
+ // and inputs beside it. No prop picks the height — the content does, and it
170
+ // can only land on the grid.
171
+ //
172
+ // `--spacing-5` is one line here because `triggerContainer` pins its
173
+ // line-height to exactly that; the two must stay in step, which is why both
174
+ // read the same token rather than one hardcoding 20px.
175
+ const linePad = token => `calc((${token} - ${spacingVars['--spacing-5']} - 2 * ${borderVars['--border-width']}) / 2)`;
158
176
  const sizeStyles = {
159
177
  sm: {
160
- kZKoxP: "x6k0iem",
178
+ kAzted: "x1gdqauq",
179
+ k8WAf4: "x1ecmfrv",
161
180
  $$css: true
162
181
  },
163
182
  md: {
164
- kZKoxP: "x1ueg155",
183
+ kAzted: "x1uogy3y",
184
+ k8WAf4: "x1ioay2v",
165
185
  $$css: true
166
186
  },
167
187
  lg: {
168
- kZKoxP: "xssyfek",
188
+ kAzted: "x1xf4nls",
189
+ k8WAf4: "x1vn5h1t",
169
190
  $$css: true
170
191
  }
171
192
  };
@@ -219,7 +240,8 @@ function DefaultOption({
219
240
  }) {
220
241
  return /*#__PURE__*/_jsx(SelectorOption, {
221
242
  icon: option.icon,
222
- label: option.label ?? option.value
243
+ label: option.label ?? option.value,
244
+ description: option.description
223
245
  });
224
246
  }
225
247
 
@@ -282,6 +304,7 @@ export function Selector(props) {
282
304
  startIcon,
283
305
  htmlName,
284
306
  renderOption,
307
+ renderValue,
285
308
  indicatorPosition = 'end',
286
309
  hasSearch = false,
287
310
  searchPlaceholder: searchPlaceholderFromProps,
@@ -770,6 +793,43 @@ export function Selector(props) {
770
793
  // on-field icon would duplicate it — keep the chevron indicator instead.
771
794
  const showStatusIcon = status != null && effectiveStatusVariant !== 'detached';
772
795
  const showStatusTooltip = status != null && effectiveStatusVariant === 'tooltip' && !!status.message;
796
+
797
+ // Two lines cannot fit inside an InputGroup: the group pins the row height,
798
+ // and the trigger clamps its value box to one line so nothing bleeds through
799
+ // its border (styles.triggerValueInGroup). The clamp holds for any node; the
800
+ // context is what lets the rows the system draws itself reflow into that one
801
+ // line — label and description side by side — instead of being cut off at
802
+ // it. Outside a group the caller's own row decides, and the trigger's
803
+ // padding sizes it to whatever that draws.
804
+ const rowLayout = inputGroup ? 'inline' : 'stacked';
805
+
806
+ // What the closed trigger shows for the current selection: the option's icon
807
+ // and label. `startIcon` wins over the option's own icon so a caller who
808
+ // pins a field icon does not get two.
809
+ const valueContent = selectedItem && renderValue ? /*#__PURE__*/_jsx(SelectorRowLayoutContext, {
810
+ value: rowLayout,
811
+ children: /*#__PURE__*/_jsx("span", {
812
+ ...{
813
+ 0: {
814
+ className: "x1iyjqo2 xeuugli xb3r6kr x1yc453h"
815
+ },
816
+ 1: {
817
+ className: "x1iyjqo2 xeuugli xb3r6kr x1yc453h xmz0i5r"
818
+ }
819
+ }[!!inputGroup << 0],
820
+ children: renderValue(selectedItem)
821
+ })
822
+ }) : /*#__PURE__*/_jsxs(_Fragment, {
823
+ children: [!startIcon && selectedItem?.icon != null && renderIconSlot(selectedItem.icon, {
824
+ size: 'sm',
825
+ color: 'secondary'
826
+ }), /*#__PURE__*/_jsx("span", {
827
+ ...{
828
+ className: "x1iyjqo2 xeuugli xb3r6kr xlyipyv xuxw1ft x1yc453h"
829
+ },
830
+ children: selectedItem?.label ?? placeholder
831
+ })]
832
+ });
773
833
  const selectorContent = /*#__PURE__*/_jsxs(_Fragment, {
774
834
  children: [/*#__PURE__*/_jsxs("div", {
775
835
  ref: el => {
@@ -787,7 +847,7 @@ export function Selector(props) {
787
847
  size,
788
848
  status: status?.type ?? null,
789
849
  disabled: isDisabled ? 'disabled' : null
790
- }), stylex.props(inputWrapperStyles.base, styles.triggerContainer, sizeStyles[size], variant === 'ghost' && styles.triggerGhost, variant === 'ghost' && focusOutlineStyles.focusWithin, isDisabled && inputWrapperStyles.disabled, variant === 'ghost' && isDisabled && styles.triggerGhostDisabled, !selectedItem && styles.triggerPlaceholder, variant !== 'ghost' && status && inputStatusBorderStyles[status.type], variant !== 'ghost' && status && !isDisabled && inputStatusHoverShadowStyles[status.type], variant !== 'ghost' && inputGroup && groupStyles.inGroup, xstyle), className, style),
850
+ }), stylex.props(inputWrapperStyles.base, styles.triggerContainer, sizeStyles[size], variant === 'ghost' && styles.triggerGhost, variant === 'ghost' && focusOutlineStyles.focusWithin, isDisabled && inputWrapperStyles.disabled, variant === 'ghost' && isDisabled && styles.triggerGhostDisabled, !selectedItem && styles.triggerPlaceholder, variant !== 'ghost' && status && inputStatusBorderStyles[status.type], variant !== 'ghost' && status && !isDisabled && inputStatusHoverShadowStyles[status.type], variant !== 'ghost' && inputGroup && groupStyles.inGroup, inputGroup && styles.triggerInGroup, xstyle), className, style),
791
851
  children: [startIcon && renderIconSlot(startIcon, {
792
852
  size: 'sm',
793
853
  color: 'secondary'
@@ -822,14 +882,14 @@ export function Selector(props) {
822
882
  onKeyDown: handleTriggerKeyDown,
823
883
  tabIndex: isDisabled && !showsDisabledMessage ? -1 : 0,
824
884
  ...{
825
- className: "x78zum5 x6s0dn4 x1qughib x1txdalj x1iyjqo2 xs83m0k x1r8uery xeuugli x1717udv x1ghz6dp xc342km xng3xce xjbqb8w xjb2p0i x1qlqyl8 x15bjb6t x1heor9g x1ypdohk x1a2a7pz"
826
- },
827
- children: /*#__PURE__*/_jsx("span", {
828
- ...{
829
- className: "x1iyjqo2 xeuugli xb3r6kr xlyipyv xuxw1ft x1yc453h"
885
+ 0: {
886
+ className: "x78zum5 x6s0dn4 x1qughib x1txdalj x1iyjqo2 xs83m0k x1r8uery xeuugli x1717udv x1ghz6dp xc342km xng3xce xjbqb8w xjb2p0i x1qlqyl8 x15bjb6t x1heor9g x1ypdohk x1a2a7pz"
830
887
  },
831
- children: selectedItem?.label ?? placeholder
832
- })
888
+ 1: {
889
+ className: "x78zum5 x6s0dn4 x1qughib x1txdalj x1iyjqo2 xs83m0k x1r8uery xeuugli x1717udv x1ghz6dp xc342km xng3xce xjbqb8w xjb2p0i x1qlqyl8 x15bjb6t x1heor9g x1ypdohk x1a2a7pz xkh2ocl"
890
+ }
891
+ }[!!inputGroup << 0],
892
+ children: valueContent
833
893
  }), htmlName != null && /*#__PURE__*/_jsx("input", {
834
894
  type: "hidden",
835
895
  name: htmlName,
@@ -21,6 +21,19 @@ export interface SelectorOptionProps {
21
21
  * Secondary description text displayed below the label.
22
22
  */
23
23
  description?: ReactNode;
24
+ /**
25
+ * How the label and description sit together. `stacked` puts the
26
+ * description on its own line below the label; `inline` keeps both on one
27
+ * line, with the description ellipsizing first.
28
+ *
29
+ * In a Selector trigger this is the caller's choice and the trigger sizes
30
+ * itself to it — one line at the size token, two lines exactly one text line
31
+ * taller. Inside an `InputGroup` the row height is pinned by the group, so
32
+ * `inline` is forced.
33
+ *
34
+ * @default 'stacked'
35
+ */
36
+ layout?: 'stacked' | 'inline';
24
37
  /**
25
38
  * Additional content to render after the label/description.
26
39
  */
@@ -70,7 +83,7 @@ export interface SelectorOptionProps {
70
83
  * />
71
84
  * ```
72
85
  */
73
- export declare function SelectorOption({ icon, label, description, endContent, xstyle, className, style, }: SelectorOptionProps): import("react").JSX.Element;
86
+ export declare function SelectorOption({ icon, label, description, layout, endContent, xstyle, className, style, }: SelectorOptionProps): import("react").JSX.Element;
74
87
  export declare namespace SelectorOption {
75
88
  var displayName: string;
76
89
  }
@@ -1 +1 @@
1
- {"version":3,"file":"SelectorOption.d.ts","sourceRoot":"","sources":["../../src/Selector/SelectorOption.tsx"],"names":[],"mappings":"AAEA;;;;;;GAMG;AAEH,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,OAAO,CAAC;AAErC,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AACnD,OAAO,EAAiB,KAAK,QAAQ,EAAC,MAAM,SAAS,CAAC;AAatD,MAAM,WAAW,mBAAmB;IAClC;;OAEG;IACH,IAAI,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;IAE5B;;OAEG;IACH,KAAK,EAAE,SAAS,CAAC;IAEjB;;OAEG;IACH,WAAW,CAAC,EAAE,SAAS,CAAC;IAExB;;OAEG;IACH,UAAU,CAAC,EAAE,SAAS,CAAC;IAEvB;;;;;;;;;OASG;IACH,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB;;;OAGG;IACH,KAAK,CAAC,EAAE,KAAK,CAAC,aAAa,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,cAAc,CAAC,EAC7B,IAAI,EACJ,KAAK,EACL,WAAW,EACX,UAAU,EACV,MAAM,EACN,SAAS,EACT,KAAK,GACN,EAAE,mBAAmB,+BAerB;yBAvBe,cAAc"}
1
+ {"version":3,"file":"SelectorOption.d.ts","sourceRoot":"","sources":["../../src/Selector/SelectorOption.tsx"],"names":[],"mappings":"AAEA;;;;;;GAMG;AAEH,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,OAAO,CAAC;AAErC,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AACnD,OAAO,EAAiB,KAAK,QAAQ,EAAC,MAAM,SAAS,CAAC;AActD,MAAM,WAAW,mBAAmB;IAClC;;OAEG;IACH,IAAI,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;IAE5B;;OAEG;IACH,KAAK,EAAE,SAAS,CAAC;IAEjB;;OAEG;IACH,WAAW,CAAC,EAAE,SAAS,CAAC;IAExB;;;;;;;;;;;OAWG;IACH,MAAM,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;IAE9B;;OAEG;IACH,UAAU,CAAC,EAAE,SAAS,CAAC;IAEvB;;;;;;;;;OASG;IACH,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB;;;OAGG;IACH,KAAK,CAAC,EAAE,KAAK,CAAC,aAAa,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,cAAc,CAAC,EAC7B,IAAI,EACJ,KAAK,EACL,WAAW,EACX,MAAM,EACN,UAAU,EACV,MAAM,EACN,SAAS,EACT,KAAK,GACN,EAAE,mBAAmB,+BAoBrB;yBA7Be,cAAc"}
@@ -11,6 +11,7 @@
11
11
  import * as stylex from '@stylexjs/stylex';
12
12
  import { renderIconSlot } from "../Icon/index.js";
13
13
  import { Item } from "../Item/index.js";
14
+ import { useSelectorRowLayout } from "./SelectorRowLayoutContext.js";
14
15
  import { mergeProps } from "../utils/index.js";
15
16
  import { themeProps } from "../utils/themeProps.js";
16
17
  import { jsx as _jsx } from "react/jsx-runtime";
@@ -49,11 +50,15 @@ export function SelectorOption({
49
50
  icon,
50
51
  label,
51
52
  description,
53
+ layout,
52
54
  endContent,
53
55
  xstyle,
54
56
  className,
55
57
  style
56
58
  }) {
59
+ // A height-pinned host (the trigger inside an InputGroup) overrides the
60
+ // caller's choice: the row physically cannot be two lines there.
61
+ const enforcedLayout = useSelectorRowLayout();
57
62
  return /*#__PURE__*/_jsx(Item, {
58
63
  startContent: icon ? renderIconSlot(icon, {
59
64
  size: 'sm',
@@ -61,6 +66,7 @@ export function SelectorOption({
61
66
  }) : undefined,
62
67
  label: label,
63
68
  description: description,
69
+ layout: enforcedLayout === 'inline' ? 'inline' : layout,
64
70
  endContent: endContent,
65
71
  xstyle: [embeddedStyles.root, xstyle],
66
72
  ...mergeProps(themeProps('selector-option'), {
@@ -0,0 +1,8 @@
1
+ export type SelectorRowLayout = 'stacked' | 'inline';
2
+ export declare const SelectorRowLayoutContext: import("react").Context<SelectorRowLayout>;
3
+ /**
4
+ * The row layout a host imposes on the options it renders. `stacked` outside
5
+ * any height-pinned host.
6
+ */
7
+ export declare function useSelectorRowLayout(): SelectorRowLayout;
8
+ //# sourceMappingURL=SelectorRowLayoutContext.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SelectorRowLayoutContext.d.ts","sourceRoot":"","sources":["../../src/Selector/SelectorRowLayoutContext.ts"],"names":[],"mappings":"AAmBA,MAAM,MAAM,iBAAiB,GAAG,SAAS,GAAG,QAAQ,CAAC;AAErD,eAAO,MAAM,wBAAwB,4CACQ,CAAC;AAG9C;;;GAGG;AACH,wBAAgB,oBAAoB,IAAI,iBAAiB,CAExD"}
@@ -0,0 +1,27 @@
1
+ // Copyright (c) Meta Platforms, Inc. and affiliates.
2
+
3
+ 'use client';
4
+
5
+ /**
6
+ * @file SelectorRowLayoutContext.ts
7
+ * @input React createContext/use
8
+ * @output Exports the row-layout context and useSelectorRowLayout hook
9
+ * @position Internal to the Selector module; read by SelectorOption
10
+ *
11
+ * The trigger inside an InputGroup is height-pinned by the group, so its value
12
+ * box is clamped to one line and anything taller is cut off at the fold. This
13
+ * context is how the rows the system draws itself avoid being cut: they reflow
14
+ * label and description onto that one line instead. The geometry does not
15
+ * depend on it — a node that ignores this context still cannot grow the row.
16
+ */
17
+ import { createContext, use } from 'react';
18
+ export const SelectorRowLayoutContext = /*#__PURE__*/createContext('stacked');
19
+ SelectorRowLayoutContext.displayName = 'SelectorRowLayoutContext';
20
+
21
+ /**
22
+ * The row layout a host imposes on the options it renders. `stacked` outside
23
+ * any height-pinned host.
24
+ */
25
+ export function useSelectorRowLayout() {
26
+ return use(SelectorRowLayoutContext);
27
+ }
@@ -11,6 +11,7 @@ import type { IconType } from '../Icon';
11
11
  export type SelectorOptionData = {
12
12
  value: string;
13
13
  label?: string;
14
+ description?: ReactNode;
14
15
  disabled?: boolean;
15
16
  icon?: ReactNode | IconType;
16
17
  };
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/Selector/types.ts"],"names":[],"mappings":"AAEA;;;;GAIG;AAEH,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,OAAO,CAAC;AACrC,OAAO,KAAK,EAAC,QAAQ,EAAC,MAAM,SAAS,CAAC;AAEtC;;GAEG;AACH,MAAM,MAAM,kBAAkB,GAAG;IAC/B,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,IAAI,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;CAC7B,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,eAAe,GAAG;IAC5B,IAAI,EAAE,SAAS,CAAC;CACjB,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,eAAe,GAAG;IAC5B,IAAI,EAAE,SAAS,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,kBAAkB,EAAE,CAAC;CAC/B,CAAC;AAEF;;;GAGG;AACH,MAAM,MAAM,kBAAkB,GAC1B,MAAM,GACN,kBAAkB,GAClB,eAAe,GACf,eAAe,CAAC"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/Selector/types.ts"],"names":[],"mappings":"AAEA;;;;GAIG;AAEH,OAAO,KAAK,EAAC,SAAS,EAAC,MAAM,OAAO,CAAC;AACrC,OAAO,KAAK,EAAC,QAAQ,EAAC,MAAM,SAAS,CAAC;AAEtC;;GAEG;AACH,MAAM,MAAM,kBAAkB,GAAG;IAC/B,KAAK,EAAE,MAAM,CAAC;IAGd,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,SAAS,CAAC;IACxB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,IAAI,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;CAC7B,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,eAAe,GAAG;IAC5B,IAAI,EAAE,SAAS,CAAC;CACjB,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,eAAe,GAAG;IAC5B,IAAI,EAAE,SAAS,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,kBAAkB,EAAE,CAAC;CAC/B,CAAC;AAEF;;;GAGG;AACH,MAAM,MAAM,kBAAkB,GAC5B,MAAM,GAAG,kBAAkB,GAAG,eAAe,GAAG,eAAe,CAAC"}
package/dist/astryx.css CHANGED
@@ -451,6 +451,9 @@
451
451
  .xish69e:not(#\#):not(#\#){overscroll-behavior:contain}
452
452
  .x8du1vd:not(#\#):not(#\#){overscroll-behavior:none}
453
453
  .xt970qd:not(#\#):not(#\#){padding-block:0}
454
+ .x1vn5h1t:not(#\#):not(#\#){padding-block:calc((var(--size-element-lg) - var(--spacing-5) - 2 * var(--border-width)) / 2)}
455
+ .x1ioay2v:not(#\#):not(#\#){padding-block:calc((var(--size-element-md) - var(--spacing-5) - 2 * var(--border-width)) / 2)}
456
+ .x1ecmfrv:not(#\#):not(#\#){padding-block:calc((var(--size-element-sm) - var(--spacing-5) - 2 * var(--border-width)) / 2)}
454
457
  .x1x7cmac:not(#\#):not(#\#){padding-block:calc(var(--spacing-1) - 1px)}
455
458
  .xwo4yc8:not(#\#):not(#\#){padding-block:calc(var(--tree-list-row-gap,0px) / 2)}
456
459
  .x13f7esw:not(#\#):not(#\#){padding-block:var(--spacing-0-5)}
@@ -636,6 +639,7 @@
636
639
  .x1q8g9m5:not(#\#):not(#\#):not(#\#){background-color:var(--color-warning)}
637
640
  .x1fd97le:not(#\#):not(#\#):not(#\#){background-color:var(--table-sticky-background,var(--color-background-card))}
638
641
  .xl8spv7:not(#\#):not(#\#):not(#\#){background-color:var(--x-backgroundColor)}
642
+ .xafqdz2:not(#\#):not(#\#):not(#\#){background-image:linear-gradient(to bottom,var(--color-background-surface) 60%,transparent)}
639
643
  .x1vrk509:not(#\#):not(#\#):not(#\#){background-image:linear-gradient(var(--color-background-muted),var(--color-background-muted))}
640
644
  .x14bno8m:not(#\#):not(#\#):not(#\#){background-image:linear-gradient(var(--color-neutral),var(--color-neutral))}
641
645
  .x18o3ruo:not(#\#):not(#\#):not(#\#){background-image:none}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@astryxdesign/core",
3
- "version": "0.4.5-canary.e238799",
3
+ "version": "0.4.5-canary.ffd05c4",
4
4
  "displayName": "Astryx Core",
5
5
  "description": "The component library. Accessible, themeable React components with built-in spacing, dark mode, and StyleX styling.",
6
6
  "author": "Meta Open Source",
@@ -656,7 +656,7 @@
656
656
  "react-dom": ">=19.0.0"
657
657
  },
658
658
  "devDependencies": {
659
- "@astryxdesign/cli": "0.4.5-canary.e238799",
659
+ "@astryxdesign/cli": "0.4.5-canary.ffd05c4",
660
660
  "@babel/cli": "^8.0.4",
661
661
  "@babel/core": "^7.29.7",
662
662
  "@babel/preset-react": "^8.0.1",
@@ -237,4 +237,45 @@ describe('BottomSheetPanel', () => {
237
237
  expect(panelRef).toHaveBeenLastCalledWith(null);
238
238
  expect(panelRef).toHaveBeenCalledTimes(2);
239
239
  });
240
+
241
+ it('floats the handle bar over content that starts at the sheet top edge', () => {
242
+ renderPanel({kind: 'open', entering: false});
243
+
244
+ const bar = getPanel().querySelector<HTMLElement>(
245
+ 'div[aria-hidden="true"]',
246
+ );
247
+ if (bar == null) {
248
+ throw new Error('handle bar not found');
249
+ }
250
+ const body = bar.nextElementSibling as HTMLElement;
251
+
252
+ // Out of flow: the bar costs the content no layout space. That is the
253
+ // point of it -- the content sits closer to the sheet's top edge, and
254
+ // scrolled content passes beneath the pill rather than stopping at a
255
+ // hard edge.
256
+ expect(getComputedStyle(bar).position).toBe('absolute');
257
+
258
+ // So the body must not reserve room for it. A top padding here would
259
+ // push the content back down and undo the change.
260
+ expect(getComputedStyle(body).paddingTop).toBe('');
261
+ });
262
+
263
+ // The pill is only legible over the content riding up beneath it because
264
+ // the bar carries a backdrop; without it, text runs straight through the
265
+ // pill. jsdom's StyleX runtime does not inject the rule, so assert on the
266
+ // style definition itself (same approach as AspectRatio's reset.css tests).
267
+ it('backs the floating handle bar with a surface gradient', async () => {
268
+ const fs = await import('fs');
269
+ const path = await import('path');
270
+ const source = fs.readFileSync(
271
+ path.resolve(__dirname, './BottomSheetPanel.tsx'),
272
+ 'utf-8',
273
+ );
274
+
275
+ const handleBar = source.match(/handleBar: \{([\s\S]*?)\n {2}\},/);
276
+ expect(handleBar).not.toBeNull();
277
+ expect(handleBar![1]).toContain("position: 'absolute'");
278
+ expect(handleBar![1]).toContain('linear-gradient(to bottom');
279
+ expect(handleBar![1]).toContain("colorVars['--color-background-surface']");
280
+ });
240
281
  });