@poodle64/ui 2026.10.5 → 2026.10.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -899,7 +899,7 @@ no module rebuilds them and a need one module finds becomes a toggle for all.
899
899
  | `selected`, `bulkActions` | Ticking exists only with `bulkActions`, whose snippet gets the ticked rows in the bar that replaces the toolbar. |
900
900
  | `open`, `editor` | Opening exists only with `editor`: the row lifts out of its card as its own surface, holding the snippet. Its second argument carries the row's `template` and each column's grid line, so fields can sit under their columns. |
901
901
  | `originActions`, `onAttachment` | Split, join and undo under a synthetic row's statement lines; the paperclip as a button. |
902
- | `noun`, `empty`, `footer`, `layout` | "line" for a printed layer; the empty state; "Show more" after the last group; a forced `phone`/`narrow`/`wide` where the ledger's own width (below 600px, from 1200px) should not decide. |
902
+ | `noun`, `empty`, `footer`, `layout` | "line" for a printed layer; the empty state; "Show more" after the last group; a forced `phone`/`narrow`/`wide` where the ledger's own width (below 480px, from 1200px) should not decide. |
903
903
 
904
904
  Settled here, the same in every module, and not props:
905
905
 
@@ -985,7 +985,7 @@ stays for a dense grid of data; a module's own records are a RecordList.
985
985
  | `noun`, `empty`, `footer`, `layout` | As the Ledger's. |
986
986
 
987
987
  A sort orders rows inside their groups, largest first (words from A), then
988
- reversed, then the list's own order. On a phone (below 600px of list) a row is its thumbnail, title
988
+ reversed, then the list's own order. On a phone (below 480px of list) a row is its thumbnail, title
989
989
  and lines, with the first end-aligned column's value beside the title. Measured
990
990
  in a real engine at 390, 1440 and 3360px (`harness/drive.mjs`, `?surface=records`).
991
991
 
@@ -8,7 +8,7 @@
8
8
  *
9
9
  * It fills its parent's height and scrolls its own rows, so the head card
10
10
  * stays at the top: give it a bounded parent (`flex-1 min-h-0` in a
11
- * full-height page). Width picks the layout: a phone's list below 600px, the
11
+ * full-height page). Width picks the layout: a phone's list below 480px, the
12
12
  * wide column widths from 1200px.
13
13
  */
14
14
  import type { Snippet } from 'svelte';
@@ -42,7 +42,8 @@
42
42
  ROW_TEXT,
43
43
  RULE,
44
44
  THROUGH,
45
- groupSpacing
45
+ groupSpacing,
46
+ listLayout
46
47
  } from './look.js';
47
48
  import { AU_LOCALE } from '../../../format.js';
48
49
  import { cn } from '../../../utils.js';
@@ -212,15 +213,7 @@
212
213
  /** The bars above the list end where its cards do: clear of its scroll bar's gutter. */
213
214
  const edge = $derived(`calc(0.5rem + ${Math.max(0, listOuter - listInner)}px)`);
214
215
  const mode = $derived(
215
- layout !== 'auto'
216
- ? layout
217
- : width === 0
218
- ? 'narrow'
219
- : width < 600
220
- ? 'phone'
221
- : width >= 1200
222
- ? 'wide'
223
- : 'narrow'
216
+ layout !== 'auto' ? layout : listLayout(width)
224
217
  );
225
218
  const WIDE = $derived(mode === 'wide');
226
219
  const PHONE = $derived(mode === 'phone');
@@ -7,7 +7,7 @@
7
7
  *
8
8
  * It fills its parent's height and scrolls its own rows, so the head card
9
9
  * stays at the top: give it a bounded parent (`flex-1 min-h-0` in a
10
- * full-height page). Width picks the layout: a phone's list below 600px, the
10
+ * full-height page). Width picks the layout: a phone's list below 480px, the
11
11
  * wide column widths from 1200px.
12
12
  */
13
13
  import type { Snippet } from 'svelte';
@@ -3,6 +3,15 @@
3
3
  * the RecordList. A head card, row cards with hairlines between rows, and each
4
4
  * group's label on the page ground.
5
5
  */
6
+ /**
7
+ * The layout a list's own width picks: a phone's list below 480px, the wide
8
+ * tracks from 1200px, the narrow tracks between. The list's width, not the
9
+ * window's: beside a ContextColumn at 1280px with the rail open it is 588px,
10
+ * which is a laptop's list, not a phone's.
11
+ */
12
+ export declare const PHONE_BELOW = 480;
13
+ export declare const WIDE_FROM = 1200;
14
+ export declare function listLayout(width: number): 'phone' | 'narrow' | 'wide';
6
15
  export declare const CELL = "min-w-0 truncate px-2";
7
16
  export declare const END = "pr-5 text-right";
8
17
  /** The row's height rides the package's density ramp: 3.5rem, 3rem compact. */
