@hjmds/react 1.39.0 → 1.41.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.
@@ -1 +1 @@
1
- {"version":3,"file":"reaction-picker.js","sourceRoot":"","sources":["../src/reaction-picker.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAC1D,OAAO,EAAE,YAAY,EAAE,iBAAiB,EAAE,sBAAsB,EAAiD,MAAM,mCAAmC,CAAC;AAC3J,OAAO,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAGtC,gFAAgF;AAChF,MAAM,UAAU,cAAc,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,aAAa,EAAE,QAAQ,GAAG,KAAK,EAAE,MAAM,GAAG,MAAM,EAAE,IAAI,EAAE,WAAW,EAAuB;IAChJ,MAAM,CAAC,QAAQ,EAAE,WAAW,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IAChD,MAAM,IAAI,GAAG,MAAM,CAAiB,IAAI,CAAC,CAAC;IAC1C,MAAM,MAAM,GAAG,MAAM,CAAoB,IAAI,CAAC,CAAC;IAC/C,MAAM,OAAO,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC;IAC9B,MAAM,GAAG,GAAG,sBAAsB,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC;IAClD,iBAAiB,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;IAC9B,MAAM,UAAU,GAAG,QAAQ,IAAI,CAAC,CAAC,IAAI,CAAC;IACtC,+GAA+G;IAC/G,6GAA6G;IAC7G,+GAA+G;IAC/G,kGAAkG;IAClG,MAAM,KAAK,GAAG,MAAM,KAAK,MAAM,CAAC;IAChC,MAAM,OAAO,GAAG,UAAU,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,OAAO,CAAC;IAC3C,MAAM,MAAM,GAAG,CAAC,EAAU,EAAE,EAAE,GAAG,IAAI,CAAC,QAAQ,EAAE,CAAC;QAAC,OAAO,CAAC,OAAO,GAAG,CAAC,CAAC,IAAI,CAAC,OAAO,EAAE,QAAQ,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC;QAAC,aAAa,CAAC,YAAY,CAAC,GAAG,EAAE,KAAK,EAAE,EAAE,CAAC,CAAC,CAAC;QAAC,WAAW,CAAC,KAAK,CAAC,CAAC;IAAC,CAAC,CAAC,CAAC,CAAC;IAC3L,qHAAqH;IACrH,eAAe,CAAC,GAAG,EAAE,GAAG,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,CAAC,CAAC,IAAI,OAAO,CAAC,OAAO,IAAI,CAAC,UAAU,IAAI,IAAI,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,aAAa,CAAC;QAAE,MAAM,CAAC,OAAO,EAAE,KAAK,EAAE,CAAC,CAAC,OAAO,CAAC,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1N,OAAO,eAAK,GAAG,EAAE,IAAI,EAAE,IAAI,EAAC,OAAO,gBAAa,KAAK,EAAE,SAAS,EAAC,qBAAqB,iBAAc,MAAM,mBAAiB,UAAU,IAAI,SAAS,EAAE,KAAK,EAAE,WAAW,aACpK,cAAK,SAAS,EAAC,8BAA8B,YAC1C,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE;oBACpB,MAAM,KAAK,GAAG,+BAAkB,MAAM,EAAC,SAAS,EAAC,4BAA4B,aAAE,MAAM,CAAC,KAAK,EAAE,MAAM,CAAC,KAAK,KAAK,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,MAAM,CAAC,KAAK,EAAE,IAAQ,CAAC;oBAC5J,MAAM,QAAQ,GAAG,KAAK,KAAK,MAAM,CAAC,EAAE,CAAC;oBACrC,OAAO,KAAK;wBACV,CAAC,CAAC,iBAAwB,IAAI,EAAC,QAAQ,EAAC,SAAS,EAAC,oCAAoC,eAAW,OAAO,mBAAgB,QAAQ,IAAI,SAAS,kBAAgB,QAAQ,EAAE,QAAQ,EAAE,QAAQ,IAAI,MAAM,CAAC,QAAQ,gBAAc,MAAM,CAAC,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC,YAAG,KAAK,IAAjQ,MAAM,CAAC,EAAE,CAAkQ;wBAC1R,CAAC,CAAC,KAAC,MAAM,IAAiB,IAAI,EAAC,OAAO,EAAC,KAAK,EAAC,MAAM,EAAC,QAAQ,EAAE,QAAQ,EAAE,QAAQ,EAAE,QAAQ,IAAI,MAAM,CAAC,QAAQ,gBAAc,MAAM,CAAC,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC,YAAG,KAAK,IAAlK,MAAM,CAAC,EAAE,CAAmK,CAAC;gBAChM,CAAC,CAAC,GACE,EACN,wBAAM,IAAI,CAAC,CAAC,CAAC,KAAK;oBAChB,CAAC,CAAC,iBAAQ,GAAG,EAAE,MAAM,EAAE,IAAI,EAAC,QAAQ,EAAC,SAAS,EAAC,oCAAoC,eAAW,OAAO,gBAAa,IAAI,CAAC,KAAK,mBAAiB,UAAU,EAAE,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,WAAW,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,OAAO,CAAC,YAAE,8BAAkB,MAAM,EAAC,SAAS,EAAC,4BAA4B,YAAE,UAAU,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,GAAQ,GAAS;oBACtU,CAAC,CAAC,KAAC,MAAM,IAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAC,OAAO,EAAC,KAAK,EAAC,MAAM,gBAAa,IAAI,CAAC,KAAK,mBAAiB,UAAU,EAAE,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,WAAW,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,OAAO,CAAC,YAAE,8BAAkB,MAAM,EAAC,SAAS,EAAC,4BAA4B,YAAE,UAAU,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,GAAQ,GAAS,CAAC,CAAC,CAAC,IAAI,GAAO,IAC7R,CAAC;AACT,CAAC","sourcesContent":["import { useLayoutEffect, useRef, useState } from \"react\";\nimport { nextReaction, validateReactions, resolveReactionOptions, type ReactionMoreOptions, type ReactionOption } from \"@hjmds/design-contracts/reactions\";\nimport { Button } from \"./actions.js\";\nimport type { HjmCompositionStyleProp } from \"./composition-style.js\";\nexport type ReactionPickerProps = Readonly<{ label: string; options: readonly ReactionOption[]; value: string | null; onValueChange: (value: string | null) => void; disabled?: boolean; layout?: \"wrap\" | \"strip\"; layoutStyle?: HjmCompositionStyleProp; more?: ReactionMoreOptions }>;\n/** Controlled single reaction; counts and persistence belong to the product. */\nexport function ReactionPicker({ label, options, value, onValueChange, disabled = false, layout = \"wrap\", more, layoutStyle }: ReactionPickerProps) {\n const [expanded, setExpanded] = useState(false);\n const root = useRef<HTMLDivElement>(null);\n const toggle = useRef<HTMLButtonElement>(null);\n const refocus = useRef(false);\n const all = resolveReactionOptions(options, more);\n validateReactions(all, value);\n const showingAll = expanded && !!more;\n // The wrap layout sits on the page background, where a ghost Button's selected treatment (content color on the\n // canvas) cannot show: an emoji ignores text color. It uses the chip frame instead — hairline at rest, brand\n // border and accent fill when chosen — with toggle-button semantics (aria-pressed), matching Native. The strip\n // layout keeps ghost Buttons because the message bubble supplies its surface (2026-10-17 review).\n const chips = layout === \"wrap\";\n const visible = showingAll ? all : options;\n const choose = (id: string) => { if (!disabled) { refocus.current = !!root.current?.contains(document.activeElement); onValueChange(nextReaction(all, value, id)); setExpanded(false); } };\n // A catalog-only button unmounts on collapse: refocus the toggle, not <body>. Inert hosts restore their own trigger.\n useLayoutEffect(() => { const node = root.current; if (refocus.current && !showingAll && node && !node.closest(\"[inert]\") && !node.contains(document.activeElement)) toggle.current?.focus(); refocus.current = false; });\n return <div ref={root} role=\"group\" aria-label={label} className=\"hjm-reaction-picker\" data-layout={layout} data-expanded={showingAll || undefined} style={layoutStyle}>\n <div className=\"hjm-reaction-picker__options\">\n {visible.map(option => {\n const glyph = <span aria-hidden=\"true\" className=\"hjm-reaction-picker__glyph\">{option.emoji}{option.count === undefined ? null : ` ${option.count}`}</span>;\n const selected = value === option.id;\n return chips\n ? <button key={option.id} type=\"button\" className=\"hjm-chip hjm-reaction-picker__chip\" data-size=\"small\" data-selected={selected || undefined} aria-pressed={selected} disabled={disabled || option.disabled} aria-label={option.label} onClick={() => choose(option.id)}>{glyph}</button>\n : <Button key={option.id} tone=\"ghost\" shape=\"pill\" selected={selected} disabled={disabled || option.disabled} aria-label={option.label} onClick={() => choose(option.id)}>{glyph}</Button>;\n })}\n </div>\n <div>{more ? chips\n ? <button ref={toggle} type=\"button\" className=\"hjm-chip hjm-reaction-picker__chip\" data-size=\"small\" aria-label={more.label} aria-expanded={showingAll} disabled={disabled} onClick={() => setExpanded(current => !current)}><span aria-hidden=\"true\" className=\"hjm-reaction-picker__glyph\">{showingAll ? \"−\" : \"+\"}</span></button>\n : <Button ref={toggle} tone=\"ghost\" shape=\"pill\" aria-label={more.label} aria-expanded={showingAll} disabled={disabled} onClick={() => setExpanded(current => !current)}><span aria-hidden=\"true\" className=\"hjm-reaction-picker__glyph\">{showingAll ? \"−\" : \"+\"}</span></Button> : null}</div>\n </div>;\n}\n"]}
1
+ {"version":3,"file":"reaction-picker.js","sourceRoot":"","sources":["../src/reaction-picker.tsx"],"names":[],"mappings":"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","sourcesContent":["import { useLayoutEffect, useRef, useState } from \"react\";\nimport { nextReaction, validateReactions, resolveReactionOptions, type ReactionMoreOptions, type ReactionOption } from \"@hjmds/design-contracts/reactions\";\nimport { Button } from \"./actions.js\";\nimport type { HjmCompositionStyleProp } from \"./composition-style.js\";\nexport type ReactionPickerProps = Readonly<{ label: string; options: readonly ReactionOption[]; value: string | null; onValueChange: (value: string | null) => void; disabled?: boolean; layout?: \"wrap\" | \"strip\"; layoutStyle?: HjmCompositionStyleProp; more?: ReactionMoreOptions }>;\n/** Controlled single reaction; counts and persistence belong to the product. */\nexport function ReactionPicker({ label, options, value, onValueChange, disabled = false, layout = \"wrap\", more, layoutStyle }: ReactionPickerProps) {\n const [expanded, setExpanded] = useState(false);\n const root = useRef<HTMLDivElement>(null);\n const toggle = useRef<HTMLButtonElement>(null);\n const refocus = useRef(false);\n const all = resolveReactionOptions(options, more);\n validateReactions(all, value);\n const showingAll = expanded && !!more;\n // Wrap reactions keep Chip's compact frame for counted emoji; strip reactions use ghost Buttons.\n // Both resolve the same neutral selected surface because emoji cannot communicate a text-color change.\n const chips = layout === \"wrap\";\n const visible = showingAll ? all : options;\n const choose = (id: string) => { if (!disabled) { refocus.current = !!root.current?.contains(document.activeElement); onValueChange(nextReaction(all, value, id)); setExpanded(false); } };\n // A catalog-only button unmounts on collapse: refocus the toggle, not <body>. Inert hosts restore their own trigger.\n useLayoutEffect(() => { const node = root.current; if (refocus.current && !showingAll && node && !node.closest(\"[inert]\") && !node.contains(document.activeElement)) toggle.current?.focus(); refocus.current = false; });\n return <div ref={root} role=\"group\" aria-label={label} className=\"hjm-reaction-picker\" data-layout={layout} data-expanded={showingAll || undefined} style={layoutStyle}>\n <div className=\"hjm-reaction-picker__options\">\n {visible.map(option => {\n const glyph = <span aria-hidden=\"true\" className=\"hjm-reaction-picker__glyph\">{option.emoji}{option.count === undefined ? null : ` ${option.count}`}</span>;\n const selected = value === option.id;\n return chips\n ? <button key={option.id} type=\"button\" className=\"hjm-chip hjm-reaction-picker__chip\" data-size=\"small\" data-selected={selected || undefined} aria-pressed={selected} disabled={disabled || option.disabled} aria-label={option.label} onClick={() => choose(option.id)}>{glyph}</button>\n : <Button key={option.id} tone=\"ghost\" shape=\"pill\" selected={selected} disabled={disabled || option.disabled} aria-label={option.label} onClick={() => choose(option.id)}>{glyph}</Button>;\n })}\n </div>\n <div>{more ? chips\n ? <button ref={toggle} type=\"button\" className=\"hjm-chip hjm-reaction-picker__chip\" data-size=\"small\" aria-label={more.label} aria-expanded={showingAll} disabled={disabled} onClick={() => setExpanded(current => !current)}><span aria-hidden=\"true\" className=\"hjm-reaction-picker__glyph\">{showingAll ? \"−\" : \"+\"}</span></button>\n : <Button ref={toggle} tone=\"ghost\" shape=\"pill\" aria-label={more.label} aria-expanded={showingAll} disabled={disabled} onClick={() => setExpanded(current => !current)}><span aria-hidden=\"true\" className=\"hjm-reaction-picker__glyph\">{showingAll ? \"−\" : \"+\"}</span></Button> : null}</div>\n </div>;\n}\n"]}
package/dist/styles.css CHANGED
@@ -1,4 +1,4 @@
1
- /* Broad neutral and pale-brand surfaces use the theme canvas. Selection stays visible through borders; primary actions and compact state marks retain their semantic fills. */
1
+ /* Persistent selection uses its neutral surface. Focus, primary actions and compact value marks retain their distinct semantic roles; see theme-palette.md. */
2
2
  .hjm-root,
3
3
  .hjm-root *,
4
4
  .hjm-root *::before,
@@ -268,7 +268,7 @@
268
268
  /* Toggle treatment: aria-pressed already carried the state, so without a paired
269
269
  visual every consumer painted the selected background in product styles.
270
270
  Selection uses content color without an added border (2026-10-10 user request); focus stays separate. */
271
- .hjm-button[data-selected="true"], .hjm-icon-button[data-selected="true"] { color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); border-color: transparent; }
271
+ .hjm-button[data-selected="true"], .hjm-icon-button[data-selected="true"] { color: var(--hjm-color-text); background: var(--hjm-color-surface-selected); border-color: transparent; }
272
272
  .hjm-button:active:not(:disabled):not([aria-disabled="true"]), .hjm-icon-button:active:not(:disabled):not([aria-disabled="true"]) { opacity: var(--hjm-button-pressed-opacity); }
