@ponchia/ui 0.6.12 → 0.8.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.
Files changed (84) hide show
  1. package/CHANGELOG.md +210 -0
  2. package/MIGRATIONS.json +14 -0
  3. package/README.md +14 -6
  4. package/behaviors/dialog.d.ts.map +1 -1
  5. package/behaviors/dialog.js +14 -0
  6. package/behaviors/modal.d.ts +4 -0
  7. package/behaviors/modal.d.ts.map +1 -1
  8. package/behaviors/modal.js +4 -0
  9. package/behaviors/splitter.d.ts +2 -0
  10. package/behaviors/splitter.d.ts.map +1 -1
  11. package/behaviors/splitter.js +15 -1
  12. package/behaviors/theme.d.ts +3 -2
  13. package/behaviors/theme.d.ts.map +1 -1
  14. package/behaviors/theme.js +10 -6
  15. package/bin/bronto-ui-check.mjs +286 -0
  16. package/classes/classes.json +86 -7
  17. package/classes/index.d.ts +53 -1
  18. package/classes/index.js +60 -0
  19. package/classes/vscode.css-custom-data.json +24 -0
  20. package/css/app.css +14 -3
  21. package/css/disclosure.css +15 -5
  22. package/css/dots.css +43 -18
  23. package/css/feedback.css +46 -8
  24. package/css/forms.css +3 -3
  25. package/css/navigation.css +1 -1
  26. package/css/overlay.css +19 -5
  27. package/css/primitives.css +101 -6
  28. package/css/report.css +0 -40
  29. package/css/site.css +19 -3
  30. package/css/skins.css +97 -3
  31. package/css/state.css +161 -0
  32. package/css/table.css +1 -1
  33. package/css/tokens.css +6 -0
  34. package/css/workbench.css +151 -0
  35. package/dist/bronto.css +1 -1
  36. package/dist/css/app.css +1 -1
  37. package/dist/css/disclosure.css +1 -1
  38. package/dist/css/dots.css +1 -1
  39. package/dist/css/feedback.css +1 -1
  40. package/dist/css/forms.css +1 -1
  41. package/dist/css/navigation.css +1 -1
  42. package/dist/css/overlay.css +1 -1
  43. package/dist/css/primitives.css +1 -1
  44. package/dist/css/report-kit.css +1 -1
  45. package/dist/css/report.css +1 -1
  46. package/dist/css/site.css +1 -1
  47. package/dist/css/skins.css +1 -1
  48. package/dist/css/state.css +1 -1
  49. package/dist/css/table.css +1 -1
  50. package/dist/css/tokens.css +1 -1
  51. package/dist/css/workbench.css +1 -1
  52. package/docs/adr/0001-color-system.md +32 -3
  53. package/docs/adr/0004-prune-unused-adapters.md +34 -0
  54. package/docs/architecture.md +14 -10
  55. package/docs/command.md +18 -4
  56. package/docs/contrast.md +102 -18
  57. package/docs/migrations/0.6-to-0.7.md +85 -0
  58. package/docs/package-contract.md +10 -5
  59. package/docs/reference.md +52 -1
  60. package/docs/reporting.md +8 -8
  61. package/docs/stability.md +39 -9
  62. package/docs/state.md +51 -1
  63. package/docs/theming.md +67 -5
  64. package/docs/usage.md +119 -19
  65. package/docs/workbench.md +99 -6
  66. package/llms.txt +7 -3
  67. package/package.json +13 -3
  68. package/qwik/index.d.ts.map +1 -1
  69. package/qwik/index.js +4 -0
  70. package/react/index.d.ts.map +1 -1
  71. package/react/index.js +4 -0
  72. package/solid/index.d.ts.map +1 -1
  73. package/solid/index.js +4 -0
  74. package/svelte/index.d.ts.map +1 -1
  75. package/svelte/index.js +4 -0
  76. package/tokens/figma.variables.json +84 -0
  77. package/tokens/index.d.ts +2 -2
  78. package/tokens/index.js +23 -0
  79. package/tokens/index.json +12 -0
  80. package/tokens/resolved.json +6 -0
  81. package/tokens/skins.js +117 -7
  82. package/tokens/tokens.dtcg.json +2514 -399
  83. package/vue/index.d.ts.map +1 -1
  84. package/vue/index.js +4 -0