@@ -3,6 +3,17 @@
3
3
  * the RecordList. A head card, row cards with hairlines between rows, and each
4
4
  * group's label on the page ground.
5
5
  */
6
+ /**
7
+ * The layout a list's own width picks: a phone's list below 480px, the wide
8
+ * tracks from 1200px, the narrow tracks between. The list's width, not the
9
+ * window's: beside a ContextColumn at 1280px with the rail open it is 588px,
10
+ * which is a laptop's list, not a phone's.
11
+ */
12
+ export const PHONE_BELOW = 480;
13
+ export const WIDE_FROM = 1200;
14
+ export function listLayout(width) {
15
+ return width === 0 ? 'narrow' : width < PHONE_BELOW ? 'phone' : width >= WIDE_FROM ? 'wide' : 'narrow';
16
+ }
6
17
  export const CELL = 'min-w-0 truncate px-2';
7
18
  export const END = 'pr-5 text-right';
8
19
  /** The row's height rides the package's density ramp: 3.5rem, 3rem compact. */
@@ -13,7 +13,7 @@
13
13
  *
14
14
  * It fills its parent's height and scrolls its own rows, so the head card
15
15
  * stays at the top: give it a bounded parent (`flex-1 min-h-0`). Width picks
16
- * the layout, as the Ledger's does: a phone's list below 600px, the wide
16
+ * the layout, as the Ledger's does: a phone's list below 480px, the wide
17
17
  * tracks and the `'wide'` columns from 1200px. On a phone a row is its
18
18
  * thumbnail, title and lines, with the first end-aligned column's value
19
19
  * beside the title.
@@ -38,7 +38,8 @@
38
38
  ROW_TEXT,
39
39
  RULE,
40
40
  THROUGH,
41
- groupSpacing
41
+ groupSpacing,
42
+ listLayout
42
43
  } from '../ledger/look.js';
43
44
  import ListToolbar from '../list-toolbar/list-toolbar.svelte';
44
45
  import type { ListAction, ListIconAction } from '../list-toolbar/types.js';
@@ -146,15 +147,7 @@
146
147
  /** The bar ends where the cards do: clear of the scroll bar's gutter. */
147
148
  const edge = $derived(`calc(0.5rem + ${Math.max(0, listOuter - listInner)}px)`);
148
149
  const mode = $derived(
149
- layout !== 'auto'
150
- ? layout
151
- : width === 0
152
- ? 'narrow'
153
- : width < 600
154
- ? 'phone'
155
- : width >= 1200
156
- ? 'wide'
157
- : 'narrow'
150
+ layout !== 'auto' ? layout : listLayout(width)
158
151
  );
159
152
  const WIDE = $derived(mode === 'wide');
160
153
  const PHONE = $derived(mode === 'phone');
@@ -12,7 +12,7 @@
12
12
  *
13
13
  * It fills its parent's height and scrolls its own rows, so the head card
14
14
  * stays at the top: give it a bounded parent (`flex-1 min-h-0`). Width picks
15
- * the layout, as the Ledger's does: a phone's list below 600px, the wide
15
+ * the layout, as the Ledger's does: a phone's list below 480px, the wide
16
16
  * tracks and the `'wide'` columns from 1200px. On a phone a row is its
17
17
  * thumbnail, title and lines, with the first end-aligned column's value
18
18
  * beside the title.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poodle64/ui",
3
- "version": "2026.10.5",
3
+ "version": "2026.10.6",
4
4
  "description": "Household shared component layer: shadcn-svelte primitives (bits-ui) plus the composed page chrome every app builds its routes from, restyled by each app's @poodle64/design-tokens alias layer. One fix reaches every app.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "meta": {
3
3
  "package": "@poodle64/ui",
4
- "version": "2026.10.5",
4
+ "version": "2026.10.6",
5
5
  "generatedBy": "scripts/generate-registry.mjs",
6
6
  "source": "scripts/situations.json + package source (DO NOT EDIT the outputs by hand)",
7
7
  "componentCount": 66,
@@ -1,7 +1,7 @@
1
1
  # @poodle64/ui — situation → component map
2
2
 
3
3
  <!-- GENERATED by scripts/generate-registry.mjs from scripts/situations.json + package source. DO NOT EDIT. -->
4
- Generated from `@poodle64/ui@2026.10.5`. 66 components, 18 situations.
4
+ Generated from `@poodle64/ui@2026.10.6`. 66 components, 18 situations.
5
5
 
6
6
  **Read this before writing a `<div>`.** Find the SITUATION you are in below, then compose the component named for it — do not hand-build it from raw `Card` or utility classes. Import is `import { Name } from '<import path>'`. Props marked `?` are optional. This map is the retrieval step the [`frontend-design` skill] makes mandatory; the [CHI 2026 study] measured composing-from-a-registry at 95% design-system compliance against 71% for writing the CSS from a prose style guide.
7
7