273
273
  /* data-state="disabled" also covers focusable boundaries (aria-disabled, e.g. Carousel previous on the first slide),
274
274
  which looked enabled while Native dimmed them (2026-10-17 review E9). */
@@ -287,7 +287,7 @@
287
287
  .hjm-button[data-tone="primary"] { --hjm-button-face-fill: var(--hjm-color-primary); }
288
288
  .hjm-button[data-tone="secondary"] { --hjm-button-face-fill: var(--hjm-color-bg); --hjm-button-face-border: var(--hjm-color-border-control); }
289
289
  .hjm-button[data-tone="danger"] { --hjm-button-face-fill: var(--hjm-color-danger-fill); }
290
- .hjm-button[data-selected="true"] { --hjm-button-face-fill: var(--hjm-color-bg); --hjm-button-face-border: transparent; }
290
+ .hjm-button[data-selected="true"] { --hjm-button-face-fill: var(--hjm-color-surface-selected); --hjm-button-face-border: transparent; }
291
291
  .hjm-button[data-raised="true"] { padding: 0 0 var(--hjm-button-depth); border: 0; gap: 0; flex-direction: column; background: color-mix(in srgb, var(--hjm-button-side), #000 var(--hjm-button-side-shade)); }
292
292
  .hjm-button__face { position: relative; display: flex; box-sizing: border-box; inline-size: 100%; min-block-size: inherit; flex: 1; align-items: center; justify-content: inherit; gap: var(--hjm-space-xs); padding: var(--hjm-space-xs) var(--hjm-button-face-padding); border: 1px solid var(--hjm-button-face-border, transparent); border-radius: inherit; background: var(--hjm-button-face-fill); transition: transform var(--hjm-button-settle) ease-out; }
293
293
  .hjm-button[data-raised="true"]:active:not(:disabled):not([aria-disabled="true"]) { opacity: 1; }
@@ -813,7 +813,7 @@
813
813
  .hjm-choice[data-presentation="card"][data-state="checked"],
814
814
  .hjm-choice[data-presentation="card"][data-state="mixed"],
815
815
  .hjm-choice[data-presentation="grouped"][data-state="checked"],
816
- .hjm-choice[data-presentation="grouped"][data-state="mixed"] { border-color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); }
816
+ .hjm-choice[data-presentation="grouped"][data-state="mixed"] { border-color: var(--hjm-color-border-control); background: var(--hjm-color-surface-selected); }
817
817
  .hjm-choice[data-size="small"] { min-block-size: 44px; gap: var(--hjm-space-xs); padding: var(--hjm-space-xs) var(--hjm-space-sm); }
818
818
  .hjm-choice[data-size="small"][data-presentation="plain"] { padding: 0; }
819
819
  .hjm-choice__input { position: absolute; opacity: 0; inline-size: 1px; block-size: 1px; }
@@ -881,7 +881,7 @@
881
881
  .hjm-choice[data-presentation="chips"] .hjm-choice__indicator { display: none; }
882
882
  .hjm-choice[data-presentation="chips"] .hjm-choice__leading { color: inherit; }
883
883
  .hjm-choice[data-presentation="chips"] .hjm-choice__copy { min-inline-size: 0; overflow-wrap: anywhere; padding-block: 0; }
884
- .hjm-choice[data-presentation="chips"][data-state="checked"], .hjm-choice[data-presentation="chips"][data-state="mixed"] { color: var(--hjm-color-content-brand); border-color: var(--hjm-color-content-brand); }
884
+ .hjm-choice[data-presentation="chips"][data-state="checked"], .hjm-choice[data-presentation="chips"][data-state="mixed"] { color: var(--hjm-color-text); border-color: var(--hjm-color-border-control); background: var(--hjm-color-surface-selected); }
885
885
  .hjm-choice[data-presentation="chips"]:has(.hjm-choice__input:focus-visible) { outline: var(--hjm-focus-width) solid var(--hjm-color-focus); outline-offset: var(--hjm-focus-offset); }
886
886
  /* A described switch: copy + switchRecipe.rowPaddingVertical 8 on both sides, min rowTwoLineMinHeight 56, same as Native.
887
887
  Stacked switch rows carry this spacing themselves; containers add no gap between them (2026-10-17). */
@@ -923,7 +923,7 @@
923
923
  /* Vertical only: neighbours are 4px apart, so a horizontal slop would overlap the next option's target. */
924
924
  .hjm-segmented:where(:not([data-presentation="pills"]):not([data-presentation="text"])) .hjm-segmented__item::after { content: ""; position: absolute; inset: calc((var(--hjm-segmented-height) - 2 * (var(--hjm-space-xxs) + 1px) - var(--hjm-control-min-touch-target)) / 2) 0; }
925
925
  .hjm-segmented__item input { position: absolute; opacity: 0; }
926
- .hjm-segmented__item[data-state="checked"] { box-shadow: inset 0 0 0 2px var(--hjm-color-focus); color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); font-weight: var(--hjm-font-weight-semibold); }
926
+ .hjm-segmented__item[data-state="checked"] { box-shadow: inset 0 0 0 2px var(--hjm-color-focus); color: var(--hjm-color-text); background: var(--hjm-color-surface-selected); font-weight: var(--hjm-font-weight-semibold); }
927
927
  .hjm-segmented__item[data-disabled="true"] { opacity: 0.5; cursor: not-allowed; }
