@krapwoo/ds-viewer 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +82 -0
- package/dist/cli/agentsFile.js +31 -0
- package/dist/cli/doctor.js +492 -0
- package/dist/cli/explain.js +151 -0
- package/dist/cli/githubAction.js +68 -0
- package/dist/cli/init.js +6 -2
- package/dist/cli/main.js +49 -0
- package/dist/cli/pageIndex.js +27 -1
- package/dist/cli/props.js +4 -3
- package/dist/cli/staticPage.js +356 -0
- package/dist/cli/sync.js +11 -4
- package/dist/native/catalog/comparison.js +283 -0
- package/dist/native/catalog/tokens.js +119 -0
- package/dist/native/catalog/types.js +1 -0
- package/native/catalog/ComparisonGrid.tsx +9 -7
- package/native/catalog/SpacingScaleGallery.tsx +1 -1
- package/native/catalog/catalogNavigation.ts +1 -1
- package/native/catalog/comparison.ts +63 -5
- package/native/catalog/index.ts +2 -1
- package/native/catalog/pageApi.ts +11 -2
- package/native/catalog/types.ts +9 -6
- package/package.json +5 -1
- package/starter-kit/components/Avatar/Avatar.catalog.tsx +4 -22
- package/starter-kit/components/Badge/Badge.catalog.tsx +15 -23
- package/starter-kit/components/Banner/Banner.tsx +1 -1
- package/starter-kit/components/BottomSheet/BottomSheet.tsx +2 -2
- package/starter-kit/components/Button/Button.catalog.tsx +15 -29
- package/starter-kit/components/Dialog/Dialog.tsx +2 -2
- package/starter-kit/components/Pill/Pill.catalog.tsx +12 -26
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@krapwoo/ds-viewer",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.0",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"description": "A browsable, always-current catalog for an Expo / React Native design system.",
|
|
@@ -29,6 +29,7 @@
|
|
|
29
29
|
"starter-kit",
|
|
30
30
|
"dist/cli",
|
|
31
31
|
"dist/config",
|
|
32
|
+
"dist/native",
|
|
32
33
|
"config/index.ts",
|
|
33
34
|
"README.md",
|
|
34
35
|
"LICENSE"
|
|
@@ -51,6 +52,7 @@
|
|
|
51
52
|
},
|
|
52
53
|
"devDependencies": {
|
|
53
54
|
"@types/node": "^22.0.0",
|
|
55
|
+
"@types/react": "^19.0.0",
|
|
54
56
|
"puppeteer": "^25.12.0"
|
|
55
57
|
},
|
|
56
58
|
"scripts": {
|
|
@@ -59,6 +61,8 @@
|
|
|
59
61
|
"typecheck": "tsc -p tsconfig.json --noEmit",
|
|
60
62
|
"kit:dev": "npm run build && cd kit-host && node node_modules/@krapwoo/ds-viewer/dist/cli/main.js dev",
|
|
61
63
|
"check:catalog": "npm run build && node scripts/checkCatalogConsole.mjs kit-host",
|
|
64
|
+
"check:doctor": "npm run build && cd kit-host && node node_modules/@krapwoo/ds-viewer/dist/cli/main.js doctor --ci",
|
|
65
|
+
"check:types": "tsc --noEmit -p kit-host",
|
|
62
66
|
"release": "node scripts/release.mjs"
|
|
63
67
|
}
|
|
64
68
|
}
|
|
@@ -1,30 +1,12 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
|
-
import { defineCatalogPage,
|
|
2
|
+
import { defineCatalogPage, grid } from '@krapwoo/ds-viewer';
|
|
3
3
|
import { Avatar } from './Avatar';
|
|
4
4
|
import { DS_SEMANTIC } from '../../tokens';
|
|
5
5
|
|
|
6
|
-
// Grid comparisons: each cell is a real instance with exactly the props its row and column name.
|
|
7
|
-
// Never build these by multiplying `variants` with `states` — those are pre-rendered nodes and
|
|
8
|
-
// cannot combine.
|
|
9
|
-
function grid(
|
|
10
|
-
rowLabel: string,
|
|
11
|
-
columnLabel: string,
|
|
12
|
-
rows: { key: string; label: string }[],
|
|
13
|
-
columns: { key: string; label: string }[],
|
|
14
|
-
cell: (row: string, column: string) => React.ReactNode,
|
|
15
|
-
size?: ComparisonDef['size'],
|
|
16
|
-
): ComparisonDef {
|
|
17
|
-
return {
|
|
18
|
-
rowLabel,
|
|
19
|
-
columnLabel,
|
|
20
|
-
rows,
|
|
21
|
-
columns,
|
|
22
|
-
cells: rows.flatMap((row) => columns.map((column) => ({ rowKey: row.key, columnKey: column.key, node: cell(row.key, column.key) }))),
|
|
23
|
-
size,
|
|
24
|
-
};
|
|
25
|
-
}
|
|
26
|
-
|
|
27
6
|
// Avatar: content Kind × Size (Avatar's `size` is continuous; 24 / 40 default / 64 is the sweep).
|
|
7
|
+
// Neither axis names a real prop — "Kind" is which of 3 optional props is set, not one enum, and
|
|
8
|
+
// `size` has no fixed option set — so both stay unbound. An unbound axis is fully valid; `doctor`
|
|
9
|
+
// only ever reports how many examples are unbound as information, never as an error or a warning.
|
|
28
10
|
const AVATAR_COMPARISON = grid(
|
|
29
11
|
'Kind',
|
|
30
12
|
'Size',
|
|
@@ -1,29 +1,8 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
|
-
import { defineCatalogPage,
|
|
2
|
+
import { defineCatalogPage, grid } from '@krapwoo/ds-viewer';
|
|
3
3
|
import { Badge } from './Badge';
|
|
4
4
|
import type { BadgeVariant } from './Badge.types';
|
|
5
5
|
|
|
6
|
-
// Grid comparisons: each cell is a real instance with exactly the props its row and column name.
|
|
7
|
-
// Never build these by multiplying `variants` with `states` — those are pre-rendered nodes and
|
|
8
|
-
// cannot combine.
|
|
9
|
-
function grid(
|
|
10
|
-
rowLabel: string,
|
|
11
|
-
columnLabel: string,
|
|
12
|
-
rows: { key: string; label: string }[],
|
|
13
|
-
columns: { key: string; label: string }[],
|
|
14
|
-
cell: (row: string, column: string) => React.ReactNode,
|
|
15
|
-
size?: ComparisonDef['size'],
|
|
16
|
-
): ComparisonDef {
|
|
17
|
-
return {
|
|
18
|
-
rowLabel,
|
|
19
|
-
columnLabel,
|
|
20
|
-
rows,
|
|
21
|
-
columns,
|
|
22
|
-
cells: rows.flatMap((row) => columns.map((column) => ({ rowKey: row.key, columnKey: column.key, node: cell(row.key, column.key) }))),
|
|
23
|
-
size,
|
|
24
|
-
};
|
|
25
|
-
}
|
|
26
|
-
|
|
27
6
|
// Badge: Tone × Icon layout. One icon per tone, matching the Variants examples.
|
|
28
7
|
const BADGE_TONES: { key: BadgeVariant; label: string; text: string; icon: React.ComponentProps<typeof Badge>['leadingIcon'] }[] = [
|
|
29
8
|
{ key: 'neutral', label: 'Neutral', text: 'Local', icon: 'pin' },
|
|
@@ -32,10 +11,23 @@ const BADGE_TONES: { key: BadgeVariant; label: string; text: string; icon: React
|
|
|
32
11
|
{ key: 'warning', label: 'Warning', text: 'Delayed', icon: 'triangle-alert' },
|
|
33
12
|
{ key: 'negative', label: 'Negative', text: 'Suspended', icon: 'circle-slash' },
|
|
34
13
|
];
|
|
14
|
+
// `rows` is bound to Badge's own `variant` prop (design §4) — written as its own literal array
|
|
15
|
+
// (not `BADGE_TONES.map(...)`) so `doctor`'s static reader can check it without evaluating a
|
|
16
|
+
// function call; `BADGE_TONES` above still drives the real rendering in `cell` below.
|
|
17
|
+
const BADGE_ROWS = {
|
|
18
|
+
prop: 'variant',
|
|
19
|
+
items: [
|
|
20
|
+
{ key: 'neutral', label: 'Neutral' },
|
|
21
|
+
{ key: 'info', label: 'Info' },
|
|
22
|
+
{ key: 'positive', label: 'Positive' },
|
|
23
|
+
{ key: 'warning', label: 'Warning' },
|
|
24
|
+
{ key: 'negative', label: 'Negative' },
|
|
25
|
+
],
|
|
26
|
+
} as const;
|
|
35
27
|
const BADGE_COMPARISON = grid(
|
|
36
28
|
'Tone',
|
|
37
29
|
'Icon',
|
|
38
|
-
|
|
30
|
+
BADGE_ROWS,
|
|
39
31
|
[
|
|
40
32
|
{ key: 'label-only', label: 'Label only' },
|
|
41
33
|
{ key: 'leading-icon', label: 'Leading icon' },
|
|
@@ -235,7 +235,7 @@ const styles = StyleSheet.create({
|
|
|
235
235
|
},
|
|
236
236
|
// Translucent pressed overlay — sits above the banner bg so the tinted bg shows through.
|
|
237
237
|
pressOverlay: {
|
|
238
|
-
...StyleSheet.
|
|
238
|
+
...StyleSheet.absoluteFill,
|
|
239
239
|
backgroundColor: DS_SEMANTIC.interaction.pressed,
|
|
240
240
|
borderRadius: DS_RADIUS.medium,
|
|
241
241
|
},
|
|
@@ -126,8 +126,8 @@ export function BottomSheet({ visible, onDismiss, header, children, footer, styl
|
|
|
126
126
|
}
|
|
127
127
|
|
|
128
128
|
const styles = StyleSheet.create({
|
|
129
|
-
overlay: { ...StyleSheet.
|
|
130
|
-
backdrop: { ...StyleSheet.
|
|
129
|
+
overlay: { ...StyleSheet.absoluteFill, justifyContent: 'flex-end' },
|
|
130
|
+
backdrop: { ...StyleSheet.absoluteFill, backgroundColor: DS_SEMANTIC.element.overlayBackdrop },
|
|
131
131
|
sheet: {
|
|
132
132
|
maxHeight: MAX_HEIGHT_PERCENT,
|
|
133
133
|
backgroundColor: DS_SEMANTIC.surface.white,
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
2
|
import { View, StyleSheet } from 'react-native';
|
|
3
|
-
import { defineCatalogPage,
|
|
3
|
+
import { defineCatalogPage, grid } from '@krapwoo/ds-viewer';
|
|
4
4
|
import { Button } from './Button';
|
|
5
5
|
import type { ButtonVariant } from './Button.types';
|
|
6
6
|
import { DS_SEMANTIC } from '../../tokens';
|
|
@@ -16,38 +16,24 @@ const styles = StyleSheet.create({
|
|
|
16
16
|
},
|
|
17
17
|
});
|
|
18
18
|
|
|
19
|
-
// Grid comparisons: each cell is a real instance with exactly the props its row and column name.
|
|
20
|
-
// Never build these by multiplying `variants` with `states` — those are pre-rendered nodes and
|
|
21
|
-
// cannot combine.
|
|
22
|
-
function grid(
|
|
23
|
-
rowLabel: string,
|
|
24
|
-
columnLabel: string,
|
|
25
|
-
rows: { key: string; label: string }[],
|
|
26
|
-
columns: { key: string; label: string }[],
|
|
27
|
-
cell: (row: string, column: string) => React.ReactNode,
|
|
28
|
-
size?: ComparisonDef['size'],
|
|
29
|
-
): ComparisonDef {
|
|
30
|
-
return {
|
|
31
|
-
rowLabel,
|
|
32
|
-
columnLabel,
|
|
33
|
-
rows,
|
|
34
|
-
columns,
|
|
35
|
-
cells: rows.flatMap((row) => columns.map((column) => ({ rowKey: row.key, columnKey: column.key, node: cell(row.key, column.key) }))),
|
|
36
|
-
size,
|
|
37
|
-
};
|
|
38
|
-
}
|
|
39
|
-
|
|
40
19
|
// Button: Variant × State. `white` keeps the dark backdrop its variant requires.
|
|
20
|
+
// `rows` is bound to Button's own `variant` prop (design §4): each row key below is an actual
|
|
21
|
+
// `ButtonVariant` option, so `doctor` can tell when one is renamed or removed. `columns` names no
|
|
22
|
+
// single prop (disabled/loading are two separate booleans, not one "State" prop) and stays unbound
|
|
23
|
+
// — unbound axes are just as valid, and `doctor` never flags one.
|
|
41
24
|
const BUTTON_COMPARISON = grid(
|
|
42
25
|
'Variant',
|
|
43
26
|
'State',
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
27
|
+
{
|
|
28
|
+
prop: 'variant',
|
|
29
|
+
items: [
|
|
30
|
+
{ key: 'primary', label: 'Primary' },
|
|
31
|
+
{ key: 'secondary', label: 'Secondary' },
|
|
32
|
+
{ key: 'tertiary', label: 'Tertiary' },
|
|
33
|
+
{ key: 'white', label: 'White' },
|
|
34
|
+
{ key: 'ghost', label: 'Ghost' },
|
|
35
|
+
],
|
|
36
|
+
},
|
|
51
37
|
[
|
|
52
38
|
{ key: 'default', label: 'Default' },
|
|
53
39
|
{ key: 'disabled', label: 'Disabled' },
|
|
@@ -65,12 +65,12 @@ export function Dialog({ visible, onDismiss, children, style }: DialogProps) {
|
|
|
65
65
|
|
|
66
66
|
const styles = StyleSheet.create({
|
|
67
67
|
overlay: {
|
|
68
|
-
...StyleSheet.
|
|
68
|
+
...StyleSheet.absoluteFill,
|
|
69
69
|
alignItems: 'center',
|
|
70
70
|
justifyContent: 'center',
|
|
71
71
|
padding: DS_SPACING[800],
|
|
72
72
|
},
|
|
73
|
-
backdrop: { ...StyleSheet.
|
|
73
|
+
backdrop: { ...StyleSheet.absoluteFill, backgroundColor: DS_SEMANTIC.element.overlayBackdrop },
|
|
74
74
|
card: {
|
|
75
75
|
width: '100%',
|
|
76
76
|
maxWidth: 400,
|
|
@@ -1,36 +1,22 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
|
-
import { defineCatalogPage,
|
|
2
|
+
import { defineCatalogPage, grid } from '@krapwoo/ds-viewer';
|
|
3
3
|
import { Pill } from './Pill';
|
|
4
4
|
|
|
5
|
-
// Grid comparisons: each cell is a real instance with exactly the props its row and column name.
|
|
6
|
-
// Never build these by multiplying `variants` with `states` — those are pre-rendered nodes and
|
|
7
|
-
// cannot combine.
|
|
8
|
-
function grid(
|
|
9
|
-
rowLabel: string,
|
|
10
|
-
columnLabel: string,
|
|
11
|
-
rows: { key: string; label: string }[],
|
|
12
|
-
columns: { key: string; label: string }[],
|
|
13
|
-
cell: (row: string, column: string) => React.ReactNode,
|
|
14
|
-
size?: ComparisonDef['size'],
|
|
15
|
-
): ComparisonDef {
|
|
16
|
-
return {
|
|
17
|
-
rowLabel,
|
|
18
|
-
columnLabel,
|
|
19
|
-
rows,
|
|
20
|
-
columns,
|
|
21
|
-
cells: rows.flatMap((row) => columns.map((column) => ({ rowKey: row.key, columnKey: column.key, node: cell(row.key, column.key) }))),
|
|
22
|
-
size,
|
|
23
|
-
};
|
|
24
|
-
}
|
|
25
|
-
|
|
26
5
|
// Pill: Selection × State.
|
|
6
|
+
// `rows` is bound to Pill's own `variant` prop (design §4); the second item's key is
|
|
7
|
+
// `'not_selected'` (underscore), matching `PillVariant` exactly — not `'not-selected'`, which is
|
|
8
|
+
// only this page's own label-ish spelling and would fail `doctor`'s "item key must be a real
|
|
9
|
+
// option" check.
|
|
27
10
|
const PILL_COMPARISON = grid(
|
|
28
11
|
'Selection',
|
|
29
12
|
'State',
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
13
|
+
{
|
|
14
|
+
prop: 'variant',
|
|
15
|
+
items: [
|
|
16
|
+
{ key: 'selected', label: 'Selected' },
|
|
17
|
+
{ key: 'not_selected', label: 'Not selected' },
|
|
18
|
+
],
|
|
19
|
+
},
|
|
34
20
|
[
|
|
35
21
|
{ key: 'icon-text', label: 'Icon + Text' },
|
|
36
22
|
{ key: 'icon-only', label: 'Icon-only' },
|