@@ -0,0 +1,286 @@
1
+ #!/usr/bin/env node
2
+ /** Validate literal Bronto classes and CSS custom-property references in a consumer. */
3
+ import { readFileSync, readdirSync, realpathSync, statSync } from 'node:fs';
4
+ import { extname, resolve, relative, dirname } from 'node:path';
5
+ import { fileURLToPath } from 'node:url';
6
+
7
+ const packageRoot = resolve(dirname(fileURLToPath(import.meta.url)), '..');
8
+ const classesManifest = JSON.parse(
9
+ readFileSync(resolve(packageRoot, 'classes/classes.json'), 'utf8'),
10
+ );
11
+ const tokensManifest = JSON.parse(readFileSync(resolve(packageRoot, 'tokens/index.json'), 'utf8'));
12
+
13
+ const SOURCE_EXTENSIONS = new Set([
14
+ '.astro',
15
+ '.css',
16
+ '.html',
17
+ '.js',
18
+ '.jsx',
19
+ '.mjs',
20
+ '.svelte',
21
+ '.ts',
22
+ '.tsx',
23
+ '.vue',
24
+ ]);
25
+ const SKIP_DIRS = new Set([
26
+ '.git',
27
+ '.astro',
28
+ '.next',
29
+ '.nuxt',
30
+ '.output',
31
+ '.pytest_cache',
32
+ '.svelte-kit',
33
+ '.tox',
34
+ '.vercel',
35
+ '.venv',
36
+ '.vite',
37
+ '__pycache__',
38
+ 'build',
39
+ 'coverage',
40
+ 'dist',
41
+ 'node_modules',
42
+ 'out',
43
+ 'playwright-report',
44
+ 'public',
45
+ 'storybook-static',
46
+ 'test-results',
47
+ 'vendor',
48
+ 'venv',
49
+ ]);
50
+
51
+ const knownClasses = new Set(classesManifest.classes);
52
+ // CSS generic font-family keywords share the ui-* prefix but are never class
53
+ // literals. Keep the scanner broad enough to catch JS-built class strings
54
+ // while excluding these standardized non-class identifiers.
55
+ const nonClassIdentifiers = new Set(['ui-monospace', 'ui-rounded', 'ui-sans-serif', 'ui-serif']);
56
+ const knownTokens = new Set(
57
+ Object.values(tokensManifest.cssVars).flatMap((group) => Object.keys(group)),
58
+ );
59
+ for (const property of classesManifest.customProperties) knownTokens.add(property.name);
60
+ for (const entry of readdirSync(resolve(packageRoot, 'dist/css'), { withFileTypes: true })) {
61
+ if (!entry.isFile() || extname(entry.name) !== '.css') continue;
62
+ const css = readFileSync(resolve(packageRoot, 'dist/css', entry.name), 'utf8');
63
+ for (const match of css.matchAll(/(--[a-z][\w-]*)\s*:/gi)) knownTokens.add(match[1]);
64
+ }
65
+ const reservedTokenPrefixes = new Set(
66
+ [...knownTokens].map((name) => `--${name.slice(2).split('-')[0]}`),
67
+ );
68
+ const LINE_COMMENT_EXTENSIONS = new Set([
69
+ '.astro',
70
+ '.html',
71
+ '.js',
72
+ '.jsx',
73
+ '.mjs',
74
+ '.svelte',
75
+ '.ts',
76
+ '.tsx',
77
+ '.vue',
78
+ ]);
79
+ const HTML_COMMENT_EXTENSIONS = new Set(['.astro', '.html', '.svelte', '.vue']);
80
+
81
+ const blankComment = (value) => value.replace(/[^\r\n]/g, ' ');
82
+
83
+ function quoteEnd(text, start, quote) {
84
+ for (let index = start + 1; index < text.length; index += 1) {
85
+ if (text[index] === '\\') index += 1;
86
+ else if (text[index] === quote) return index + 1;
87
+ }
88
+ return text.length;
89
+ }
90
+
91
+ function stripSlashComments(text, lineComments) {
92
+ let output = '';
93
+ let index = 0;
94
+ while (index < text.length) {
95
+ const char = text[index];
96
+ const next = text[index + 1];
97
+ if (char === '"' || char === "'" || char === '`') {
98
+ const end = quoteEnd(text, index, char);
99
+ output += text.slice(index, end);
100
+ index = end;
101
+ continue;
102
+ }
103
+ if (char === '/' && next === '*') {
104
+ const close = text.indexOf('*/', index + 2);
105
+ const end = close === -1 ? text.length : close + 2;
106
+ output += blankComment(text.slice(index, end));
107
+ index = end;
108
+ continue;
109
+ }
110
+ if (lineComments && char === '/' && next === '/') {
111
+ const newline = text.indexOf('\n', index + 2);
112
+ const end = newline === -1 ? text.length : newline;
113
+ output += blankComment(text.slice(index, end));
114
+ index = end;
115
+ continue;
116
+ }
117
+ output += char;
118
+ index += 1;
119
+ }
120
+ return output;
121
+ }
122
+
123
+ function sourceText(text, extension) {
124
+ const withoutHtml = HTML_COMMENT_EXTENSIONS.has(extension)
125
+ ? text.replace(/<!--[\s\S]*?-->/g, blankComment)
126
+ : text;
127
+ return stripSlashComments(withoutHtml, LINE_COMMENT_EXTENSIONS.has(extension));
128
+ }
129
+
130
+ function lineAt(text, index) {
131
+ return text.slice(0, index).split('\n').length;
132
+ }
133
+
134
+ function filesUnder(input) {
135
+ const absolute = resolve(input);
136
+ const stat = statSync(absolute);
137
+ if (stat.isFile()) return SOURCE_EXTENSIONS.has(extname(absolute)) ? [absolute] : [];
138
+ if (!stat.isDirectory()) return [];
139
+ const files = [];
140
+ for (const entry of readdirSync(absolute, { withFileTypes: true })) {
141
+ if (entry.isSymbolicLink()) continue;
142
+ const child = resolve(absolute, entry.name);
143
+ if (entry.isDirectory()) {
144
+ if (!SKIP_DIRS.has(entry.name)) files.push(...filesUnder(child));
145
+ } else if (entry.isFile() && SOURCE_EXTENSIONS.has(extname(entry.name))) {
146
+ files.push(child);
147
+ }
148
+ }
149
+ return files;
150
+ }
151
+
152
+ function tokenPrefix(name) {
153
+ return `--${name.slice(2).split('-')[0]}`;
154
+ }
155
+
156
+ export function checkPaths(inputs, { allowClasses = [], allowTokens = [] } = {}) {
157
+ const allowedClasses = new Set([...knownClasses, ...allowClasses]);
158
+ const allowedTokens = new Set([...knownTokens, ...allowTokens]);
159
+ const files = [...new Set(inputs.flatMap(filesUnder))].sort();
160
+ const documents = files.map((file) => {
161
+ const text = readFileSync(file, 'utf8');
162
+ return { file, text, scanned: sourceText(text, extname(file)) };
163
+ });
164
+ const locallyDefinedTokens = new Set();
165
+ for (const { scanned } of documents) {
166
+ for (const match of scanned.matchAll(/(--[a-z][\w-]*)\s*:/gi)) {
167
+ locallyDefinedTokens.add(match[1]);
168
+ }
169
+ }
170
+
171
+ const findings = [];
172
+ const seen = new Set();
173
+ const add = (finding) => {
174
+ const key = `${finding.kind}:${finding.file}:${finding.line}:${finding.name}`;
175
+ if (seen.has(key)) return;
176
+ seen.add(key);
177
+ findings.push(finding);
178
+ };
179
+
180
+ for (const { file, text, scanned } of documents) {
181
+ for (const match of scanned.matchAll(/(?<![/\w-])ui-[a-z0-9](?:[\w-]*[a-z0-9])?(?![\w/-])/gi)) {
182
+ if (!allowedClasses.has(match[0]) && !nonClassIdentifiers.has(match[0])) {
183
+ add({ kind: 'class', file, line: lineAt(text, match.index), name: match[0] });
184
+ }
185
+ }
186
+ for (const match of scanned.matchAll(/var\(\s*(--[a-z][\w-]*)/gi)) {
187
+ const name = match[1];
188
+ if (
189
+ reservedTokenPrefixes.has(tokenPrefix(name)) &&
190
+ !allowedTokens.has(name) &&
191
+ !locallyDefinedTokens.has(name)
192
+ ) {
193
+ add({ kind: 'token', file, line: lineAt(text, match.index), name });
194
+ }
195
+ }
196
+ }
197
+
198
+ return { files: files.length, findings };
199
+ }
200
+
201
+ function usage() {
202
+ return (
203
+ `Usage: bronto-ui-check [options] [path ...]\n\n` +
204
+ `Validate literal ui-* classes and unresolved Bronto-like var(--*) references.\n\n` +
205
+ `Options:\n` +
206
+ ` --allow-class NAME Allow one consumer-owned ui-* class (repeatable)\n` +
207
+ ` --allow-token NAME Allow one consumer-owned --* token (repeatable)\n` +
208
+ ` --json Print machine-readable JSON\n` +
209
+ ` --help Show this help\n`
210
+ );
211
+ }
212
+
213
+ function parseArgs(args) {
214
+ const options = { allowClasses: [], allowTokens: [], json: false, paths: [] };
215
+ for (let index = 0; index < args.length; index += 1) {
216
+ const arg = args[index];
217
+ if (arg === '--help') return { ...options, help: true };
218
+ if (arg === '--json') options.json = true;
219
+ else if (arg === '--allow-class') {
220
+ const value = args[++index];
221
+ if (!/^ui-[a-z0-9][\w-]*$/i.test(value || '')) {
222
+ throw new Error('--allow-class requires one ui-* class name');
223
+ }
224
+ options.allowClasses.push(value);
225
+ } else if (arg === '--allow-token') {
226
+ const value = args[++index];
227
+ if (!/^--[a-z][\w-]*$/i.test(value || '')) {
228
+ throw new Error('--allow-token requires one --* custom-property name');
229
+ }
230
+ options.allowTokens.push(value);
231
+ } else if (arg.startsWith('--')) throw new Error(`Unknown option: ${arg}`);
232
+ else options.paths.push(arg);
233
+ }
234
+ return options;
235
+ }
236
+
237
+ function main() {
238
+ let options;
239
+ try {
240
+ options = parseArgs(process.argv.slice(2));
241
+ } catch (error) {
242
+ console.error(error.message);
243
+ console.error(usage());
244
+ process.exitCode = 2;
245
+ return;
246
+ }
247
+ if (options.help) {
248
+ console.log(usage());
249
+ return;
250
+ }
251
+ const paths = options.paths.length ? options.paths : ['.'];
252
+ let result;
253
+ try {
254
+ result = checkPaths(paths, options);
255
+ } catch (error) {
256
+ console.error(`[bronto-ui-check] ${error.message}`);
257
+ process.exitCode = 2;
258
+ return;
259
+ }
260
+ const cwd = process.cwd();
261
+ const output = {
262
+ files: result.files,
263
+ findings: result.findings.map((finding) => ({
264
+ ...finding,
265
+ file: relative(cwd, finding.file) || '.',
266
+ })),
267
+ };
268
+ if (options.json) console.log(JSON.stringify(output, null, 2));
269
+ else if (output.findings.length) {
270
+ for (const finding of output.findings) {
271
+ console.error(
272
+ `${finding.file}:${finding.line} unknown Bronto ${finding.kind} ${finding.name}`,
273
+ );
274
+ }
275
+ console.error(
276
+ `[bronto-ui-check] ${output.findings.length} finding(s) in ${output.files} source file(s)`,
277
+ );
278
+ } else {
279
+ console.log(`[bronto-ui-check] ${output.files} source file(s) match the shipped contract`);
280
+ }
281
+ if (output.findings.length) process.exitCode = 1;
282
+ }
283
+
284
+ // npm installs bins as symlinks in node_modules/.bin. Compare their real path
285
+ // so the CLI runs both through that public entrypoint and by its package path.
286
+ if (process.argv[1] && realpathSync(process.argv[1]) === fileURLToPath(import.meta.url)) main();
@@ -1,8 +1,8 @@
1
1
  {
2
2
  "$comment": "@ponchia/ui class vocabulary as language-neutral data — validate emitted markup without executing the ESM cls map or parsing the .d.ts. Generated from classes/index.js — do not edit by hand; run `npm run classes:json:build`. Drift-checked in CI. `groups[].base` is null for a parts-only namespace (no standalone base class — do NOT emit it). A modifier whose name contains `__` (e.g. `ui-spark__bar--pos`) attaches to THAT part, not the base host. `states` is the author-applied `is-*` hooks (runtime/behavior-managed hooks are excluded); `behaviorAttributes` are the `data-bronto-*` wiring hooks the optional behaviors delegate on; `requiredAria` is the role/aria a generator must emit per component. `states` + `customProperties` are documented in docs/reference.md and ship outside `cls` by design.",
3
3
  "counts": {
4
- "classes": 644,
5
- "groups": 179
4
+ "classes": 669,
5
+ "groups": 183
6
6
  },
7
7
  "groups": {
8
8
  "ui-accordion": {
@@ -242,13 +242,16 @@
242
242
  "base": "ui-button",
243
243
  "modifiers": [
244
244
  "ui-button--danger",
245
+ "ui-button--dense",
245
246
  "ui-button--ghost",
246
247
  "ui-button--icon",
247
248
  "ui-button--lg",
248
249
  "ui-button--sm",
249
250
  "ui-button--subtle"
250
251
  ],
251
- "parts": []
252
+ "parts": [
253
+ "ui-button__label"
254
+ ]
252
255
  },
253
256
  "ui-card": {
254
257
  "base": "ui-card",
@@ -545,8 +548,14 @@
545
548
  },
546
549
  "ui-empty-state": {
547
550
  "base": "ui-empty-state",
548
- "modifiers": [],
549
- "parts": []
551
+ "modifiers": [
552
+ "ui-empty-state--invite"
553
+ ],
554
+ "parts": [
555
+ "ui-empty-state__glyph",
556
+ "ui-empty-state__hint",
557
+ "ui-empty-state__lead"
558
+ ]
550
559
  },
551
560
  "ui-error-summary": {
552
561
  "base": "ui-error-summary",
@@ -910,6 +919,17 @@
910
919
  "ui-pagination__item"
911
920
  ]
912
921
  },
922
+ "ui-pane": {
923
+ "base": "ui-pane",
924
+ "modifiers": [],
925
+ "parts": [
926
+ "ui-pane__actions",
927
+ "ui-pane__body",
928
+ "ui-pane__head",
929
+ "ui-pane__title",
930
+ "ui-pane__title-input"
931
+ ]
932
+ },
913
933
  "ui-panel": {
914
934
  "base": "ui-panel",
915
935
  "modifiers": [],
@@ -1104,12 +1124,34 @@
1104
1124
  },
1105
1125
  "ui-selectionbar": {
1106
1126
  "base": "ui-selectionbar",
1107
- "modifiers": [],
1127
+ "modifiers": [
1128
+ "ui-selectionbar--anchor-block-end",
1129
+ "ui-selectionbar--anchor-block-start",
1130
+ "ui-selectionbar--anchored"
1131
+ ],
1108
1132
  "parts": [
1109
1133
  "ui-selectionbar__actions",
1110
1134
  "ui-selectionbar__count"
1111
1135
  ]
1112
1136
  },
1137
+ "ui-severity": {
1138
+ "base": "ui-severity",
1139
+ "modifiers": [],
1140
+ "parts": []
1141
+ },
1142
+ "ui-severity-dot": {
1143
+ "base": "ui-severity-dot",
1144
+ "modifiers": [],
1145
+ "parts": []
1146
+ },
1147
+ "ui-severity-row": {
1148
+ "base": "ui-severity-row",
1149
+ "modifiers": [],
1150
+ "parts": [
1151
+ "ui-severity-row__meta",
1152
+ "ui-severity-row__title"
1153
+ ]
1154
+ },
1113
1155
  "ui-shortcut": {
1114
1156
  "base": "ui-shortcut",
1115
1157
  "modifiers": [],
@@ -1447,13 +1489,18 @@
1447
1489
  "ui-toolstrip": {
1448
1490
  "base": "ui-toolstrip",
1449
1491
  "modifiers": [
1492
+ "ui-toolstrip--anchor-block-end",
1493
+ "ui-toolstrip--anchor-block-start",
1494
+ "ui-toolstrip--anchored",
1450
1495
  "ui-toolstrip--compact",
1451
- "ui-toolstrip--floating"
1496
+ "ui-toolstrip--floating",
1497
+ "ui-toolstrip--pane"
1452
1498
  ],
1453
1499
  "parts": [
1454
1500
  "ui-toolstrip__actions",
1455
1501
  "ui-toolstrip__brand",
1456
1502
  "ui-toolstrip__context",
1503
+ "ui-toolstrip__fill",
1457
1504
  "ui-toolstrip__group",
1458
1505
  "ui-toolstrip__search"
1459
1506
  ]
@@ -1610,11 +1657,13 @@
1610
1657
  "ui-bullet__target",
1611
1658
  "ui-button",
1612
1659
  "ui-button--danger",
1660
+ "ui-button--dense",
1613
1661
  "ui-button--ghost",
1614
1662
  "ui-button--icon",
1615
1663
  "ui-button--lg",
1616
1664
  "ui-button--sm",
1617
1665
  "ui-button--subtle",
1666
+ "ui-button__label",
1618
1667
  "ui-card",
1619
1668
  "ui-card--accent",
1620
1669
  "ui-card--interactive",
@@ -1748,6 +1797,10 @@
1748
1797
  "ui-dotspinner--lg",
1749
1798
  "ui-dotspinner--sm",
1750
1799
  "ui-empty-state",
1800
+ "ui-empty-state--invite",
1801
+ "ui-empty-state__glyph",
1802
+ "ui-empty-state__hint",
1803
+ "ui-empty-state__lead",
1751
1804
  "ui-error-summary",
1752
1805
  "ui-error-summary__list",
1753
1806
  "ui-error-summary__title",
@@ -1907,6 +1960,12 @@
1907
1960
  "ui-pagehead__title",
1908
1961
  "ui-pagination",
1909
1962
  "ui-pagination__item",
1963
+ "ui-pane",
1964
+ "ui-pane__actions",
1965
+ "ui-pane__body",
1966
+ "ui-pane__head",
1967
+ "ui-pane__title",
1968
+ "ui-pane__title-input",
1910
1969
  "ui-panel",
1911
1970
  "ui-panel__head",
1912
1971
  "ui-popover",
@@ -1994,8 +2053,16 @@
1994
2053
  "ui-sel--on",
1995
2054
  "ui-select",
1996
2055
  "ui-selectionbar",
2056
+ "ui-selectionbar--anchor-block-end",
2057
+ "ui-selectionbar--anchor-block-start",
2058
+ "ui-selectionbar--anchored",
1997
2059
  "ui-selectionbar__actions",
1998
2060
  "ui-selectionbar__count",
2061
+ "ui-severity",
2062
+ "ui-severity-dot",
2063
+ "ui-severity-row",
2064
+ "ui-severity-row__meta",
2065
+ "ui-severity-row__title",
1999
2066
  "ui-shortcut",
2000
2067
  "ui-shortcut__sep",
2001
2068
  "ui-sidebar",
@@ -2124,11 +2191,16 @@
2124
2191
  "ui-tool-call__status",
2125
2192
  "ui-tool-log",
2126
2193
  "ui-toolstrip",
2194
+ "ui-toolstrip--anchor-block-end",
2195
+ "ui-toolstrip--anchor-block-start",
2196
+ "ui-toolstrip--anchored",
2127
2197
  "ui-toolstrip--compact",
2128
2198
  "ui-toolstrip--floating",
2199
+ "ui-toolstrip--pane",
2129
2200
  "ui-toolstrip__actions",
2130
2201
  "ui-toolstrip__brand",
2131
2202
  "ui-toolstrip__context",
2203
+ "ui-toolstrip__fill",
2132
2204
  "ui-toolstrip__group",
2133
2205
  "ui-toolstrip__search",
2134
2206
  "ui-tooltip",
@@ -2791,6 +2863,13 @@
2791
2863
  "behavior": "initSplitter",
2792
2864
  "note": "keyboard + pointer ARIA window-splitter behavior; updates --splitter-pos and aria-valuenow, then emits bronto:splitter:resize. The host owns persistence and pane state."
2793
2865
  },
2866
+ {
2867
+ "name": "data-bronto-splitter-adjust",
2868
+ "on": "a button inside a .ui-splitter host",
2869
+ "value": "signed percentage-point delta, for example -10 or 10",
2870
+ "behavior": "initSplitter",
2871
+ "note": "single-pointer non-drag alternative to moving the separator; activation clamps to aria-valuemin/aria-valuemax and emits bronto:splitter:resize."
2872
+ },
2794
2873
  {
2795
2874
  "name": "data-bronto-source-ref",
2796
2875
  "on": "a button/control that references a source card",
@@ -21,6 +21,8 @@ export declare const cls: {
21
21
  readonly buttonIcon: 'ui-button--icon';
22
22
  readonly buttonSm: 'ui-button--sm';
23
23
  readonly buttonLg: 'ui-button--lg';
24
+ readonly buttonDense: 'ui-button--dense';
25
+ readonly buttonLabel: 'ui-button__label';
24
26
  readonly card: 'ui-card';
25
27
  readonly cardHead: 'ui-card__head';
26
28
  readonly cardAccent: 'ui-card--accent';
@@ -54,6 +56,10 @@ export declare const cls: {
54
56
  readonly linkCta: 'ui-link--cta';
55
57
  readonly keyValue: 'ui-key-value';
56
58
  readonly emptyState: 'ui-empty-state';
59
+ readonly emptyStateInvite: 'ui-empty-state--invite';
60
+ readonly emptyStateGlyph: 'ui-empty-state__glyph';
61
+ readonly emptyStateLead: 'ui-empty-state__lead';
62
+ readonly emptyStateHint: 'ui-empty-state__hint';
57
63
  readonly dot: 'ui-dot';
58
64
  readonly dotAccent: 'ui-dot--accent';
59
65
  readonly dotSuccess: 'ui-dot--success';
@@ -560,6 +566,11 @@ export declare const cls: {
560
566
  readonly jobBlocked: 'ui-job--blocked';
561
567
  readonly jobFailed: 'ui-job--failed';
562
568
  readonly jobComplete: 'ui-job--complete';
569
+ readonly severity: 'ui-severity';
570
+ readonly severityDot: 'ui-severity-dot';
571
+ readonly severityRow: 'ui-severity-row';
572
+ readonly severityRowTitle: 'ui-severity-row__title';
573
+ readonly severityRowMeta: 'ui-severity-row__meta';
563
574
  readonly generated: 'ui-generated';
564
575
  readonly generatedLabel: 'ui-generated__label';
565
576
  readonly originLabel: 'ui-origin-label';
@@ -577,11 +588,22 @@ export declare const cls: {
577
588
  readonly toolstrip: 'ui-toolstrip';
578
589
  readonly toolstripFloating: 'ui-toolstrip--floating';
579
590
  readonly toolstripCompact: 'ui-toolstrip--compact';
591
+ readonly toolstripPane: 'ui-toolstrip--pane';
592
+ readonly toolstripAnchored: 'ui-toolstrip--anchored';
593
+ readonly toolstripAnchorBlockStart: 'ui-toolstrip--anchor-block-start';
594
+ readonly toolstripAnchorBlockEnd: 'ui-toolstrip--anchor-block-end';
580
595
  readonly toolstripBrand: 'ui-toolstrip__brand';
581
596
  readonly toolstripContext: 'ui-toolstrip__context';
582
597
  readonly toolstripGroup: 'ui-toolstrip__group';
583
598
  readonly toolstripActions: 'ui-toolstrip__actions';
599
+ readonly toolstripFill: 'ui-toolstrip__fill';
584
600
  readonly toolstripSearch: 'ui-toolstrip__search';
601
+ readonly pane: 'ui-pane';
602
+ readonly paneHead: 'ui-pane__head';
603
+ readonly paneTitle: 'ui-pane__title';
604
+ readonly paneTitleInput: 'ui-pane__title-input';
605
+ readonly paneActions: 'ui-pane__actions';
606
+ readonly paneBody: 'ui-pane__body';
585
607
  readonly segmentedButtons: 'ui-segmented-buttons';
586
608
  readonly segmentedButtonsButton: 'ui-segmented-buttons__button';
587
609
  readonly property: 'ui-property';
@@ -590,6 +612,9 @@ export declare const cls: {
590
612
  readonly selectionbar: 'ui-selectionbar';
591
613
  readonly selectionbarCount: 'ui-selectionbar__count';
592
614
  readonly selectionbarActions: 'ui-selectionbar__actions';
615
+ readonly selectionbarAnchored: 'ui-selectionbar--anchored';
616
+ readonly selectionbarAnchorBlockStart: 'ui-selectionbar--anchor-block-start';
617
+ readonly selectionbarAnchorBlockEnd: 'ui-selectionbar--anchor-block-end';
593
618
  readonly splitter: 'ui-splitter';
594
619
  readonly splitterVertical: 'ui-splitter--vertical';
595
620
  readonly splitterHorizontal: 'ui-splitter--horizontal';
@@ -666,7 +691,17 @@ export declare function cx(...parts: readonly ClassValue[]): string;
666
691
  export interface ButtonOpts {
667
692
  variant?: 'ghost' | 'subtle' | 'danger';
668
693
  icon?: boolean;
669
- size?: 'sm' | 'lg';
694
+ size?: 'sm' | 'lg' | 'dense';
695
+ }
696
+ export interface EmptyStateOpts {
697
+ invite?: boolean;
698
+ }
699
+ export interface ToolstripOpts {
700
+ variant?: 'floating' | 'compact' | 'pane';
701
+ anchor?: 'block-start' | 'block-end';
702
+ }
703
+ export interface SelectionbarOpts {
704
+ anchor?: 'block-start' | 'block-end';
670
705
  }
671
706
  export interface CardOpts {
672
707
  accent?: boolean;
@@ -952,11 +987,28 @@ export interface Ui {
952
987
  state(opts?: StateOpts): string;
953
988
  job(opts?: JobOpts): string;
954
989
  originLabel(opts?: OriginLabelOpts): string;
990
+ emptyState(opts?: EmptyStateOpts): string;
991
+ toolstrip(opts?: ToolstripOpts): string;
992
+ selectionbar(opts?: SelectionbarOpts): string;
955
993
  }
956
994
 
957
995
  export declare const ui: Ui;
958
996
  export default ui;
959
997
 
998
+ /** The canonical severity ladder, worst to best. `unknown` is deliberately not
999
+ * a member: it means "not measured", not "nearly ok". */
1000
+ export declare const SEVERITY_LEVELS: readonly ['critical', 'error', 'warning', 'notice', 'ok'];
1001
+
1002
+ export type SeverityLevel = (typeof SEVERITY_LEVELS)[number];
1003
+
1004
+ /** Bundles `data-level` with the severity class so the attribute that carries
1005
+ * the meaning cannot be forgotten. An unrecognised level resolves to
1006
+ * `'unknown'`, which paints the neutral tone. */
1007
+ export declare function severity(
1008
+ level: SeverityLevel | (string & {}) | null | undefined,
1009
+ opts?: { part?: 'chip' | 'dot' | 'row' },
1010
+ ): { class: string; 'data-level': string };
1011
+
960
1012
  /** Min/max for the value-bearing fills; defaults to 0–100. */
961
1013
  export interface ValueRangeOpts {
962
1014
  min?: number;