928
928
 
929
929
  /* segmentedControlRecipe.adaptive.largeTextLayout stacks oversized labels, matching RN.
@@ -1037,7 +1037,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1037
1037
  .hjm-list-row[data-density="relaxed"][data-lines="two"] { min-block-size: var(--hjm-list-row-relaxed-two-line); }
1038
1038
  .hjm-list-row[data-density="spacious"] { --hjm-list-row-inline: var(--hjm-list-row-spacious-padding-inline); min-block-size: var(--hjm-list-row-spacious-one-line); padding-block: var(--hjm-list-row-spacious-padding-block); }
1039
1039
  .hjm-list-row[data-density="spacious"][data-lines="two"] { min-block-size: var(--hjm-list-row-spacious-two-line); }
1040
- .hjm-list-row[data-state="selected"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
1040
+ .hjm-list-row[data-state="selected"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
1041
1041
  .hjm-list-row[data-state="disabled"] { opacity: 0.5; cursor: not-allowed; }
1042
1042
  /* trailingAction: one surface for the row command and its separate action, as Native. The frame takes the bleed; the
1043
1043
  command keeps the start padding and the action the end padding, so the action box ends on the content edge (an
@@ -1046,7 +1046,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1046
1046
  .hjm-list-row-frame[data-density="compact"] { --hjm-list-row-inline: var(--hjm-list-row-compact-padding-inline); }
1047
1047
  .hjm-list-row-frame[data-density="relaxed"] { --hjm-list-row-inline: var(--hjm-list-row-relaxed-padding-inline); }
1048
1048
  .hjm-list-row-frame[data-density="spacious"] { --hjm-list-row-inline: var(--hjm-list-row-spacious-padding-inline); }
1049
- .hjm-list-row-frame[data-state="selected"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
1049
+ .hjm-list-row-frame[data-state="selected"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
1050
1050
  .hjm-list-row-frame[data-state="disabled"] { opacity: 0.5; }
1051
1051
  .hjm-list-row-frame > .hjm-list-row { flex: 1 1 auto; min-inline-size: 0; inline-size: auto; margin-inline: 0; padding-inline-end: 0; }
1052
1052
  .hjm-list-row-frame > .hjm-list-row[data-state] { background: transparent; box-shadow: none; opacity: 1; }
@@ -1104,7 +1104,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1104
1104
  .hjm-chip { position: relative; min-block-size: var(--hjm-control-min-touch-target); display: inline-flex; align-items: center; gap: var(--hjm-space-xs); padding-inline: var(--hjm-space-md); border: 1px solid var(--hjm-color-border); border-radius: 999px; background: var(--hjm-color-bg); color: var(--hjm-color-text-body); font: inherit; font-weight: var(--hjm-text-emphasis-medium); cursor: pointer; }
1105
1105
  .hjm-chip[data-size="small"] { min-block-size: 36px; padding-inline: var(--hjm-space-sm); gap: var(--hjm-space-xxs); }
1106
1106
  .hjm-chip[data-size="small"]::after { content: ""; position: absolute; inset: -4px 0; }
1107
- .hjm-chip[data-selected] { border-color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); color: var(--hjm-color-content-brand); }
1107
+ .hjm-chip[data-selected] { border-color: var(--hjm-color-border-control); background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); }
1108
1108
  .hjm-chip:disabled { opacity: 0.5; cursor: not-allowed; }
1109
1109
  .hjm-chip:focus-visible { outline: var(--hjm-focus-width) solid var(--hjm-color-focus); outline-offset: var(--hjm-focus-offset); }
1110
1110
  .hjm-chip__indicator, .hjm-chip__leading, .hjm-chip__trailing { display: inline-flex; flex: 0 0 auto; }
@@ -1611,7 +1611,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1611
1611
  /* Panel headings and empty-state copy share the same narrow column as rows. */
1612
1612
  .hjm-transfer-list__title,
1613
1613
  .hjm-transfer-list__empty { min-inline-size: 0; overflow-wrap: anywhere; }
1614
- .hjm-transfer-list__option[aria-selected="true"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
1614
+ .hjm-transfer-list__option[aria-selected="true"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
1615
1615
  .hjm-transfer-list__option[aria-disabled="true"] { color: var(--hjm-color-text-weak); }
1616
1616
  .hjm-transfer-list__option:focus-visible,
1617
1617
  .hjm-transfer-list__empty:focus-visible,
@@ -1973,9 +1973,9 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1973
1973
  }
1974
1974
  /* The pressed state is announced by aria-pressed; color only reinforces it. */
1975
1975
  .hjm-toggle-group__item[aria-pressed="true"] {
1976
- border-color: var(--hjm-color-focus);
1977
- background: var(--hjm-color-bg);
1978
- color: var(--hjm-color-content-brand);
1976
+ border-color: var(--hjm-color-border-control);
1977
+ background: var(--hjm-color-surface-selected);
1978
+ color: var(--hjm-color-text);
1979
1979
  font-weight: var(--hjm-text-emphasis-strong);
1980
1980
  }
1981
1981
  .hjm-toggle-group__item:disabled { cursor: default; color: var(--hjm-color-text-weak); }
@@ -2208,7 +2208,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2208
2208
  color: var(--hjm-color-text);
2209
2209
  cursor: default;
2210
2210
  }
2211
- .hjm-tree__node[aria-selected="true"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
2211
+ .hjm-tree__node[aria-selected="true"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
2212
2212
  .hjm-tree__node[aria-disabled="true"] { color: var(--hjm-color-text-weak); }
2213
2213
  .hjm-tree__node:focus-visible { outline: 2px solid var(--hjm-color-focus); outline-offset: -2px; }
2214
2214
  .hjm-tree__indent { flex: 0 0 auto; inline-size: calc(var(--hjm-tree-depth) * var(--hjm-tree-indent)); }
@@ -2482,6 +2482,8 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2482
2482
  .hjm-sheet[data-placement="bottom"] {
2483
2483
  inline-size: min(var(--hjm-sheet-max-width), 100%);
2484
2484
  max-block-size: var(--hjm-sheet-max-height);
2485
+ /* The bottom edge is docked to the viewport, not an exposed card perimeter. */
2486
+ border-block-end-width: 0;
2485
2487
  border-end-start-radius: 0;
2486
2488
  border-end-end-radius: 0;
2487
2489
  }
@@ -2672,7 +2674,8 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2672
2674
  .hjm-menu__item:hover,
2673
2675
  .hjm-menu__item[data-focus="true"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
2674
2676
  .hjm-menu__item[data-tone="danger"] { color: var(--hjm-color-danger); }
2675
- .hjm-menu__item[data-state="selected"] { color: var(--hjm-color-content-brand); font-weight: var(--hjm-text-emphasis-strong); }
2677
+ .hjm-menu__item[data-state="selected"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); font-weight: var(--hjm-text-emphasis-strong); }
2678
+ .hjm-menu__item[data-state="selected"][data-tone="danger"] { color: var(--hjm-color-danger); }
2676
2679
  .hjm-menu__item:disabled { opacity: 0.5; cursor: not-allowed; }
2677
2680
  .hjm-menu__state-message { min-block-size: var(--hjm-control-min-touch-target); display: flex; align-items: center; padding: var(--hjm-space-xs) var(--hjm-space-sm); color: var(--hjm-color-text-muted); overflow-wrap: anywhere; }
2678
2681
  .hjm-menu__section-label { padding: var(--hjm-space-xs) var(--hjm-space-sm); color: var(--hjm-color-text-muted); font-size: var(--hjm-type-label-size); font-weight: var(--hjm-text-emphasis-medium); }
@@ -2726,7 +2729,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2726
2729
  .hjm-select__listbox[data-density="comfortable"] .hjm-select__option { min-block-size: 3.5rem; }
2727
2730
  .hjm-select__option { cursor: pointer; }
2728
2731
  .hjm-select__option[data-active="true"] { box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); background: var(--hjm-color-bg); }
2729
- .hjm-select__option[data-state="selected"] { color: var(--hjm-color-content-brand); font-weight: var(--hjm-font-weight-semibold); }
2732
+ .hjm-select__option[data-state="selected"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); font-weight: var(--hjm-font-weight-semibold); }
2730
2733
  .hjm-select__option[data-state="disabled"] { opacity: 0.5; cursor: not-allowed; }
