@sveltekitchen/sveltekitchen 0.0.0-stage → 1.0.1

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 (142) hide show
  1. package/README.md +137 -2
  2. package/dist/components/Accordion.svelte +36 -0
  3. package/dist/components/Accordion.svelte.d.ts +15 -0
  4. package/dist/components/AccordionItem.svelte +73 -0
  5. package/dist/components/AccordionItem.svelte.d.ts +21 -0
  6. package/dist/components/Alert.svelte +23 -0
  7. package/dist/components/Alert.svelte.d.ts +15 -0
  8. package/dist/components/Badge.svelte +16 -0
  9. package/dist/components/Badge.svelte.d.ts +15 -0
  10. package/dist/components/Button.svelte +43 -0
  11. package/dist/components/Button.svelte.d.ts +25 -0
  12. package/dist/components/Calendar.svelte +88 -0
  13. package/dist/components/Calendar.svelte.d.ts +13 -0
  14. package/dist/components/Card.svelte +68 -0
  15. package/dist/components/Card.svelte.d.ts +25 -0
  16. package/dist/components/Chevron.svelte +36 -0
  17. package/dist/components/Chevron.svelte.d.ts +19 -0
  18. package/dist/components/Collapsible.svelte +46 -0
  19. package/dist/components/Collapsible.svelte.d.ts +19 -0
  20. package/dist/components/ConfirmDialog.svelte +70 -0
  21. package/dist/components/ConfirmDialog.svelte.d.ts +27 -0
  22. package/dist/components/DatePicker.svelte +60 -0
  23. package/dist/components/DatePicker.svelte.d.ts +17 -0
  24. package/dist/components/Divider.svelte +25 -0
  25. package/dist/components/Divider.svelte.d.ts +17 -0
  26. package/dist/components/Dropdown.svelte +100 -0
  27. package/dist/components/Dropdown.svelte.d.ts +21 -0
  28. package/dist/components/Form/Checkbox.svelte +37 -0
  29. package/dist/components/Form/Checkbox.svelte.d.ts +19 -0
  30. package/dist/components/Form/Field.svelte +28 -0
  31. package/dist/components/Form/Field.svelte.d.ts +21 -0
  32. package/dist/components/Form/Input.svelte +56 -0
  33. package/dist/components/Form/Input.svelte.d.ts +29 -0
  34. package/dist/components/Form/MaskedInput.svelte +152 -0
  35. package/dist/components/Form/MaskedInput.svelte.d.ts +25 -0
  36. package/dist/components/Form/Radio.svelte +28 -0
  37. package/dist/components/Form/Radio.svelte.d.ts +19 -0
  38. package/dist/components/Form/RadioGroup.svelte +28 -0
  39. package/dist/components/Form/RadioGroup.svelte.d.ts +19 -0
  40. package/dist/components/Form/Select.svelte +20 -0
  41. package/dist/components/Form/Select.svelte.d.ts +19 -0
  42. package/dist/components/Form/Textarea.svelte +30 -0
  43. package/dist/components/Form/Textarea.svelte.d.ts +25 -0
  44. package/dist/components/Form/Toggle.svelte +21 -0
  45. package/dist/components/Form/Toggle.svelte.d.ts +17 -0
  46. package/dist/components/Modal.svelte +77 -0
  47. package/dist/components/Modal.svelte.d.ts +27 -0
  48. package/dist/components/Pagination.svelte +77 -0
  49. package/dist/components/Pagination.svelte.d.ts +17 -0
  50. package/dist/components/Progress.svelte +34 -0
  51. package/dist/components/Progress.svelte.d.ts +21 -0
  52. package/dist/components/Spinner.svelte +24 -0
  53. package/dist/components/Spinner.svelte.d.ts +13 -0
  54. package/dist/components/Table.svelte +100 -0
  55. package/dist/components/Table.svelte.d.ts +21 -0
  56. package/dist/components/ThemeToggle.svelte +22 -0
  57. package/dist/components/ThemeToggle.svelte.d.ts +11 -0
  58. package/dist/components/Tooltip.svelte +45 -0
  59. package/dist/components/Tooltip.svelte.d.ts +15 -0
  60. package/dist/css/base/root.css +103 -0
  61. package/dist/css/base.css +47 -0
  62. package/dist/css/components/accordion.css +151 -0
  63. package/dist/css/components/alert.css +56 -0
  64. package/dist/css/components/badge.css +56 -0
  65. package/dist/css/components/button.css +171 -0
  66. package/dist/css/components/calendar.css +105 -0
  67. package/dist/css/components/card.css +128 -0
  68. package/dist/css/components/checkbox-radio.css +105 -0
  69. package/dist/css/components/collapsible.css +61 -0
  70. package/dist/css/components/divider.css +42 -0
  71. package/dist/css/components/dock-layout.css +111 -0
  72. package/dist/css/components/dropdown.css +68 -0
  73. package/dist/css/components/floating-shell.css +93 -0
  74. package/dist/css/components/form.css +286 -0
  75. package/dist/css/components/login.css +145 -0
  76. package/dist/css/components/modal.css +179 -0
  77. package/dist/css/components/nav.css +190 -0
  78. package/dist/css/components/nestable.css +187 -0
  79. package/dist/css/components/pagination.css +50 -0
  80. package/dist/css/components/progress.css +50 -0
  81. package/dist/css/components/sidebar.css +78 -0
  82. package/dist/css/components/spinner.css +36 -0
  83. package/dist/css/components/table.css +98 -0
  84. package/dist/css/components/tooltip.css +77 -0
  85. package/dist/css/components/topbar-layout.css +108 -0
  86. package/dist/css/icons/icons.css +52 -0
  87. package/dist/css/index.css +20 -0
  88. package/dist/css/layout/container.css +12 -0
  89. package/dist/css/layout/grid.css +40 -0
  90. package/dist/css/layout/shell.css +185 -0
  91. package/dist/css/overlay/default.css +27 -0
  92. package/dist/css/tokens/colors.css +81 -0
  93. package/dist/css/tokens/radius.css +8 -0
  94. package/dist/css/tokens/shadows.css +23 -0
  95. package/dist/css/tokens/spacing.css +30 -0
  96. package/dist/css/tokens/transitions.css +10 -0
  97. package/dist/css/tokens/typography.css +44 -0
  98. package/dist/index.d.ts +43 -0
  99. package/dist/index.js +52 -0
  100. package/dist/layout/NavItem.svelte +84 -0
  101. package/dist/layout/NavItem.svelte.d.ts +25 -0
  102. package/dist/layout/Shell.svelte +7 -0
  103. package/dist/layout/Shell.svelte.d.ts +13 -0
  104. package/dist/layout/SidebarProfile.svelte +31 -0
  105. package/dist/layout/SidebarProfile.svelte.d.ts +19 -0
  106. package/dist/layouts/AppShell.svelte +60 -0
  107. package/dist/layouts/AppShell.svelte.d.ts +21 -0
  108. package/dist/layouts/BarLayout.svelte +60 -0
  109. package/dist/layouts/BarLayout.svelte.d.ts +21 -0
  110. package/dist/layouts/BottomBarLayout.svelte +23 -0
  111. package/dist/layouts/BottomBarLayout.svelte.d.ts +15 -0
  112. package/dist/layouts/DockLayout.svelte +81 -0
  113. package/dist/layouts/DockLayout.svelte.d.ts +15 -0
  114. package/dist/layouts/FloatingDockLayout.svelte +56 -0
  115. package/dist/layouts/FloatingDockLayout.svelte.d.ts +13 -0
  116. package/dist/layouts/FloatingLayout.svelte +80 -0
  117. package/dist/layouts/FloatingLayout.svelte.d.ts +19 -0
  118. package/dist/layouts/FloatingLeftLayout.svelte +59 -0
  119. package/dist/layouts/FloatingLeftLayout.svelte.d.ts +15 -0
  120. package/dist/layouts/FloatingShell.svelte +80 -0
  121. package/dist/layouts/FloatingShell.svelte.d.ts +19 -0
  122. package/dist/layouts/FloatingTopLayout.svelte +68 -0
  123. package/dist/layouts/FloatingTopLayout.svelte.d.ts +15 -0
  124. package/dist/layouts/HybridLayout.svelte +20 -0
  125. package/dist/layouts/HybridLayout.svelte.d.ts +17 -0
  126. package/dist/layouts/IconRailLayout.svelte +75 -0
  127. package/dist/layouts/IconRailLayout.svelte.d.ts +15 -0
  128. package/dist/layouts/LeftBarLayout.svelte +19 -0
  129. package/dist/layouts/LeftBarLayout.svelte.d.ts +15 -0
  130. package/dist/layouts/RightBarLayout.svelte +21 -0
  131. package/dist/layouts/RightBarLayout.svelte.d.ts +15 -0
  132. package/dist/layouts/SideBar.svelte +86 -0
  133. package/dist/layouts/SideBar.svelte.d.ts +17 -0
  134. package/dist/layouts/SidebarLayout.svelte +11 -0
  135. package/dist/layouts/SidebarLayout.svelte.d.ts +15 -0
  136. package/dist/layouts/TopBar.svelte +90 -0
  137. package/dist/layouts/TopBar.svelte.d.ts +21 -0
  138. package/dist/layouts/TopBarLayout.svelte +26 -0
  139. package/dist/layouts/TopBarLayout.svelte.d.ts +15 -0
  140. package/dist/theme/theme.svelte.d.ts +11 -0
  141. package/dist/theme/theme.svelte.js +48 -0
  142. package/package.json +56 -4