2731
2734
  .hjm-select__option-copy { min-inline-size: 0; flex: 1 1 auto; display: grid; gap: var(--hjm-space-xxs); }
2732
2735
  .hjm-select__option-description, .hjm-select__message { color: var(--hjm-color-text-muted); font-size: var(--hjm-type-label-size); }
@@ -2767,7 +2770,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2767
2770
  .hjm-combobox__listbox[data-density="comfortable"] .hjm-combobox__option { min-block-size: 3.5rem; }
2768
2771
  .hjm-combobox__option { cursor: pointer; }
2769
2772
  .hjm-combobox__option[data-state="active"] { box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); background: var(--hjm-color-bg); }
2770
- .hjm-combobox__option[data-state="selected"] { color: var(--hjm-color-content-brand); font-weight: var(--hjm-font-weight-semibold); }
2773
+ .hjm-combobox__option[aria-selected="true"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); font-weight: var(--hjm-font-weight-semibold); }
2771
2774
  .hjm-combobox__option[data-state="disabled"] { opacity: 0.5; cursor: not-allowed; }
2772
2775
  .hjm-combobox__message { color: var(--hjm-color-text-muted); }
2773
2776
  .hjm-form__fieldset { min-inline-size: 0; margin: 0; padding: 0; border: 0; }
@@ -3300,14 +3303,14 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
3300
3303
  .hjm-tabs:is([data-appearance="gooey"], [data-appearance="slide"]) .hjm-tabs__list { position: relative; }
3301
3304
  .hjm-tabs:is([data-appearance="gooey"], [data-appearance="slide"]) .hjm-tabs__tab[data-state="selected"]::after { display: none; }
3302
3305
  .hjm-tabs__indicator { position: absolute; bottom: 0; height: 2px; border-radius: var(--hjm-radius-full); background: var(--hjm-color-content-brand); pointer-events: none; }
3303
- /* indicator="filled" (tabsRecipe.indicators.filled): a surface-accent pill behind the selected tab, no list divider.
3306
+ /* indicator="filled" (tabsRecipe.indicators.filled): a neutral selection pill behind the selected tab, no list divider.
3304
3307
  The moving pill spans the tab height and sits under the labels. */
3305
3308
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__list { border: 0; }
3306
3309
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab { border-radius: var(--hjm-radius-full); }
3307
- .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab[data-state="selected"] { color: var(--hjm-color-content-brand); }
3310
+ .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab[data-state="selected"] { color: var(--hjm-color-text); }
3308
3311
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab[data-state="selected"]::after { display: none; }
3309
- .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]):not([data-indicator-motion="moving"]) .hjm-tabs__tab[data-state="selected"] { background: var(--hjm-color-surface-accent); }
3310
- .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__indicator { top: 0; bottom: 0; height: auto; border-radius: var(--hjm-radius-full); background: var(--hjm-color-surface-accent); z-index: 0; }
3312
+ .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]):not([data-indicator-motion="moving"]) .hjm-tabs__tab[data-state="selected"] { background: var(--hjm-color-surface-selected); }
3313
+ .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__indicator { top: 0; bottom: 0; height: auto; border-radius: var(--hjm-radius-full); background: var(--hjm-color-surface-selected); z-index: 0; }
3311
3314
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__list { position: relative; }
3312
3315
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab { z-index: 1; }
3313
3316
  .hjm-tabs__gooey { height: 6px; }
@@ -3330,7 +3333,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
3330
3333
  }
3331
3334
  .hjm-bottom-navigation[data-presentation="capsule"][data-expanded-labels="false"] .hjm-bottom-navigation__item { flex-direction: row; }
3332
3335
  .hjm-bottom-navigation[data-presentation="capsule"][data-expanded-labels="false"] .hjm-bottom-navigation__item:not([data-state="selected"]) .hjm-bottom-navigation__label { display: none; }
3333
- .hjm-bottom-navigation[data-presentation="capsule"] .hjm-bottom-navigation__item[data-state="selected"] { background: var(--hjm-color-surface-accent); }
3336
+ .hjm-bottom-navigation[data-presentation="capsule"]:not([data-selection="tile"]) .hjm-bottom-navigation__item[data-state="selected"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); }
3334
3337
  .hjm-bottom-navigation[data-presentation="capsule"] .hjm-bottom-navigation__primary-action { position: static; translate: none; flex-shrink: 0; }
3335
3338
  @media (prefers-reduced-motion: reduce) { .hjm-bottom-navigation[data-presentation="capsule"] .hjm-bottom-navigation__item { transition: none; } }
3336
3339
 
@@ -3605,9 +3608,8 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3605
3608
  /* Only the chat strip enlarges glyphs, to the title type step Native's strip uses. The default
3606
3609
  wrap layout keeps the button's own size, as published before the strip existed. */
3607
3610
  .hjm-reaction-picker[data-layout="strip"] .hjm-reaction-picker__glyph { font-size: var(--hjm-type-title-size); line-height: var(--hjm-type-title-line-height); }
3608
- /* Wrap reactions reuse the chip frame (chipRecipe). Emoji ignore the brand content color, so the chosen reaction
3609
- also takes the accent fill that Native's strip and wrap items use. */
3610
- .hjm-reaction-picker__chip[data-selected] { background: var(--hjm-color-surface-accent); }
3611
+ /* Emoji ignore text color; wrap and strip both retain the shared neutral selection fill. */
3612
+ .hjm-reaction-picker__chip[data-selected] { background: var(--hjm-color-surface-selected); }
3611
3613
 
3612
3614
  /* The embedded circle uses the small 36px recipe; centre it in the field rather than on the text baseline.
3613
3615
  Reduce only its trailing inset to 8px, preserving the text's 16px leading padding. */
@@ -3635,8 +3637,8 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3635
3637
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__item::before { content:""; position:absolute; inset:var(--hjm-space-xxs) 0; border-radius:var(--hjm-radius-full); background:var(--hjm-color-bg); border:1px solid var(--hjm-color-border-control); }
3636
3638
  .hjm-segmented[data-presentation="pills"][data-size="small"] .hjm-segmented__item { padding-inline:var(--hjm-space-sm); }
3637
3639
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__item > span { position:relative; overflow-wrap:anywhere; }
3638
- .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"] { color:var(--hjm-color-bg); font-weight:var(--hjm-font-weight-semibold); }
3639
- .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"]::before { background:var(--hjm-color-text-body); border-color:var(--hjm-color-text-body); }
3640
+ .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"] { color:var(--hjm-color-text); font-weight:var(--hjm-font-weight-semibold); }
3641
+ .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"]::before { background:var(--hjm-color-surface-selected); border-color:var(--hjm-color-surface-selected); }
3640
3642
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__item:focus-within { outline:2px solid var(--hjm-color-focus); outline-offset:2px; }
3641
3643
 
3642
3644
  /* Reference rating: real radios preserve browser keyboard and form behavior. */
@@ -3649,11 +3651,11 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3649
3651
  /* Selection artwork moves independently; radios, labels and focus stay in place.
3650
3652
  An opt-in avoids changing existing connected/pill consumers before review. */
3651
3653
  .hjm-segmented__items:has(> .hjm-segmented__highlight) { position: relative; isolation: isolate; }
3652
- .hjm-segmented__highlight { position: absolute; pointer-events: none; z-index: 1; border-radius: var(--hjm-radius-md); background: var(--hjm-color-bg); box-shadow: inset 0 0 0 2px var(--hjm-color-focus); }
3654
+ .hjm-segmented__highlight { position: absolute; pointer-events: none; z-index: 1; border-radius: var(--hjm-radius-md); background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 2px var(--hjm-color-focus); }
3653
3655
  .hjm-segmented__highlight[data-moving="true"] { transition: left var(--hjm-motion-normal) ease-out, top var(--hjm-motion-normal) ease-out, width var(--hjm-motion-normal) ease-out, height var(--hjm-motion-normal) ease-out; }
3654
3656
  .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"] { background: transparent; box-shadow: none; }
3655
3657
  .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item > span { position: relative; z-index: 2; pointer-events: none; }
3656
- .hjm-segmented[data-presentation="pills"] .hjm-segmented__highlight { border-radius: var(--hjm-radius-full); background: var(--hjm-color-text-body); box-shadow: none; }
3658
+ .hjm-segmented[data-presentation="pills"] .hjm-segmented__highlight { border-radius: var(--hjm-radius-full); background: var(--hjm-color-surface-selected); box-shadow: none; }
3657
3659
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"]::before { background: transparent; }
3658
3660
  [data-motion="reduced"] .hjm-segmented__highlight { transition: none; }
3659
3661
  @media (prefers-reduced-motion: reduce) { .hjm-segmented__highlight { transition: none; } }
@@ -3803,11 +3805,16 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3803
3805
  .hjm-time-picker__caption { text-align:center; color:var(--hjm-color-text-muted); margin-block-end:var(--hjm-space-xs); }
3804
3806
  .hjm-time-picker__list { position:relative; block-size:var(--hjm-time-height); overflow-y:auto; overscroll-behavior:contain; scrollbar-width:thin; }
3805
3807
  .hjm-time-picker__list button { display:block; inline-size:100%; min-block-size:var(--hjm-time-row); border:0; border-radius:var(--hjm-radius-md); background:transparent; color:var(--hjm-color-text); font:inherit; font-variant-numeric:tabular-nums; cursor:pointer; }
3806
- .hjm-time-picker__list button[aria-selected=true] { background:var(--hjm-color-surface-accent); color:var(--hjm-color-text); font-weight:500; }
3808
+ .hjm-time-picker__list button[aria-selected=true] { background:var(--hjm-color-surface-selected); color:var(--hjm-color-text); font-weight:500; }
3807
3809
  .hjm-time-picker__list button:disabled { opacity:.4; cursor:default; }
3808
3810
  .hjm-time-picker__list button:focus-visible,.hjm-time-picker__trigger:focus-visible { outline:2px solid var(--hjm-color-content-brand); outline-offset:-2px; }
3809
3811
  .hjm-time-picker__description { color:var(--hjm-color-text-muted); }
3810
3812
  .hjm-time-picker__error { color:var(--hjm-color-danger); }
3813
+ .hjm-time-picker__viewport { position:relative; }
3814
+ .hjm-time-picker__center { position:absolute; inset-inline:0; inset-block-start:calc((var(--hjm-time-height) - var(--hjm-time-row)) / 2); block-size:var(--hjm-time-row); border:var(--hjm-stroke-default) solid var(--hjm-color-border-control); border-radius:var(--hjm-radius-md); pointer-events:none; z-index:1; }
3815
+ .hjm-time-picker__list[data-wheel] { box-sizing:border-box; padding-block:calc((var(--hjm-time-height) - var(--hjm-time-row)) / 2); scroll-snap-type:y mandatory; overflow-anchor:none; scrollbar-width:none; }
3816
+ .hjm-time-picker__list[data-wheel] button { block-size:var(--hjm-time-row); scroll-snap-align:center; }
3817
+ .hjm-time-picker__list[data-wheel][aria-disabled=true] { overflow-y:hidden; }
3811
3818
 
3812
3819
  /* IconTile's own target keeps the full artwork width; Button's face padding would squeeze narrow grid cells. */
3813
3820
  .hjm-icon-tile-action { display: block; box-sizing: border-box; width: 100%; margin: 0; padding: 0; border: 0; border-radius: var(--hjm-radius-md); background: transparent; color: inherit; font: inherit; cursor: pointer; }
@@ -3834,3 +3841,20 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3834
3841
  .hjm-segmented[data-selection-tone="brand"] .hjm-segmented__highlight { background: var(--hjm-color-primary); }
3835
3842
  .hjm-segmented[data-selection-tone="brand"] .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"],
3836
3843
  .hjm-segmented[data-selection-tone="brand"][data-presentation="pills"] .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"]::before { background: transparent; }