@@ -0,0 +1,24 @@
1
+ <script>
2
+ // Spinner — an inline loading indicator. Sizes to the surrounding text
3
+ // by default (1em) and uses currentColor, so it works inside a button,
4
+ // next to text, or standalone. Not a full-screen overlay.
5
+ let {
6
+ size = undefined, // e.g. '1rem', '20px'; defaults to 1em (matches text)
7
+ label = 'Loading', // accessible label
8
+ ...restProps
9
+ } = $props();
10
+ </script>
11
+
12
+ <span
13
+ class="spinner"
14
+ role="status"
15
+ aria-label={label}
16
+ style:width={size}
17
+ style:height={size}
18
+ {...restProps}
19
+ >
20
+ <svg class="spinner-svg" viewBox="0 0 24 24" fill="none" aria-hidden="true">
21
+ <circle class="spinner-track" cx="12" cy="12" r="9" stroke-width="3" />
22
+ <path class="spinner-head" d="M21 12a9 9 0 0 0-9-9" stroke-width="3" stroke-linecap="round" />
23
+ </svg>
24
+ </span>
@@ -0,0 +1,13 @@
1
+ export default Spinner;
2
+ type Spinner = {
3
+ $on?(type: string, callback: (e: any) => void): () => void;
4
+ $set?(props: Partial<$$ComponentProps>): void;
5
+ };
6
+ declare const Spinner: import("svelte").Component<{
7
+ size?: any;
8
+ label?: string;
9
+ } & Record<string, any>, {}, "">;
10
+ type $$ComponentProps = {
11
+ size?: any;
12
+ label?: string;
13
+ } & Record<string, any>;
@@ -0,0 +1,100 @@
1
+ <script>
2
+ // Table — a data table with optional column sorting, custom cell
3
+ // rendering, and an empty state.
4
+ //
5
+ // columns: [{ key, label, sortable?, align?, width? }]
6
+ // rows: array of objects keyed by column.key
7
+ // cell: optional snippet(row, column) for custom cell content
8
+ // Sorting is client-side and non-destructive (does not mutate `rows`).
9
+
10
+ let {
11
+ columns = [],
12
+ rows = [],
13
+ cell, // snippet(row, column)
14
+ sortable = false, // enable sorting globally (per-column overrides)
15
+ emptyText = 'No data',
16
+ striped = false,
17
+ ...restProps
18
+ } = $props();
19
+
20
+ let sortKey = $state(null);
21
+ let sortDir = $state('asc'); // 'asc' | 'desc'
22
+
23
+ function canSort(col) {
24
+ return col.sortable ?? sortable;
25
+ }
26
+
27
+ function toggleSort(col) {
28
+ if (!canSort(col)) return;
29
+ if (sortKey === col.key) {
30
+ sortDir = sortDir === 'asc' ? 'desc' : 'asc';
31
+ } else {
32
+ sortKey = col.key;
33
+ sortDir = 'asc';
34
+ }
35
+ }
36
+
37
+ let sortedRows = $derived.by(() => {
38
+ if (!sortKey) return rows;
39
+ const copy = [...rows];
40
+ copy.sort((a, b) => {
41
+ const av = a[sortKey], bv = b[sortKey];
42
+ if (av == null) return 1;
43
+ if (bv == null) return -1;
44
+ let cmp;
45
+ if (typeof av === 'number' && typeof bv === 'number') cmp = av - bv;
46
+ else cmp = String(av).localeCompare(String(bv), undefined, { numeric: true });
47
+ return sortDir === 'asc' ? cmp : -cmp;
48
+ });
49
+ return copy;
50
+ });
51
+ </script>
52
+
53
+ <div class="table-wrapper" {...restProps}>
54
+ <table class="table" class:table-striped={striped}>
55
+ <thead>
56
+ <tr>
57
+ {#each columns as col}
58
+ <th
59
+ style:text-align={col.align ?? 'left'}
60
+ style:width={col.width}
61
+ class:table-th-sortable={canSort(col)}
62
+ aria-sort={sortKey === col.key ? (sortDir === 'asc' ? 'ascending' : 'descending') : undefined}
63
+ >
64
+ {#if canSort(col)}
65
+ <button type="button" class="table-sort-btn" onclick={() => toggleSort(col)}>
66
+ {col.label}
67
+ <span class="material-symbols-outlined table-sort-icon" class:active={sortKey === col.key}>
68
+ {sortKey === col.key ? (sortDir === 'asc' ? 'arrow_upward' : 'arrow_downward') : 'unfold_more'}
69
+ </span>
70
+ </button>
71
+ {:else}
72
+ {col.label}
73
+ {/if}
74
+ </th>
75
+ {/each}
76
+ </tr>
77
+ </thead>
78
+ <tbody>
79
+ {#if sortedRows.length === 0}
80
+ <tr>
81
+ <td class="table-empty" colspan={columns.length}>{emptyText}</td>
82
+ </tr>
83
+ {:else}
84
+ {#each sortedRows as row}
85
+ <tr>
86
+ {#each columns as col}
87
+ <td style:text-align={col.align ?? 'left'}>
88
+ {#if cell}
89
+ {@render cell(row, col)}
90
+ {:else}
91
+ {row[col.key]}
92
+ {/if}
93
+ </td>
94
+ {/each}
95
+ </tr>
96
+ {/each}
97
+ {/if}
98
+ </tbody>
99
+ </table>
100
+ </div>
@@ -0,0 +1,21 @@
1
+ export default Table;
2
+ type Table = {
3
+ $on?(type: string, callback: (e: any) => void): () => void;
4
+ $set?(props: Partial<$$ComponentProps>): void;
5
+ };
6
+ declare const Table: import("svelte").Component<{
7
+ columns?: any[];
8
+ rows?: any[];
9
+ cell: any;
10
+ sortable?: boolean;
11
+ emptyText?: string;
12
+ striped?: boolean;
13
+ } & Record<string, any>, {}, "">;
14
+ type $$ComponentProps = {
15
+ columns?: any[];
16
+ rows?: any[];
17
+ cell: any;
18
+ sortable?: boolean;
19
+ emptyText?: string;
20
+ striped?: boolean;
21
+ } & Record<string, any>;
@@ -0,0 +1,22 @@
1
+ <script>
2
+ import { theme } from '../theme/theme.svelte.js';
3
+
4
+ let {
5
+ class: className = '',
6
+ ...restProps
7
+ } = $props();
8
+ </script>
9
+
10
+ <button
11
+ class="btn btn-ghost btn-icon theme-toggle {className}"
12
+ onclick={() => theme.toggle()}
13
+ aria-label={theme.isDark ? 'Switch to light mode' : 'Switch to dark mode'}
14
+ title={theme.isDark ? 'Switch to light mode' : 'Switch to dark mode'}
15
+ {...restProps}
16
+ >
17
+ {#if theme.isDark}
18
+ <span class="material-symbols-outlined">light_mode</span>
19
+ {:else}
20
+ <span class="material-symbols-outlined">dark_mode</span>
21
+ {/if}
22
+ </button>
@@ -0,0 +1,11 @@
1
+ export default ThemeToggle;
2
+ type ThemeToggle = {
3
+ $on?(type: string, callback: (e: any) => void): () => void;
4
+ $set?(props: Partial<$$ComponentProps>): void;
5
+ };
6
+ declare const ThemeToggle: import("svelte").Component<{
7
+ class?: string;
8
+ } & Record<string, any>, {}, "">;
9
+ type $$ComponentProps = {
10
+ class?: string;
11
+ } & Record<string, any>;
@@ -0,0 +1,45 @@
1
+ <script>
2
+ // Tooltip — wraps a trigger and shows a small label on hover/focus.
3
+ // Pure CSS positioning (no floating-lib dependency); good for short hints.
4
+ //
5
+ // Usage:
6
+ // <Tooltip text="Delete" position="top">
7
+ // <button>…</button>
8
+ // </Tooltip>
9
+ let {
10
+ text,
11
+ position = 'top', // 'top' | 'bottom' | 'left' | 'right'
12
+ children,
13
+ ...restProps
14
+ } = $props();
15
+
16
+ let open = $state(false);
17
+ let id = `tt-${Math.random().toString(36).slice(2, 9)}`;
18
+
19
+ function show() { open = true; }
20
+ function hide() { open = false; }
21
+ </script>
22
+
23
+ <span
24
+ class="tooltip-wrap"
25
+ onmouseenter={show}
26
+ onmouseleave={hide}
27
+ onfocusin={show}
28
+ onfocusout={hide}
29
+ aria-describedby={open ? id : undefined}
30
+ {...restProps}
31
+ >
32
+ {@render children?.()}
33
+
34
+ {#if text}
35
+ <span
36
+ {id}
37
+ role="tooltip"
38
+ class="tooltip tooltip-{position}"
39
+ class:open
40
+ aria-hidden={!open}
41
+ >
42
+ {text}
43
+ </span>
44
+ {/if}
45
+ </span>
@@ -0,0 +1,15 @@
1
+ export default Tooltip;
2
+ type Tooltip = {
3
+ $on?(type: string, callback: (e: any) => void): () => void;
4
+ $set?(props: Partial<$$ComponentProps>): void;
5
+ };
6
+ declare const Tooltip: import("svelte").Component<{
7
+ text: any;
8
+ position?: string;
9
+ children: any;
10
+ } & Record<string, any>, {}, "">;
11
+ type $$ComponentProps = {
12
+ text: any;
13
+ position?: string;
14
+ children: any;
15
+ } & Record<string, any>;
@@ -0,0 +1,103 @@
1
+ /* base/root.css
2
+ Structural resets + element defaults.
3
+ Consumes tokens via var() but never defines them — token values
4
+ live in the overlay layer (overlay/default.css or a custom theme). */
5
+
6
+ *, *::before, *::after {
7
+ box-sizing: border-box;
8
+ }
9
+
10
+ html {
11
+ font-size: 16px;
12
+ height: 100%;
13
+ }
14
+
15
+ body {
16
+ font-family: var(--font-sans);
17
+ font-size: var(--text-base);
18
+ font-weight: 450;
19
+ line-height: var(--leading-normal);
20
+ color: var(--color-text);
21
+ background-color: var(--color-bg);
22
+ height: 100%;
23
+ margin: 0;
24
+ padding: 0;
25
+ -webkit-font-smoothing: antialiased;
26
+ }
27
+
28
+ h1, h2, h3, h4, h5, h6 {
29
+ font-weight: var(--font-semibold);
30
+ line-height: var(--leading-tight);
31
+ letter-spacing: var(--tracking-tight);
32
+ color: var(--color-text);
33
+ margin: 0;
34
+ }
35
+
36
+ h1 { font-size: var(--text-3xl); }
37
+ h2 { font-size: var(--text-2xl); }
38
+ h3 { font-size: var(--text-xl); }
39
+ h4 { font-size: var(--text-lg); }
40
+ h5 { font-size: var(--text-base); font-weight: var(--font-medium); }
41
+ h6 { font-size: var(--text-sm); font-weight: var(--font-medium); }
42
+
43
+ p {
44
+ line-height: var(--leading-normal);
45
+ margin: 0;
46
+ }
47
+
48
+ a {
49
+ color: var(--color-primary);
50
+ text-decoration: none;
51
+ transition: color var(--duration-fast) var(--ease-default);
52
+ }
53
+
54
+ a:hover {
55
+ color: var(--color-primary-hover);
56
+ }
57
+
58
+ small {
59
+ font-size: var(--text-sm);
60
+ color: var(--color-text-muted);
61
+ }
62
+
63
+ code, pre {
64
+ font-family: var(--font-mono);
65
+ font-size: var(--text-sm);
66
+ }
67
+
68
+ code {
69
+ background: var(--color-bg-subtle);
70
+ border: 1px solid var(--color-border);
71
+ border-radius: var(--radius-sm);
72
+ padding: 0 var(--space-1);
73
+ }
74
+
75
+ hr {
76
+ border: none;
77
+ border-top: 1px solid var(--color-border);
78
+ margin: var(--space-6) 0;
79
+ }
80
+
81
+ ul, ol {
82
+ padding-left: var(--space-6);
83
+ }
84
+
85
+ img, picture, video, canvas, svg {
86
+ display: block;
87
+ max-width: 100%;
88
+ }
89
+
90
+ input, button, textarea, select {
91
+ font: inherit;
92
+ }
93
+
94
+ /* Utility */
95
+ .text-muted { color: var(--color-text-muted); }
96
+ .text-subtle { color: var(--color-text-subtle); }
97
+ .text-sm { font-size: var(--text-sm); }
98
+ .text-xs { font-size: var(--text-xs); }
99
+ .text-lg { font-size: var(--text-lg); }
100
+ .text-bold { font-weight: var(--font-bold); }
101
+ .text-medium { font-weight: var(--font-medium); }
102
+ .text-right { text-align: right; }
103
+ .text-center { text-align: center; }
@@ -0,0 +1,47 @@
1
+ /* base.css — STRUCTURAL ENTRY POINT (no token values)
2
+ ──────────────────────────────────────────────────────────────
3
+ All structure: resets, layout, component anatomy. Every color /
4
+ size / shadow here is a var() reference. This file defines NO
5
+ token values — pair it with an overlay (overlay/default.css or a
6
+ generated theme.css) that supplies them.
7
+
8
+ Load order in a project:
9
+ 1. your overlay (theme.css) → defines the tokens
10
+ 2. base.css → consumes them
11
+ index.css below bundles the default overlay + this base together.
12
+ ────────────────────────────────────────────────────────────── */
13
+
14
+ /* Base */
15
+ @import './base/root.css';
16
+
17
+ /* Layout */
18
+ @import './layout/container.css';
19
+ @import './layout/grid.css';
20
+ @import './layout/shell.css';
21
+
22
+ /* Components */
23
+ @import './components/button.css';
24
+ @import './components/card.css';
25
+ @import './components/nav.css';
26
+ @import './components/sidebar.css';
27
+ @import './components/form.css';
28
+ @import './components/modal.css';
29
+ @import './components/accordion.css';
30
+ @import './components/login.css';
31
+ @import './components/badge.css';
32
+ @import './components/divider.css';
33
+ @import './components/table.css';
34
+ @import './components/alert.css';
35
+ @import './components/checkbox-radio.css';
36
+ @import './components/dropdown.css';
37
+ @import './components/spinner.css';
38
+ @import './components/tooltip.css';
39
+ @import './components/progress.css';
40
+ @import './components/pagination.css';
41
+ @import './components/calendar.css';
42
+ @import './components/topbar-layout.css';
43
+ @import './components/nestable.css';
44
+ @import './components/collapsible.css';
45
+
46
+ /* Icons */
47
+ @import './icons/icons.css';
@@ -0,0 +1,151 @@
1
+ /* components/accordion.css */
2
+
3
+ /* --- Container --- */
4
+
5
+ .accordion {
6
+ border: 1px solid var(--color-border);
7
+ border-radius: var(--radius-md);
8
+ overflow: hidden;
9
+ }
10
+
11
+ .accordion-flush { border: none; border-radius: 0; }
12
+
13
+
14
+ /* --- Item --- */
15
+
16
+ .accordion-item { border-bottom: 1px solid var(--color-border); }
17
+ .accordion-item:last-child { border-bottom: none; }
18
+
19
+
20
+ /* --- Trigger --- */
21
+
22
+ .accordion-trigger {
23
+ width: 100%;
24
+ display: flex;
25
+ align-items: center;
26
+ justify-content: space-between;
27
+ gap: var(--space-4);
28
+ padding: var(--space-4) var(--space-5);
29
+ background-color: var(--color-surface);
30
+ border: none;
31
+ cursor: pointer;
32
+ text-align: left;
33
+ font-family: var(--font-sans);
34
+ font-size: var(--text-sm);
35
+ font-weight: var(--font-medium);
36
+ color: var(--color-text);
37
+ transition: background-color var(--duration-fast) var(--ease-default);
38
+ user-select: none;
39
+ }
40
+
41
+ .accordion-trigger:hover { background-color: var(--color-bg-subtle); }
42
+
43
+ .accordion-trigger:focus-visible {
44
+ outline: 2px solid var(--color-primary);
45
+ outline-offset: -2px;
46
+ }
47
+
48
+ .accordion-item.open > .accordion-trigger {
49
+ background-color: var(--color-bg-subtle);
50
+ color: var(--color-primary);
51
+ }
52
+
53
+
54
+ /* --- Trigger content --- */
55
+
56
+ .accordion-trigger-content {
57
+ display: flex;
58
+ align-items: center;
59
+ gap: var(--space-3);
60
+ flex: 1;
61
+ min-width: 0;
62
+ }
63
+
64
+ .accordion-icon { color: var(--color-text-muted); font-size: 1.1rem; flex-shrink: 0; }
65
+ .accordion-item.open > .accordion-trigger .accordion-icon { color: var(--color-primary); }
66
+
67
+ .accordion-title { font-size: var(--text-sm); font-weight: var(--font-medium); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
68
+ .accordion-subtitle { font-size: var(--text-xs); color: var(--color-text-muted); font-weight: var(--font-normal); margin-top: var(--space-1); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
69
+
70
+
71
+ /* --- Chevron --- */
72
+
73
+ .accordion-chevron {
74
+ font-size: 1.1rem;
75
+ color: var(--color-text-subtle);
76
+ flex-shrink: 0;
77
+ transition: transform var(--duration-normal) var(--ease-default),
78
+ color var(--duration-fast) var(--ease-default);
79
+ }
80
+
81
+ .accordion-item.open > .accordion-trigger .accordion-chevron {
82
+ transform: rotate(180deg);
83
+ color: var(--color-primary);
84
+ }
85
+
86
+
87
+ /* --- Body --- */
88
+
89
+ .accordion-body {
90
+ overflow: hidden;
91
+ height: 0;
92
+ transition: height var(--duration-normal) var(--ease-default);
93
+ }
94
+
95
+ .accordion-body-inner {
96
+ padding: var(--space-4) var(--space-5);
97
+ padding-top: 0;
98
+ font-size: var(--text-sm);
99
+ color: var(--color-text-muted);
100
+ line-height: var(--leading-relaxed);
101
+ border-top: 1px solid var(--color-border);
102
+ }
103
+
104
+ .accordion-body-inner-padded { padding-top: var(--space-4); }
105
+
106
+
107
+ /* --- Badge --- */
108
+
109
+ .accordion-badge {
110
+ margin-left: auto;
111
+ background-color: var(--color-slate-100);
112
+ color: var(--color-text-muted);
113
+ font-size: var(--text-xs);
114
+ font-weight: var(--font-semibold);
115
+ padding: 0 var(--space-2);
116
+ border-radius: var(--radius-full);
117
+ flex-shrink: 0;
118
+ line-height: 1.6;
119
+ }
120
+
121
+ .accordion-item.open .accordion-badge {
122
+ background-color: var(--color-primary);
123
+ color: var(--color-primary-text);
124
+ }
125
+
126
+
127
+ /* --- Variants --- */
128
+
129
+ .accordion-separated {
130
+ border: none;
131
+ background: transparent;
132
+ display: flex;
133
+ flex-direction: column;
134
+ gap: var(--space-2);
135
+ }
136
+
137
+ .accordion-separated .accordion-item {
138
+ border: 1px solid var(--color-border);
139
+ border-radius: var(--radius-md);
140
+ overflow: hidden;
141
+ }
142
+
143
+ .accordion-separated .accordion-item.open {
144
+ border-color: var(--color-primary);
145
+ box-shadow: 0 0 0 3px rgb(37 99 235 / 0.08);
146
+ }
147
+
148
+ .accordion-minimal { border: none; }
149
+ .accordion-minimal .accordion-item { border-bottom: 1px solid var(--color-border); }
150
+ .accordion-minimal .accordion-trigger { padding-left: 0; padding-right: 0; }
151
+ .accordion-minimal .accordion-body-inner { padding-left: 0; padding-right: 0; }
@@ -0,0 +1,56 @@
1
+ /* components/alert.css */
2
+
3
+ .alert {
4
+ display: flex;
5
+ align-items: flex-start;
6
+ gap: var(--space-3);
7
+ padding: var(--space-4);
8
+ border-radius: var(--radius-md);
9
+ border: 1px solid transparent;
10
+ font-size: var(--text-sm);
11
+ }
12
+
13
+ .alert-icon {
14
+ flex-shrink: 0;
15
+ font-size: 1.1rem;
16
+ line-height: 1.5;
17
+ }
18
+
19
+ .alert-content { flex: 1; min-width: 0; }
20
+
21
+ .alert-title {
22
+ font-weight: var(--font-semibold);
23
+ margin-bottom: var(--space-1);
24
+ }
25
+
26
+ .alert-message {
27
+ color: inherit;
28
+ opacity: 0.85;
29
+ line-height: var(--leading-relaxed);
30
+ }
31
+
32
+ /* --- Variants --- */
33
+
34
+ .alert-info {
35
+ background-color: var(--color-info-bg);
36
+ border-color: var(--color-info);
37
+ color: var(--color-info);
38
+ }
39
+
40
+ .alert-success {
41
+ background-color: var(--color-success-bg);
42
+ border-color: var(--color-success);
43
+ color: var(--color-success);
44
+ }
45
+
46
+ .alert-warning {
47
+ background-color: var(--color-warning-bg);
48
+ border-color: var(--color-warning);
49
+ color: var(--color-warning);
50
+ }
51
+
52
+ .alert-error {
53
+ background-color: var(--color-error-bg);
54
+ border-color: var(--color-error);
55
+ color: var(--color-error);
56
+ }
@@ -0,0 +1,56 @@
1
+ /* components/badge.css */
2
+
3
+ .badge {
4
+ display: inline-flex;
5
+ align-items: center;
6
+ gap: var(--space-1);
7
+ padding: 0.125rem var(--space-2);
8
+ font-size: var(--text-xs);
9
+ font-weight: var(--font-semibold);
10
+ border-radius: var(--radius-full);
11
+ line-height: 1.6;
12
+ white-space: nowrap;
13
+ }
14
+
15
+ /* --- Variants --- */
16
+
17
+ .badge-default {
18
+ background-color: var(--color-slate-100);
19
+ color: var(--color-slate-600);
20
+ }
21
+
22
+ .badge-primary {
23
+ background-color: var(--color-primary);
24
+ color: white;
25
+ }
26
+
27
+ .badge-success {
28
+ background-color: var(--color-success-bg);
29
+ color: var(--color-success);
30
+ }
31
+
32
+ .badge-warning {
33
+ background-color: var(--color-warning-bg);
34
+ color: var(--color-warning);
35
+ }
36
+
37
+ .badge-error {
38
+ background-color: var(--color-error-bg);
39
+ color: var(--color-error);
40
+ }
41
+
42
+ .badge-info {
43
+ background-color: var(--color-info-bg);
44
+ color: var(--color-info);
45
+ }
46
+
47
+ /* Dot indicator */
48
+ .badge-dot::before {
49
+ content: '';
50
+ display: inline-block;
51
+ width: 0.4rem;
52
+ height: 0.4rem;
53
+ border-radius: var(--radius-full);
54
+ background-color: currentColor;
55
+ flex-shrink: 0;
56
+ }