3844
+
3845
+ /* Photo chrome is deliberately independent of the product theme: no card frame or crop. */
3846
+ .hjm-image-viewer { position: fixed; inset: 0; display: flex; flex-direction: column; min-inline-size: 0; background: #000; color: #fff; padding-block: env(safe-area-inset-top) env(safe-area-inset-bottom); }
3847
+ .hjm-image-viewer__header, .hjm-image-viewer__footer { display: flex; align-items: center; gap: var(--hjm-space-xs); padding: var(--hjm-space-xs) max(var(--hjm-space-md), env(safe-area-inset-left)) var(--hjm-space-xs) max(var(--hjm-space-md), env(safe-area-inset-right)); }
3848
+ .hjm-image-viewer__footer > span { flex: 1; text-align: center; }
3849
+ .hjm-image-viewer__stage { flex: 1; min-block-size: 0; overflow: hidden; position: relative; touch-action: none; }
3850
+ .hjm-image-viewer__image { inline-size: 100%; block-size: 100%; display: flex; align-items: center; justify-content: center; }
3851
+ .hjm-image-viewer__image img { inline-size: 100%; block-size: 100%; object-fit: contain; user-select: none; }
3852
+ .hjm-image-viewer__image > [role="status"], .hjm-image-viewer__image > [role="alert"] { position: absolute; background: #000; color: #fff; padding: var(--hjm-space-md); }
3853
+ .hjm-image-viewer .hjm-icon-button { color: #fff; background: #222; }
3854
+
3855
+ .hjm-image-viewer__actions { margin-inline-start: auto; }
3856
+
3857
+ /* Persistent selection uses a neutral surface; active-descendant focus keeps its own treatment. */
3858
+ .hjm-surface[data-tone="selected"] { background: var(--hjm-color-surface-selected); }
3859
+ .hjm-surface[data-tone="selected"][data-bordered="true"] { border-color: var(--hjm-color-border-control); }
3860
+ .hjm-data-table__table tr[aria-selected="true"] > :is(td, th) { background-color: var(--hjm-color-surface-selected); }
@@ -1,5 +1,5 @@
1
1
  @layer hjm {
2
- /* Broad neutral and pale-brand surfaces use the theme canvas. Selection stays visible through borders; primary actions and compact state marks retain their semantic fills. */
2
+ /* Persistent selection uses its neutral surface. Focus, primary actions and compact value marks retain their distinct semantic roles; see theme-palette.md. */
3
3
  .hjm-root,
4
4
  .hjm-root *,
5
5
  .hjm-root *::before,
@@ -269,7 +269,7 @@
269
269
  /* Toggle treatment: aria-pressed already carried the state, so without a paired
270
270
  visual every consumer painted the selected background in product styles.
271
271
  Selection uses content color without an added border (2026-10-10 user request); focus stays separate. */
272
- .hjm-button[data-selected="true"], .hjm-icon-button[data-selected="true"] { color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); border-color: transparent; }
272
+ .hjm-button[data-selected="true"], .hjm-icon-button[data-selected="true"] { color: var(--hjm-color-text); background: var(--hjm-color-surface-selected); border-color: transparent; }
273
273
  .hjm-button:active:not(:disabled):not([aria-disabled="true"]), .hjm-icon-button:active:not(:disabled):not([aria-disabled="true"]) { opacity: var(--hjm-button-pressed-opacity); }
274
274
  /* data-state="disabled" also covers focusable boundaries (aria-disabled, e.g. Carousel previous on the first slide),
275
275
  which looked enabled while Native dimmed them (2026-10-17 review E9). */
@@ -288,7 +288,7 @@
288
288
  .hjm-button[data-tone="primary"] { --hjm-button-face-fill: var(--hjm-color-primary); }
289
289
  .hjm-button[data-tone="secondary"] { --hjm-button-face-fill: var(--hjm-color-bg); --hjm-button-face-border: var(--hjm-color-border-control); }
290
290
  .hjm-button[data-tone="danger"] { --hjm-button-face-fill: var(--hjm-color-danger-fill); }
291
- .hjm-button[data-selected="true"] { --hjm-button-face-fill: var(--hjm-color-bg); --hjm-button-face-border: transparent; }
291
+ .hjm-button[data-selected="true"] { --hjm-button-face-fill: var(--hjm-color-surface-selected); --hjm-button-face-border: transparent; }
292
292
  .hjm-button[data-raised="true"] { padding: 0 0 var(--hjm-button-depth); border: 0; gap: 0; flex-direction: column; background: color-mix(in srgb, var(--hjm-button-side), #000 var(--hjm-button-side-shade)); }
293
293
  .hjm-button__face { position: relative; display: flex; box-sizing: border-box; inline-size: 100%; min-block-size: inherit; flex: 1; align-items: center; justify-content: inherit; gap: var(--hjm-space-xs); padding: var(--hjm-space-xs) var(--hjm-button-face-padding); border: 1px solid var(--hjm-button-face-border, transparent); border-radius: inherit; background: var(--hjm-button-face-fill); transition: transform var(--hjm-button-settle) ease-out; }
294
294
  .hjm-button[data-raised="true"]:active:not(:disabled):not([aria-disabled="true"]) { opacity: 1; }
@@ -814,7 +814,7 @@
814
814
  .hjm-choice[data-presentation="card"][data-state="checked"],
815
815
  .hjm-choice[data-presentation="card"][data-state="mixed"],
816
816
  .hjm-choice[data-presentation="grouped"][data-state="checked"],
817
- .hjm-choice[data-presentation="grouped"][data-state="mixed"] { border-color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); }
817
+ .hjm-choice[data-presentation="grouped"][data-state="mixed"] { border-color: var(--hjm-color-border-control); background: var(--hjm-color-surface-selected); }
818
818
  .hjm-choice[data-size="small"] { min-block-size: 44px; gap: var(--hjm-space-xs); padding: var(--hjm-space-xs) var(--hjm-space-sm); }
819
819
  .hjm-choice[data-size="small"][data-presentation="plain"] { padding: 0; }
820
820
  .hjm-choice__input { position: absolute; opacity: 0; inline-size: 1px; block-size: 1px; }
@@ -882,7 +882,7 @@
882
882
  .hjm-choice[data-presentation="chips"] .hjm-choice__indicator { display: none; }
883
883
  .hjm-choice[data-presentation="chips"] .hjm-choice__leading { color: inherit; }
884
884
  .hjm-choice[data-presentation="chips"] .hjm-choice__copy { min-inline-size: 0; overflow-wrap: anywhere; padding-block: 0; }
885
- .hjm-choice[data-presentation="chips"][data-state="checked"], .hjm-choice[data-presentation="chips"][data-state="mixed"] { color: var(--hjm-color-content-brand); border-color: var(--hjm-color-content-brand); }
885
+ .hjm-choice[data-presentation="chips"][data-state="checked"], .hjm-choice[data-presentation="chips"][data-state="mixed"] { color: var(--hjm-color-text); border-color: var(--hjm-color-border-control); background: var(--hjm-color-surface-selected); }
886
886
  .hjm-choice[data-presentation="chips"]:has(.hjm-choice__input:focus-visible) { outline: var(--hjm-focus-width) solid var(--hjm-color-focus); outline-offset: var(--hjm-focus-offset); }
887
887
  /* A described switch: copy + switchRecipe.rowPaddingVertical 8 on both sides, min rowTwoLineMinHeight 56, same as Native.
888
888
  Stacked switch rows carry this spacing themselves; containers add no gap between them (2026-10-17). */
@@ -924,7 +924,7 @@
924
924
  /* Vertical only: neighbours are 4px apart, so a horizontal slop would overlap the next option's target. */
925
925
  .hjm-segmented:where(:not([data-presentation="pills"]):not([data-presentation="text"])) .hjm-segmented__item::after { content: ""; position: absolute; inset: calc((var(--hjm-segmented-height) - 2 * (var(--hjm-space-xxs) + 1px) - var(--hjm-control-min-touch-target)) / 2) 0; }
926
926
  .hjm-segmented__item input { position: absolute; opacity: 0; }
927
- .hjm-segmented__item[data-state="checked"] { box-shadow: inset 0 0 0 2px var(--hjm-color-focus); color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); font-weight: var(--hjm-font-weight-semibold); }
927
+ .hjm-segmented__item[data-state="checked"] { box-shadow: inset 0 0 0 2px var(--hjm-color-focus); color: var(--hjm-color-text); background: var(--hjm-color-surface-selected); font-weight: var(--hjm-font-weight-semibold); }
928
928
  .hjm-segmented__item[data-disabled="true"] { opacity: 0.5; cursor: not-allowed; }
929
929
 
930
930
  /* segmentedControlRecipe.adaptive.largeTextLayout stacks oversized labels, matching RN.
@@ -1038,7 +1038,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1038
1038
  .hjm-list-row[data-density="relaxed"][data-lines="two"] { min-block-size: var(--hjm-list-row-relaxed-two-line); }
1039
1039
  .hjm-list-row[data-density="spacious"] { --hjm-list-row-inline: var(--hjm-list-row-spacious-padding-inline); min-block-size: var(--hjm-list-row-spacious-one-line); padding-block: var(--hjm-list-row-spacious-padding-block); }
1040
1040
  .hjm-list-row[data-density="spacious"][data-lines="two"] { min-block-size: var(--hjm-list-row-spacious-two-line); }
1041
- .hjm-list-row[data-state="selected"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
1041
+ .hjm-list-row[data-state="selected"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
1042
1042
  .hjm-list-row[data-state="disabled"] { opacity: 0.5; cursor: not-allowed; }
1043
1043
  /* trailingAction: one surface for the row command and its separate action, as Native. The frame takes the bleed; the
1044
1044
  command keeps the start padding and the action the end padding, so the action box ends on the content edge (an
@@ -1047,7 +1047,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1047
1047
  .hjm-list-row-frame[data-density="compact"] { --hjm-list-row-inline: var(--hjm-list-row-compact-padding-inline); }
1048
1048
  .hjm-list-row-frame[data-density="relaxed"] { --hjm-list-row-inline: var(--hjm-list-row-relaxed-padding-inline); }
1049
1049
  .hjm-list-row-frame[data-density="spacious"] { --hjm-list-row-inline: var(--hjm-list-row-spacious-padding-inline); }
1050
- .hjm-list-row-frame[data-state="selected"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
1050
+ .hjm-list-row-frame[data-state="selected"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
1051
1051
  .hjm-list-row-frame[data-state="disabled"] { opacity: 0.5; }
1052
1052
  .hjm-list-row-frame > .hjm-list-row { flex: 1 1 auto; min-inline-size: 0; inline-size: auto; margin-inline: 0; padding-inline-end: 0; }
1053
1053
  .hjm-list-row-frame > .hjm-list-row[data-state] { background: transparent; box-shadow: none; opacity: 1; }
@@ -1105,7 +1105,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1105
1105
  .hjm-chip { position: relative; min-block-size: var(--hjm-control-min-touch-target); display: inline-flex; align-items: center; gap: var(--hjm-space-xs); padding-inline: var(--hjm-space-md); border: 1px solid var(--hjm-color-border); border-radius: 999px; background: var(--hjm-color-bg); color: var(--hjm-color-text-body); font: inherit; font-weight: var(--hjm-text-emphasis-medium); cursor: pointer; }
1106
1106
  .hjm-chip[data-size="small"] { min-block-size: 36px; padding-inline: var(--hjm-space-sm); gap: var(--hjm-space-xxs); }
1107
1107
  .hjm-chip[data-size="small"]::after { content: ""; position: absolute; inset: -4px 0; }
1108
- .hjm-chip[data-selected] { border-color: var(--hjm-color-content-brand); background: var(--hjm-color-bg); color: var(--hjm-color-content-brand); }
1108
+ .hjm-chip[data-selected] { border-color: var(--hjm-color-border-control); background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); }
1109
1109
  .hjm-chip:disabled { opacity: 0.5; cursor: not-allowed; }
1110
1110
  .hjm-chip:focus-visible { outline: var(--hjm-focus-width) solid var(--hjm-color-focus); outline-offset: var(--hjm-focus-offset); }
1111
1111
  .hjm-chip__indicator, .hjm-chip__leading, .hjm-chip__trailing { display: inline-flex; flex: 0 0 auto; }
@@ -1612,7 +1612,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1612
1612
  /* Panel headings and empty-state copy share the same narrow column as rows. */
1613
1613
  .hjm-transfer-list__title,
1614
1614
  .hjm-transfer-list__empty { min-inline-size: 0; overflow-wrap: anywhere; }
1615
- .hjm-transfer-list__option[aria-selected="true"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
1615
+ .hjm-transfer-list__option[aria-selected="true"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
1616
1616
  .hjm-transfer-list__option[aria-disabled="true"] { color: var(--hjm-color-text-weak); }
1617
1617
  .hjm-transfer-list__option:focus-visible,
1618
1618
  .hjm-transfer-list__empty:focus-visible,
@@ -1974,9 +1974,9 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
1974
1974
  }
1975
1975
  /* The pressed state is announced by aria-pressed; color only reinforces it. */
1976
1976
  .hjm-toggle-group__item[aria-pressed="true"] {
1977
- border-color: var(--hjm-color-focus);
1978
- background: var(--hjm-color-bg);
1979
- color: var(--hjm-color-content-brand);
1977
+ border-color: var(--hjm-color-border-control);
1978
+ background: var(--hjm-color-surface-selected);
1979
+ color: var(--hjm-color-text);
1980
1980
  font-weight: var(--hjm-text-emphasis-strong);
1981
1981
  }
1982
1982
  .hjm-toggle-group__item:disabled { cursor: default; color: var(--hjm-color-text-weak); }
@@ -2209,7 +2209,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2209
2209
  color: var(--hjm-color-text);
2210
2210
  cursor: default;
2211
2211
  }
2212
- .hjm-tree__node[aria-selected="true"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
2212
+ .hjm-tree__node[aria-selected="true"] { background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 1px var(--hjm-color-border-control); }
2213
2213
  .hjm-tree__node[aria-disabled="true"] { color: var(--hjm-color-text-weak); }
2214
2214
  .hjm-tree__node:focus-visible { outline: 2px solid var(--hjm-color-focus); outline-offset: -2px; }
2215
2215
  .hjm-tree__indent { flex: 0 0 auto; inline-size: calc(var(--hjm-tree-depth) * var(--hjm-tree-indent)); }
@@ -2483,6 +2483,8 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2483
2483
  .hjm-sheet[data-placement="bottom"] {
2484
2484
  inline-size: min(var(--hjm-sheet-max-width), 100%);
2485
2485
  max-block-size: var(--hjm-sheet-max-height);
2486
+ /* The bottom edge is docked to the viewport, not an exposed card perimeter. */
2487
+ border-block-end-width: 0;
2486
2488
  border-end-start-radius: 0;
2487
2489
  border-end-end-radius: 0;
2488
2490
  }
@@ -2673,7 +2675,8 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2673
2675
  .hjm-menu__item:hover,
2674
2676
  .hjm-menu__item[data-focus="true"] { background: var(--hjm-color-bg); box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); }
2675
2677
  .hjm-menu__item[data-tone="danger"] { color: var(--hjm-color-danger); }
2676
- .hjm-menu__item[data-state="selected"] { color: var(--hjm-color-content-brand); font-weight: var(--hjm-text-emphasis-strong); }
2678
+ .hjm-menu__item[data-state="selected"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); font-weight: var(--hjm-text-emphasis-strong); }
2679
+ .hjm-menu__item[data-state="selected"][data-tone="danger"] { color: var(--hjm-color-danger); }
2677
2680
  .hjm-menu__item:disabled { opacity: 0.5; cursor: not-allowed; }
2678
2681
  .hjm-menu__state-message { min-block-size: var(--hjm-control-min-touch-target); display: flex; align-items: center; padding: var(--hjm-space-xs) var(--hjm-space-sm); color: var(--hjm-color-text-muted); overflow-wrap: anywhere; }
2679
2682
  .hjm-menu__section-label { padding: var(--hjm-space-xs) var(--hjm-space-sm); color: var(--hjm-color-text-muted); font-size: var(--hjm-type-label-size); font-weight: var(--hjm-text-emphasis-medium); }
@@ -2727,7 +2730,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2727
2730
  .hjm-select__listbox[data-density="comfortable"] .hjm-select__option { min-block-size: 3.5rem; }
2728
2731
  .hjm-select__option { cursor: pointer; }
2729
2732
  .hjm-select__option[data-active="true"] { box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); background: var(--hjm-color-bg); }
2730
- .hjm-select__option[data-state="selected"] { color: var(--hjm-color-content-brand); font-weight: var(--hjm-font-weight-semibold); }
2733
+ .hjm-select__option[data-state="selected"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); font-weight: var(--hjm-font-weight-semibold); }
2731
2734
  .hjm-select__option[data-state="disabled"] { opacity: 0.5; cursor: not-allowed; }
2732
2735
  .hjm-select__option-copy { min-inline-size: 0; flex: 1 1 auto; display: grid; gap: var(--hjm-space-xxs); }
2733
2736
  .hjm-select__option-description, .hjm-select__message { color: var(--hjm-color-text-muted); font-size: var(--hjm-type-label-size); }
@@ -2768,7 +2771,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
2768
2771
  .hjm-combobox__listbox[data-density="comfortable"] .hjm-combobox__option { min-block-size: 3.5rem; }
2769
2772
  .hjm-combobox__option { cursor: pointer; }
2770
2773
  .hjm-combobox__option[data-state="active"] { box-shadow: inset 0 0 0 1px var(--hjm-color-content-brand); background: var(--hjm-color-bg); }
2771
- .hjm-combobox__option[data-state="selected"] { color: var(--hjm-color-content-brand); font-weight: var(--hjm-font-weight-semibold); }
2774
+ .hjm-combobox__option[aria-selected="true"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); font-weight: var(--hjm-font-weight-semibold); }
2772
2775
  .hjm-combobox__option[data-state="disabled"] { opacity: 0.5; cursor: not-allowed; }
2773
2776
  .hjm-combobox__message { color: var(--hjm-color-text-muted); }
2774
2777
  .hjm-form__fieldset { min-inline-size: 0; margin: 0; padding: 0; border: 0; }
@@ -3301,14 +3304,14 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
3301
3304
  .hjm-tabs:is([data-appearance="gooey"], [data-appearance="slide"]) .hjm-tabs__list { position: relative; }
3302
3305
  .hjm-tabs:is([data-appearance="gooey"], [data-appearance="slide"]) .hjm-tabs__tab[data-state="selected"]::after { display: none; }
3303
3306
  .hjm-tabs__indicator { position: absolute; bottom: 0; height: 2px; border-radius: var(--hjm-radius-full); background: var(--hjm-color-content-brand); pointer-events: none; }
3304
- /* indicator="filled" (tabsRecipe.indicators.filled): a surface-accent pill behind the selected tab, no list divider.
3307
+ /* indicator="filled" (tabsRecipe.indicators.filled): a neutral selection pill behind the selected tab, no list divider.
3305
3308
  The moving pill spans the tab height and sits under the labels. */
3306
3309
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__list { border: 0; }
3307
3310
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab { border-radius: var(--hjm-radius-full); }
3308
- .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab[data-state="selected"] { color: var(--hjm-color-content-brand); }
3311
+ .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab[data-state="selected"] { color: var(--hjm-color-text); }
3309
3312
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab[data-state="selected"]::after { display: none; }
3310
- .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]):not([data-indicator-motion="moving"]) .hjm-tabs__tab[data-state="selected"] { background: var(--hjm-color-surface-accent); }
3311
- .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__indicator { top: 0; bottom: 0; height: auto; border-radius: var(--hjm-radius-full); background: var(--hjm-color-surface-accent); z-index: 0; }
3313
+ .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]):not([data-indicator-motion="moving"]) .hjm-tabs__tab[data-state="selected"] { background: var(--hjm-color-surface-selected); }
3314
+ .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__indicator { top: 0; bottom: 0; height: auto; border-radius: var(--hjm-radius-full); background: var(--hjm-color-surface-selected); z-index: 0; }
3312
3315
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__list { position: relative; }
3313
3316
  .hjm-tabs:is([data-indicator="filled"],[data-indicator="solid"]) .hjm-tabs__tab { z-index: 1; }
3314
3317
  .hjm-tabs__gooey { height: 6px; }
@@ -3331,7 +3334,7 @@ button.hjm-list-row, a.hjm-list-row { cursor: pointer; }
3331
3334
  }
3332
3335
  .hjm-bottom-navigation[data-presentation="capsule"][data-expanded-labels="false"] .hjm-bottom-navigation__item { flex-direction: row; }
3333
3336
  .hjm-bottom-navigation[data-presentation="capsule"][data-expanded-labels="false"] .hjm-bottom-navigation__item:not([data-state="selected"]) .hjm-bottom-navigation__label { display: none; }
3334
- .hjm-bottom-navigation[data-presentation="capsule"] .hjm-bottom-navigation__item[data-state="selected"] { background: var(--hjm-color-surface-accent); }
3337
+ .hjm-bottom-navigation[data-presentation="capsule"]:not([data-selection="tile"]) .hjm-bottom-navigation__item[data-state="selected"] { background: var(--hjm-color-surface-selected); color: var(--hjm-color-text); }
3335
3338
  .hjm-bottom-navigation[data-presentation="capsule"] .hjm-bottom-navigation__primary-action { position: static; translate: none; flex-shrink: 0; }
3336
3339
  @media (prefers-reduced-motion: reduce) { .hjm-bottom-navigation[data-presentation="capsule"] .hjm-bottom-navigation__item { transition: none; } }
3337
3340
 
@@ -3606,9 +3609,8 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3606
3609
  /* Only the chat strip enlarges glyphs, to the title type step Native's strip uses. The default
3607
3610
  wrap layout keeps the button's own size, as published before the strip existed. */
3608
3611
  .hjm-reaction-picker[data-layout="strip"] .hjm-reaction-picker__glyph { font-size: var(--hjm-type-title-size); line-height: var(--hjm-type-title-line-height); }
3609
- /* Wrap reactions reuse the chip frame (chipRecipe). Emoji ignore the brand content color, so the chosen reaction
3610
- also takes the accent fill that Native's strip and wrap items use. */
3611
- .hjm-reaction-picker__chip[data-selected] { background: var(--hjm-color-surface-accent); }
3612
+ /* Emoji ignore text color; wrap and strip both retain the shared neutral selection fill. */
3613
+ .hjm-reaction-picker__chip[data-selected] { background: var(--hjm-color-surface-selected); }
3612
3614
 
3613
3615
  /* The embedded circle uses the small 36px recipe; centre it in the field rather than on the text baseline.
3614
3616
  Reduce only its trailing inset to 8px, preserving the text's 16px leading padding. */
@@ -3636,8 +3638,8 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3636
3638
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__item::before { content:""; position:absolute; inset:var(--hjm-space-xxs) 0; border-radius:var(--hjm-radius-full); background:var(--hjm-color-bg); border:1px solid var(--hjm-color-border-control); }
3637
3639
  .hjm-segmented[data-presentation="pills"][data-size="small"] .hjm-segmented__item { padding-inline:var(--hjm-space-sm); }
3638
3640
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__item > span { position:relative; overflow-wrap:anywhere; }
3639
- .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"] { color:var(--hjm-color-bg); font-weight:var(--hjm-font-weight-semibold); }
3640
- .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"]::before { background:var(--hjm-color-text-body); border-color:var(--hjm-color-text-body); }
3641
+ .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"] { color:var(--hjm-color-text); font-weight:var(--hjm-font-weight-semibold); }
3642
+ .hjm-segmented[data-presentation="pills"] .hjm-segmented__item[data-state="checked"]::before { background:var(--hjm-color-surface-selected); border-color:var(--hjm-color-surface-selected); }
3641
3643
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__item:focus-within { outline:2px solid var(--hjm-color-focus); outline-offset:2px; }
3642
3644
 
3643
3645
  /* Reference rating: real radios preserve browser keyboard and form behavior. */
@@ -3650,11 +3652,11 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3650
3652
  /* Selection artwork moves independently; radios, labels and focus stay in place.
3651
3653
  An opt-in avoids changing existing connected/pill consumers before review. */
3652
3654
  .hjm-segmented__items:has(> .hjm-segmented__highlight) { position: relative; isolation: isolate; }
3653
- .hjm-segmented__highlight { position: absolute; pointer-events: none; z-index: 1; border-radius: var(--hjm-radius-md); background: var(--hjm-color-bg); box-shadow: inset 0 0 0 2px var(--hjm-color-focus); }
3655
+ .hjm-segmented__highlight { position: absolute; pointer-events: none; z-index: 1; border-radius: var(--hjm-radius-md); background: var(--hjm-color-surface-selected); box-shadow: inset 0 0 0 2px var(--hjm-color-focus); }
3654
3656
  .hjm-segmented__highlight[data-moving="true"] { transition: left var(--hjm-motion-normal) ease-out, top var(--hjm-motion-normal) ease-out, width var(--hjm-motion-normal) ease-out, height var(--hjm-motion-normal) ease-out; }
3655
3657
  .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"] { background: transparent; box-shadow: none; }
3656
3658
  .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item > span { position: relative; z-index: 2; pointer-events: none; }
3657
- .hjm-segmented[data-presentation="pills"] .hjm-segmented__highlight { border-radius: var(--hjm-radius-full); background: var(--hjm-color-text-body); box-shadow: none; }
3659
+ .hjm-segmented[data-presentation="pills"] .hjm-segmented__highlight { border-radius: var(--hjm-radius-full); background: var(--hjm-color-surface-selected); box-shadow: none; }
3658
3660
  .hjm-segmented[data-presentation="pills"] .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"]::before { background: transparent; }
3659
3661
  [data-motion="reduced"] .hjm-segmented__highlight { transition: none; }
3660
3662
  @media (prefers-reduced-motion: reduce) { .hjm-segmented__highlight { transition: none; } }
@@ -3804,11 +3806,16 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3804
3806
  .hjm-time-picker__caption { text-align:center; color:var(--hjm-color-text-muted); margin-block-end:var(--hjm-space-xs); }
3805
3807
  .hjm-time-picker__list { position:relative; block-size:var(--hjm-time-height); overflow-y:auto; overscroll-behavior:contain; scrollbar-width:thin; }
3806
3808
  .hjm-time-picker__list button { display:block; inline-size:100%; min-block-size:var(--hjm-time-row); border:0; border-radius:var(--hjm-radius-md); background:transparent; color:var(--hjm-color-text); font:inherit; font-variant-numeric:tabular-nums; cursor:pointer; }
3807
- .hjm-time-picker__list button[aria-selected=true] { background:var(--hjm-color-surface-accent); color:var(--hjm-color-text); font-weight:500; }
3809
+ .hjm-time-picker__list button[aria-selected=true] { background:var(--hjm-color-surface-selected); color:var(--hjm-color-text); font-weight:500; }
3808
3810
  .hjm-time-picker__list button:disabled { opacity:.4; cursor:default; }
3809
3811
  .hjm-time-picker__list button:focus-visible,.hjm-time-picker__trigger:focus-visible { outline:2px solid var(--hjm-color-content-brand); outline-offset:-2px; }
3810
3812
  .hjm-time-picker__description { color:var(--hjm-color-text-muted); }
3811
3813
  .hjm-time-picker__error { color:var(--hjm-color-danger); }
3814
+ .hjm-time-picker__viewport { position:relative; }
3815
+ .hjm-time-picker__center { position:absolute; inset-inline:0; inset-block-start:calc((var(--hjm-time-height) - var(--hjm-time-row)) / 2); block-size:var(--hjm-time-row); border:var(--hjm-stroke-default) solid var(--hjm-color-border-control); border-radius:var(--hjm-radius-md); pointer-events:none; z-index:1; }
3816
+ .hjm-time-picker__list[data-wheel] { box-sizing:border-box; padding-block:calc((var(--hjm-time-height) - var(--hjm-time-row)) / 2); scroll-snap-type:y mandatory; overflow-anchor:none; scrollbar-width:none; }
3817
+ .hjm-time-picker__list[data-wheel] button { block-size:var(--hjm-time-row); scroll-snap-align:center; }
3818
+ .hjm-time-picker__list[data-wheel][aria-disabled=true] { overflow-y:hidden; }
3812
3819
 
3813
3820
  /* IconTile's own target keeps the full artwork width; Button's face padding would squeeze narrow grid cells. */
3814
3821
  .hjm-icon-tile-action { display: block; box-sizing: border-box; width: 100%; margin: 0; padding: 0; border: 0; border-radius: var(--hjm-radius-md); background: transparent; color: inherit; font: inherit; cursor: pointer; }
@@ -3836,4 +3843,21 @@ button.hjm-chat-message__media-item:focus-visible { outline: 2px solid var(--hjm
3836
3843
  .hjm-segmented[data-selection-tone="brand"] .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"],
3837
3844
  .hjm-segmented[data-selection-tone="brand"][data-presentation="pills"] .hjm-segmented__items[data-highlight-ready="true"] > .hjm-segmented__item[data-state="checked"]::before { background: transparent; }
3838
3845
 
3846
+ /* Photo chrome is deliberately independent of the product theme: no card frame or crop. */
3847
+ .hjm-image-viewer { position: fixed; inset: 0; display: flex; flex-direction: column; min-inline-size: 0; background: #000; color: #fff; padding-block: env(safe-area-inset-top) env(safe-area-inset-bottom); }
3848
+ .hjm-image-viewer__header, .hjm-image-viewer__footer { display: flex; align-items: center; gap: var(--hjm-space-xs); padding: var(--hjm-space-xs) max(var(--hjm-space-md), env(safe-area-inset-left)) var(--hjm-space-xs) max(var(--hjm-space-md), env(safe-area-inset-right)); }
3849
+ .hjm-image-viewer__footer > span { flex: 1; text-align: center; }
3850
+ .hjm-image-viewer__stage { flex: 1; min-block-size: 0; overflow: hidden; position: relative; touch-action: none; }
3851
+ .hjm-image-viewer__image { inline-size: 100%; block-size: 100%; display: flex; align-items: center; justify-content: center; }
3852
+ .hjm-image-viewer__image img { inline-size: 100%; block-size: 100%; object-fit: contain; user-select: none; }
3853
+ .hjm-image-viewer__image > [role="status"], .hjm-image-viewer__image > [role="alert"] { position: absolute; background: #000; color: #fff; padding: var(--hjm-space-md); }
3854
+ .hjm-image-viewer .hjm-icon-button { color: #fff; background: #222; }
3855
+
3856
+ .hjm-image-viewer__actions { margin-inline-start: auto; }
3857
+
3858
+ /* Persistent selection uses a neutral surface; active-descendant focus keeps its own treatment. */
3859
+ .hjm-surface[data-tone="selected"] { background: var(--hjm-color-surface-selected); }
3860
+ .hjm-surface[data-tone="selected"][data-bordered="true"] { border-color: var(--hjm-color-border-control); }
3861
+ .hjm-data-table__table tr[aria-selected="true"] > :is(td, th) { background-color: var(--hjm-color-surface-selected); }
3862
+
3839
3863
  }
@@ -1 +1 @@
1
- {"version":3,"file":"time-picker.d.ts","sourceRoot":"","sources":["../src/time-picker.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAkG,KAAK,iBAAiB,EAAuB,MAAM,gDAAgD,CAAC;AAI7M,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,wBAAwB,CAAC;AAEtE,MAAM,MAAM,eAAe,GAAG,iBAAiB,GAAG,QAAQ,CAAC;IAAE,WAAW,CAAC,EAAE,uBAAuB,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;AAE1H,uGAAuG;AACvG,wBAAgB,UAAU,CAAC,KAAK,EAAE,eAAe,+BA4DhD"}
1
+ {"version":3,"file":"time-picker.d.ts","sourceRoot":"","sources":["../src/time-picker.tsx"],"names":[],"mappings":"AAEA,OAAO,EAA+H,KAAK,iBAAiB,EAAuB,MAAM,gDAAgD,CAAC;AAI1O,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,wBAAwB,CAAC;AAGtE,MAAM,MAAM,eAAe,GAAG,iBAAiB,GAAG,QAAQ,CAAC;IAAE,WAAW,CAAC,EAAE,uBAAuB,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;AAE1H,uGAAuG;AACvG,wBAAgB,UAAU,CAAC,KAAK,EAAE,eAAe,+BAmChD"}