@placeholderco/placeholder-ui 1.0.11 → 2.0.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 (289) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +134 -130
  3. package/dist/app.css +178 -0
  4. package/dist/bootstrap.min.css +3600 -0
  5. package/dist/cards/GitCard.svelte +115 -0
  6. package/dist/cards/GitCard.svelte.d.ts +22 -0
  7. package/dist/display/Avatar.svelte +29 -17
  8. package/dist/display/Avatar.svelte.d.ts +12 -2
  9. package/dist/display/LinkCollection.svelte +40 -18
  10. package/dist/display/LinkCollection.svelte.d.ts +9 -2
  11. package/dist/display/Paper.svelte +31 -19
  12. package/dist/display/Paper.svelte.d.ts +12 -3
  13. package/dist/display/alert/Alert.svelte +129 -0
  14. package/dist/display/alert/Alert.svelte.d.ts +15 -0
  15. package/dist/display/alert/AlertVariant.d.ts +1 -0
  16. package/dist/display/alert/AlertVariant.js +1 -0
  17. package/dist/display/filetree/FileTree.svelte +259 -0
  18. package/dist/display/filetree/FileTree.svelte.d.ts +76 -0
  19. package/dist/display/filetree/FileTreeItem.svelte +396 -0
  20. package/dist/display/filetree/FileTreeItem.svelte.d.ts +40 -0
  21. package/dist/display/filetree/FileTreeNode.d.ts +46 -0
  22. package/dist/display/filetree/FileTreeNode.js +115 -0
  23. package/dist/display/filetree/index.d.ts +5 -0
  24. package/dist/display/filetree/index.js +3 -0
  25. package/dist/editors/CodeMirror.svelte +306 -0
  26. package/dist/editors/CodeMirror.svelte.d.ts +31 -0
  27. package/dist/editors/tiptap/LinkActionMenu.svelte +307 -0
  28. package/dist/editors/tiptap/LinkActionMenu.svelte.d.ts +8 -0
  29. package/dist/editors/tiptap/TipTap.svelte +856 -0
  30. package/dist/editors/tiptap/TipTap.svelte.d.ts +54 -0
  31. package/dist/editors/tiptap/TipTapBubble.svelte +790 -0
  32. package/dist/editors/tiptap/TipTapBubble.svelte.d.ts +44 -0
  33. package/dist/editors/tiptap/collaboration.d.ts +55 -0
  34. package/dist/editors/tiptap/collaboration.js +1 -0
  35. package/dist/editors/tiptap/extensions/Alert.d.ts +18 -0
  36. package/dist/editors/tiptap/extensions/Alert.js +72 -0
  37. package/dist/editors/tiptap/extensions/CodeBlockEditor.d.ts +21 -0
  38. package/dist/editors/tiptap/extensions/CodeBlockEditor.js +326 -0
  39. package/dist/editors/tiptap/extensions/Div.d.ts +19 -0
  40. package/dist/editors/tiptap/extensions/Div.js +89 -0
  41. package/dist/editors/tiptap/extensions/Span.d.ts +5 -0
  42. package/dist/editors/tiptap/extensions/Span.js +56 -0
  43. package/dist/editors/tiptap/extensions/codeBlockEditor.css +236 -0
  44. package/dist/editors/tiptap/extensions/codeBlockLanguages.d.ts +17 -0
  45. package/dist/editors/tiptap/extensions/codeBlockLanguages.js +124 -0
  46. package/dist/editors/tiptap/extensions/index.d.ts +7 -0
  47. package/dist/editors/tiptap/extensions/index.js +5 -0
  48. package/dist/editors/tiptap/toolbar/AlertButton.svelte +261 -0
  49. package/dist/editors/tiptap/toolbar/AlertButton.svelte.d.ts +7 -0
  50. package/dist/editors/tiptap/toolbar/AlignCenterButton.svelte +18 -0
  51. package/dist/editors/tiptap/toolbar/AlignCenterButton.svelte.d.ts +7 -0
  52. package/dist/editors/tiptap/toolbar/AlignJustifyButton.svelte +18 -0
  53. package/dist/editors/tiptap/toolbar/AlignJustifyButton.svelte.d.ts +7 -0
  54. package/dist/editors/tiptap/toolbar/AlignLeftButton.svelte +18 -0
  55. package/dist/editors/tiptap/toolbar/AlignLeftButton.svelte.d.ts +7 -0
  56. package/dist/editors/tiptap/toolbar/AlignRightButton.svelte +18 -0
  57. package/dist/editors/tiptap/toolbar/AlignRightButton.svelte.d.ts +7 -0
  58. package/dist/editors/tiptap/toolbar/BoldButton.svelte +18 -0
  59. package/dist/editors/tiptap/toolbar/BoldButton.svelte.d.ts +7 -0
  60. package/dist/editors/tiptap/toolbar/BulletListButton.svelte +18 -0
  61. package/dist/editors/tiptap/toolbar/BulletListButton.svelte.d.ts +7 -0
  62. package/dist/editors/tiptap/toolbar/CodeBlockButton.svelte +18 -0
  63. package/dist/editors/tiptap/toolbar/CodeBlockButton.svelte.d.ts +7 -0
  64. package/dist/editors/tiptap/toolbar/CodeButton.svelte +18 -0
  65. package/dist/editors/tiptap/toolbar/CodeButton.svelte.d.ts +7 -0
  66. package/dist/editors/tiptap/toolbar/ColorButton.svelte +299 -0
  67. package/dist/editors/tiptap/toolbar/ColorButton.svelte.d.ts +20 -0
  68. package/dist/editors/tiptap/toolbar/DocumentButton.svelte +58 -0
  69. package/dist/editors/tiptap/toolbar/DocumentButton.svelte.d.ts +9 -0
  70. package/dist/editors/tiptap/toolbar/HeadingButton.svelte +30 -0
  71. package/dist/editors/tiptap/toolbar/HeadingButton.svelte.d.ts +8 -0
  72. package/dist/editors/tiptap/toolbar/HtmlButton.svelte +68 -0
  73. package/dist/editors/tiptap/toolbar/HtmlButton.svelte.d.ts +7 -0
  74. package/dist/editors/tiptap/toolbar/ImageButton.svelte +54 -0
  75. package/dist/editors/tiptap/toolbar/ImageButton.svelte.d.ts +8 -0
  76. package/dist/editors/tiptap/toolbar/ItalicButton.svelte +18 -0
  77. package/dist/editors/tiptap/toolbar/ItalicButton.svelte.d.ts +7 -0
  78. package/dist/editors/tiptap/toolbar/LinkButton.svelte +257 -0
  79. package/dist/editors/tiptap/toolbar/LinkButton.svelte.d.ts +7 -0
  80. package/dist/editors/tiptap/toolbar/OrderedListButton.svelte +18 -0
  81. package/dist/editors/tiptap/toolbar/OrderedListButton.svelte.d.ts +7 -0
  82. package/dist/editors/tiptap/toolbar/RedoButton.svelte +18 -0
  83. package/dist/editors/tiptap/toolbar/RedoButton.svelte.d.ts +7 -0
  84. package/dist/editors/tiptap/toolbar/StrikethroughButton.svelte +18 -0
  85. package/dist/editors/tiptap/toolbar/StrikethroughButton.svelte.d.ts +7 -0
  86. package/dist/editors/tiptap/toolbar/SubscriptButton.svelte +18 -0
  87. package/dist/editors/tiptap/toolbar/SubscriptButton.svelte.d.ts +7 -0
  88. package/dist/editors/tiptap/toolbar/SuperscriptButton.svelte +18 -0
  89. package/dist/editors/tiptap/toolbar/SuperscriptButton.svelte.d.ts +7 -0
  90. package/dist/editors/tiptap/toolbar/TableButton.svelte +258 -0
  91. package/dist/editors/tiptap/toolbar/TableButton.svelte.d.ts +7 -0
  92. package/dist/editors/tiptap/toolbar/ToolbarButton.svelte +84 -0
  93. package/dist/editors/tiptap/toolbar/ToolbarButton.svelte.d.ts +10 -0
  94. package/dist/editors/tiptap/toolbar/UnderlineButton.svelte +18 -0
  95. package/dist/editors/tiptap/toolbar/UnderlineButton.svelte.d.ts +7 -0
  96. package/dist/editors/tiptap/toolbar/UndoButton.svelte +18 -0
  97. package/dist/editors/tiptap/toolbar/UndoButton.svelte.d.ts +7 -0
  98. package/dist/form/Autocomplete.svelte +270 -137
  99. package/dist/form/Autocomplete.svelte.d.ts +58 -10
  100. package/dist/form/AutocompleteMulti.svelte +385 -227
  101. package/dist/form/AutocompleteMulti.svelte.d.ts +59 -10
  102. package/dist/form/Checkbox.svelte +124 -43
  103. package/dist/form/Checkbox.svelte.d.ts +26 -2
  104. package/dist/form/Chips.svelte +47 -17
  105. package/dist/form/Chips.svelte.d.ts +24 -3
  106. package/dist/form/ComboBox.svelte +30 -20
  107. package/dist/form/ComboBox.svelte.d.ts +1 -1
  108. package/dist/form/ComboBoxItemBuilder.svelte +161 -188
  109. package/dist/form/ComboBoxItemBuilder.svelte.d.ts +19 -2
  110. package/dist/form/ComboBoxMulti.svelte +38 -24
  111. package/dist/form/ComboBoxMulti.svelte.d.ts +1 -1
  112. package/dist/form/CronBuilder.svelte +84 -67
  113. package/dist/form/CronBuilder.svelte.d.ts +16 -3
  114. package/dist/form/DatePicker.svelte +177 -191
  115. package/dist/form/DatePicker.svelte.d.ts +17 -2
  116. package/dist/form/DateRangePicker.svelte +775 -0
  117. package/dist/form/DateRangePicker.svelte.d.ts +23 -0
  118. package/dist/form/DateTimePicker.svelte +168 -209
  119. package/dist/form/DateTimePicker.svelte.d.ts +10 -2
  120. package/dist/form/FormGroup.svelte +33 -10
  121. package/dist/form/FormGroup.svelte.d.ts +12 -2
  122. package/dist/form/Number.svelte +71 -29
  123. package/dist/form/Number.svelte.d.ts +39 -6
  124. package/dist/form/Radio.svelte +174 -0
  125. package/dist/form/Radio.svelte.d.ts +21 -0
  126. package/dist/form/RadioGroup.svelte +52 -138
  127. package/dist/form/RadioGroup.svelte.d.ts +19 -2
  128. package/dist/form/SegmentedControl.svelte +103 -57
  129. package/dist/form/SegmentedControl.svelte.d.ts +12 -2
  130. package/dist/form/Select.svelte +160 -229
  131. package/dist/form/Select.svelte.d.ts +35 -6
  132. package/dist/form/SelectMulti.svelte +166 -277
  133. package/dist/form/SelectMulti.svelte.d.ts +37 -6
  134. package/dist/form/Slider.svelte +185 -268
  135. package/dist/form/Slider.svelte.d.ts +33 -16
  136. package/dist/form/StringArrayBuilder.svelte +249 -0
  137. package/dist/form/StringArrayBuilder.svelte.d.ts +15 -0
  138. package/dist/form/Switch.svelte +164 -106
  139. package/dist/form/Switch.svelte.d.ts +22 -3
  140. package/dist/form/TextArea.svelte +80 -45
  141. package/dist/form/TextArea.svelte.d.ts +35 -10
  142. package/dist/form/Textbox.svelte +80 -47
  143. package/dist/form/Textbox.svelte.d.ts +41 -8
  144. package/dist/form/TimePicker.svelte +42 -47
  145. package/dist/form/TimePicker.svelte.d.ts +12 -2
  146. package/dist/form/comboBoxCore.svelte.d.ts +99 -0
  147. package/dist/form/comboBoxCore.svelte.js +243 -0
  148. package/dist/icon/Icon.svelte +8 -3
  149. package/dist/icon/Icon.svelte.d.ts +8 -3
  150. package/dist/icon/cube-send.svg +1 -0
  151. package/dist/icon/file-type-bmp.svg +1 -0
  152. package/dist/icon/file-type-csv.svg +1 -0
  153. package/dist/icon/file-type-doc.svg +1 -0
  154. package/dist/icon/file-type-docx.svg +1 -0
  155. package/dist/icon/file-type-jpg.svg +1 -0
  156. package/dist/icon/file-type-pdf.svg +1 -0
  157. package/dist/icon/file-type-png.svg +1 -0
  158. package/dist/icon/file-type-ppt.svg +1 -0
  159. package/dist/icon/file-type-svg.svg +1 -0
  160. package/dist/icon/file-type-txt.svg +1 -0
  161. package/dist/icon/file-type-xls.svg +1 -0
  162. package/dist/icon/file-type-zip.svg +1 -0
  163. package/dist/icon/index.d.ts +166 -145
  164. package/dist/icon/index.js +166 -146
  165. package/dist/icon/layout-sidebar-left-collapse.svg +1 -0
  166. package/dist/icon/layout-sidebar-left-expand.svg +1 -0
  167. package/dist/icon/logo-placeholder.svg +6 -0
  168. package/dist/icon/paperclip.svg +1 -0
  169. package/dist/icon/source-code.svg +1 -0
  170. package/dist/icon/sun-moon.svg +1 -0
  171. package/dist/icon/table.svg +6 -0
  172. package/dist/icon/thumb-down.svg +1 -0
  173. package/dist/icon/thumb-up.svg +1 -0
  174. package/dist/index.d.ts +93 -22
  175. package/dist/index.js +28 -27
  176. package/dist/layout/AppShell.svelte +12 -162
  177. package/dist/layout/AppShell.svelte.d.ts +6 -27
  178. package/dist/layout/CustomNavbar.svelte +9 -7
  179. package/dist/layout/CustomNavbar.svelte.d.ts +4 -2
  180. package/dist/layout/Navbar.svelte +158 -110
  181. package/dist/layout/Navbar.svelte.d.ts +26 -12
  182. package/dist/layout/NavbarItemDisplay.svelte +2 -2
  183. package/dist/layout/NavbarItemView.svelte +182 -0
  184. package/dist/layout/NavbarItemView.svelte.d.ts +10 -0
  185. package/dist/layout/Sidenav.svelte +280 -341
  186. package/dist/layout/Sidenav.svelte.d.ts +36 -4
  187. package/dist/models/ComboBoxItem.d.ts +2 -0
  188. package/dist/models/Employee.d.ts +53 -0
  189. package/dist/models/Employee.js +23 -0
  190. package/dist/models/Hyperlink.d.ts +3 -1
  191. package/dist/models/LinkCollectionItem.d.ts +3 -1
  192. package/dist/models/NavbarItem.d.ts +6 -2
  193. package/dist/theme.svelte.d.ts +0 -1
  194. package/dist/theme.svelte.js +46 -58
  195. package/dist/ui/Accordion.svelte +81 -242
  196. package/dist/ui/Accordion.svelte.d.ts +37 -14
  197. package/dist/ui/AccordionItem.svelte +303 -0
  198. package/dist/ui/AccordionItem.svelte.d.ts +21 -0
  199. package/dist/ui/ActionIcon.svelte +25 -21
  200. package/dist/ui/ActionIcon.svelte.d.ts +15 -2
  201. package/dist/ui/Badge.svelte +170 -161
  202. package/dist/ui/Badge.svelte.d.ts +16 -4
  203. package/dist/ui/Button.svelte +178 -205
  204. package/dist/ui/Button.svelte.d.ts +19 -2
  205. package/dist/ui/ButtonVariant.d.ts +15 -1
  206. package/dist/ui/ContextMenu.svelte +146 -0
  207. package/dist/ui/ContextMenu.svelte.d.ts +37 -0
  208. package/dist/ui/ContextMenuList.svelte +188 -0
  209. package/dist/ui/ContextMenuList.svelte.d.ts +12 -0
  210. package/dist/ui/Dialog.svelte +183 -104
  211. package/dist/ui/Dialog.svelte.d.ts +21 -2
  212. package/dist/ui/Drawer.svelte +237 -184
  213. package/dist/ui/Drawer.svelte.d.ts +20 -2
  214. package/dist/ui/Dropdown.svelte +24 -14
  215. package/dist/ui/Dropdown.svelte.d.ts +11 -2
  216. package/dist/ui/Dropzone.svelte +159 -57
  217. package/dist/ui/Dropzone.svelte.d.ts +29 -2
  218. package/dist/ui/Link.svelte +12 -4
  219. package/dist/ui/Link.svelte.d.ts +8 -2
  220. package/dist/ui/Loader.svelte +23 -18
  221. package/dist/ui/Loader.svelte.d.ts +5 -2
  222. package/dist/ui/Logo.svelte +37 -0
  223. package/dist/ui/Logo.svelte.d.ts +16 -0
  224. package/dist/ui/MultiSortable.svelte +287 -0
  225. package/dist/ui/MultiSortable.svelte.d.ts +50 -0
  226. package/dist/ui/Pagination.svelte +12 -6
  227. package/dist/ui/Pagination.svelte.d.ts +6 -2
  228. package/dist/ui/Popover.svelte +43 -65
  229. package/dist/ui/Popover.svelte.d.ts +14 -5
  230. package/dist/ui/ProgressBar.svelte +169 -0
  231. package/dist/ui/ProgressBar.svelte.d.ts +30 -0
  232. package/dist/ui/ProgressBarVariant.d.ts +7 -0
  233. package/dist/ui/ProgressBarVariant.js +1 -0
  234. package/dist/ui/SegmentedControl.svelte +0 -0
  235. package/dist/ui/SegmentedControl.svelte.d.ts +26 -0
  236. package/dist/ui/Sortable.svelte +163 -0
  237. package/dist/ui/Sortable.svelte.d.ts +47 -0
  238. package/dist/ui/Table.svelte +497 -56
  239. package/dist/ui/Table.svelte.d.ts +64 -2
  240. package/dist/ui/Tabs.svelte +22 -18
  241. package/dist/ui/Tabs.svelte.d.ts +6 -2
  242. package/dist/ui/ThemeSwitcher.svelte +26 -7
  243. package/dist/ui/ThemeSwitcher.svelte.d.ts +4 -2
  244. package/dist/ui/Tooltip.svelte +312 -180
  245. package/dist/ui/Tooltip.svelte.d.ts +4 -3
  246. package/dist/uiTheme.svelte.d.ts +86 -0
  247. package/dist/uiTheme.svelte.js +214 -0
  248. package/dist/util/DateFunctions.js +1 -1
  249. package/dist/util/DragDrop.d.ts +50 -0
  250. package/dist/util/DragDrop.js +154 -0
  251. package/dist/util/NavigateTo.js +2 -2
  252. package/dist/util/dayjs.d.ts +4 -0
  253. package/dist/util/dayjs.js +15 -0
  254. package/dist/util/interceptLinkClick.d.ts +13 -0
  255. package/dist/util/interceptLinkClick.js +33 -0
  256. package/package.json +66 -26
  257. package/dist/display/Alert.svelte +0 -179
  258. package/dist/display/Alert.svelte.d.ts +0 -13
  259. package/dist/form/FileInput.svelte +0 -235
  260. package/dist/form/FileInput.svelte.d.ts +0 -23
  261. package/dist/form/PasswordInput.svelte +0 -252
  262. package/dist/form/PasswordInput.svelte.d.ts +0 -33
  263. package/dist/form/Rating.svelte +0 -235
  264. package/dist/form/Rating.svelte.d.ts +0 -21
  265. package/dist/styles/components.css +0 -199
  266. package/dist/styles/dark.css +0 -146
  267. package/dist/styles/index.css +0 -116
  268. package/dist/styles/reset.css +0 -110
  269. package/dist/styles/semantic.css +0 -86
  270. package/dist/styles/tokens.css +0 -203
  271. package/dist/styles/utilities.css +0 -523
  272. package/dist/ui/Breadcrumbs.svelte +0 -131
  273. package/dist/ui/Breadcrumbs.svelte.d.ts +0 -16
  274. package/dist/ui/LoadingOverlay.svelte +0 -53
  275. package/dist/ui/LoadingOverlay.svelte.d.ts +0 -11
  276. package/dist/ui/Progress.svelte +0 -191
  277. package/dist/ui/Progress.svelte.d.ts +0 -15
  278. package/dist/ui/RingProgress.svelte +0 -141
  279. package/dist/ui/RingProgress.svelte.d.ts +0 -18
  280. package/dist/ui/Skeleton.svelte +0 -85
  281. package/dist/ui/Skeleton.svelte.d.ts +0 -12
  282. package/dist/ui/Stepper.svelte +0 -355
  283. package/dist/ui/Stepper.svelte.d.ts +0 -24
  284. package/dist/ui/Timeline.svelte +0 -225
  285. package/dist/ui/Timeline.svelte.d.ts +0 -23
  286. /package/dist/{actions → util}/ClickOutside.d.ts +0 -0
  287. /package/dist/{actions → util}/ClickOutside.js +0 -0
  288. /package/dist/{transitions → util}/Transitions.d.ts +0 -0
  289. /package/dist/{transitions → util}/Transitions.js +0 -0
@@ -1,91 +1,82 @@
1
1
  <script lang="ts">
2
- import type { LinkNavbarItem } from '../models/NavbarItem.js';
3
- import type { SidenavSection } from './Sidenav.svelte';
4
- import { Link, ThemeSwitcher, ActionIcon, Drawer, iconHamburger, type Hyperlink } from '../index.js';
5
- import { themeState } from '../theme.svelte.js';
2
+ import type { NavbarItem } from '../models/NavbarItem.js';
3
+ import {
4
+ ThemeSwitcher,
5
+ ActionIcon,
6
+ iconHamburger,
7
+ type Hyperlink,
8
+ viewportState
9
+ } from '../index.js';
10
+ import NavbarItemView from './NavbarItemView.svelte';
11
+ import Link from '../ui/Link.svelte';
12
+ import Logo from '../ui/Logo.svelte';
6
13
  import type { Snippet } from 'svelte';
7
14
 
8
- interface Props {
9
- drawerHeader?: string | undefined;
15
+ /** `midnight` is a legacy alias for `primary`. */
16
+ export type NavbarVariant = 'default' | 'primary' | 'midnight';
17
+
18
+ export interface NavbarProps {
19
+ /** Visual variant. `primary` uses the primary brand colour as the background across all themes */
20
+ variant?: NavbarVariant;
21
+ /** App navigation link displayed as a header */
10
22
  appNav?: Hyperlink;
11
- items?: LinkNavbarItem[];
12
- secondaryItems?: LinkNavbarItem[];
23
+ /** Primary navigation items. Items with `subItems` fold out a vertical sub-list; items with `iconSvg` show a leading icon */
24
+ items?: NavbarItem[];
25
+ /** Secondary navigation items (right side) */
26
+ secondaryItems?: NavbarItem[];
27
+ /** Hide the logo */
28
+ noLogo?: boolean;
29
+ /** Custom URL for the logo link */
30
+ logoHref?: string;
31
+ /** Additional CSS classes */
13
32
  class?: string;
33
+ /** Constrain navbar width to container */
14
34
  inContainer?: boolean;
35
+ /** Custom content for the left section */
36
+ leftSection?: Snippet;
37
+ /** Custom content for the middle section */
15
38
  middleSection?: Snippet;
39
+ /** Custom content for the right section */
16
40
  rightSection?: Snippet;
17
- /** Icons displayed to the left of the ThemeSwitcher, visible even when collapsed on mobile */
18
- iconSection?: Snippet;
19
- /** Enable responsive collapse to burger menu on small screens (default: true) */
20
- responsive?: boolean;
21
- /** Breakpoint in pixels at which the navbar collapses (default: 768) */
22
- responsiveBreakpoint?: number;
23
- // Drawer button options
41
+ /** Show mobile drawer toggle button */
24
42
  showDrawerButton?: boolean;
43
+ /** Position of the drawer toggle button */
25
44
  drawerButtonPosition?: 'left' | 'right';
45
+ /** Custom icon for the drawer toggle button */
26
46
  drawerButtonIcon?: string;
47
+ /** Callback when drawer toggle is clicked */
27
48
  onDrawerButtonClick?: () => void;
28
49
  }
29
50
 
30
51
  let {
31
- drawerHeader = undefined,
52
+ variant = 'default',
32
53
  appNav = undefined,
33
54
  items = [],
34
55
  secondaryItems = [],
56
+ noLogo = false,
57
+ logoHref = undefined,
35
58
  class: className = '',
36
59
  inContainer = false,
60
+ leftSection = undefined,
37
61
  middleSection = undefined,
38
62
  rightSection = undefined,
39
- iconSection = undefined,
40
- responsive = true,
41
- responsiveBreakpoint = 768,
42
63
  // Drawer button options
43
64
  showDrawerButton = false,
44
65
  drawerButtonPosition = 'right',
45
66
  drawerButtonIcon = iconHamburger,
46
67
  onDrawerButtonClick = undefined
47
- }: Props = $props();
48
-
49
- let drawerOpen = $state(false);
50
- let windowWidth = $state(typeof window !== 'undefined' ? window.innerWidth : 1024);
51
- const isCollapsed = $derived(responsive && windowWidth <= responsiveBreakpoint);
52
-
53
- const drawerSections = $derived.by((): SidenavSection[] => {
54
- const sections: SidenavSection[] = [];
55
- if (items.length > 0) {
56
- sections.push({
57
- items: items.map((item) => ({
58
- label: item.label,
59
- href: item.href,
60
- iconSvg: item.iconSvg
61
- }))
62
- });
63
- }
64
- if (secondaryItems.length > 0) {
65
- sections.push({
66
- items: secondaryItems.map((item) => ({
67
- label: item.label,
68
- href: item.href,
69
- iconSvg: item.iconSvg
70
- }))
71
- });
72
- }
73
- return sections;
74
- });
68
+ }: NavbarProps = $props();
75
69
 
76
- function handleBurgerClick() {
77
- drawerOpen = true;
78
- }
70
+ const isPrimary = $derived(variant === 'primary' || variant === 'midnight');
79
71
  </script>
80
72
 
81
- <svelte:window onresize={() => (windowWidth = window.innerWidth)} />
82
-
83
- <header>
73
+ <header class={isPrimary ? 'primary' : ''}>
84
74
  <div class="inner-navbar {className} {inContainer ? 'container' : ''}">
75
+ {@render leftSection?.()}
85
76
  {#if showDrawerButton && drawerButtonPosition === 'left'}
86
77
  <ActionIcon
87
78
  svg={drawerButtonIcon}
88
- variant="secondary-subtle"
79
+ variant={isPrimary ? 'accent-subtle' : 'secondary-subtle'}
89
80
  size="1.25rem"
90
81
  onclick={onDrawerButtonClick}
91
82
  class="drawer-btn drawer-btn-left"
@@ -97,49 +88,52 @@
97
88
  </div>
98
89
  {/if}
99
90
 
100
- {#if !isCollapsed}
91
+ {#if items.length > 0}
101
92
  <div class="primary links-container">
102
93
  {#each items as item}
103
- <Link href={item.href}>{item.label}</Link>
94
+ <NavbarItemView {item} />
104
95
  {/each}
105
96
  </div>
106
97
  {/if}
107
98
 
108
- <div class="middle">
109
- {@render middleSection?.()}
110
- </div>
111
-
112
- {#if !isCollapsed}
99
+ {#if middleSection}
100
+ <div class="middle">
101
+ {@render middleSection()}
102
+ </div>
103
+ {/if}
104
+ <!-- <ActionIcon
105
+ class="hamburger"
106
+ variant={$isDarkMode ? 'auto-subtle' : 'primary'}
107
+ onclick={toggleDrawer}
108
+ svg={iconHamburger}
109
+ /> -->
110
+ {#if secondaryItems.length > 0}
113
111
  <div class="secondary links-container">
114
112
  {#each secondaryItems as item}
115
- {#if item.href.indexOf('/') === 0}
116
- <Link href={item.href}>{item.label}</Link>
117
- {:else}
118
- <a href={item.href}>{item.label}</a>
119
- {/if}
113
+ <NavbarItemView {item} />
120
114
  {/each}
121
115
  </div>
122
- {@render rightSection?.()}
123
116
  {/if}
124
- {#if iconSection}
125
- <div class="icon-section">
126
- {@render iconSection()}
117
+ {#if rightSection}
118
+ <div class="right">
119
+ {@render rightSection()}
127
120
  </div>
128
121
  {/if}
129
- <ThemeSwitcher darkVariant="secondary-subtle" lightVariant="primary-subtle" />
130
- {#if isCollapsed}
131
- <ActionIcon
132
- svg={iconHamburger}
133
- variant={themeState.isDarkMode ? 'secondary-subtle' : 'primary-subtle'}
134
- size="1.25rem"
135
- onclick={handleBurgerClick}
136
- class="responsive-burger"
137
- />
122
+ <ThemeSwitcher
123
+ darkVariant="accent-subtle"
124
+ lightVariant={isPrimary ? 'accent-subtle' : 'primary-subtle'}
125
+ />
126
+ {#if !viewportState.isMobile && !noLogo}
127
+ {#if logoHref}
128
+ <Logo href={logoHref} fill={isPrimary ? 'white' : undefined} />
129
+ {:else}
130
+ <Logo fill={isPrimary ? 'white' : undefined} />
131
+ {/if}
138
132
  {/if}
139
133
  {#if showDrawerButton && drawerButtonPosition === 'right'}
140
134
  <ActionIcon
141
135
  svg={drawerButtonIcon}
142
- variant="secondary-subtle"
136
+ variant={isPrimary ? 'accent-subtle' : 'secondary-subtle'}
143
137
  size="1.25rem"
144
138
  onclick={onDrawerButtonClick}
145
139
  class="drawer-btn drawer-btn-right"
@@ -148,55 +142,116 @@
148
142
  </div>
149
143
  </header>
150
144
 
151
- {#if responsive}
152
- <Drawer
153
- bind:open={drawerOpen}
154
- title={drawerHeader ?? appNav?.text ?? ''}
155
- sections={drawerSections}
156
- closeForLargeScreens={true}
157
- largeScreenBreakpoint={responsiveBreakpoint}
158
- />
159
- {/if}
160
-
161
145
  <style>
162
146
  header {
163
147
  position: sticky;
164
148
  top: 0;
165
- z-index: var(--pui-z-sticky);
166
- height: 46px;
149
+ z-index: 40;
150
+ height: var(--header-height);
167
151
  display: flex;
168
- background: var(--pui-color-white);
169
- border-bottom: 1px solid var(--pui-border-default);
152
+ background: white;
153
+ border-bottom: 0.666667px solid rgb(222, 226, 230);
170
154
  }
171
155
 
172
156
  .links-container {
173
157
  display: flex;
174
- gap: var(--pui-spacing-4);
158
+ gap: 1rem;
175
159
  }
176
160
 
177
161
  :global(.dark) header {
178
- background: var(--pui-color-black);
162
+ background: black;
163
+ border: none;
164
+ }
165
+
166
+ /* Primary variant: primary brand background regardless of theme */
167
+ header.primary,
168
+ :global(.dark) header.primary {
169
+ background: var(--ui-primary);
179
170
  border: none;
180
171
  }
181
172
 
173
+ header.primary .inner-navbar {
174
+ color: white;
175
+ }
176
+
177
+ /* Top-level links/triggers: white, turning accent on hover (matches dark navbar).
178
+ Use `>` so these rules don't leak into the fold-out sub-list panels, which keep
179
+ their own (paper) colour scheme regardless of the primary variant. */
180
+ header.primary .inner-navbar .links-container > :global(a),
181
+ header.primary
182
+ .inner-navbar
183
+ .links-container
184
+ > :global(.navbar-parent)
185
+ > :global(.navbar-parent-trigger),
186
+ header.primary .inner-navbar .header-hero :global(a) {
187
+ color: white;
188
+ transition: color 200ms;
189
+ }
190
+
191
+ header.primary .inner-navbar .links-container > :global(a:hover),
192
+ header.primary
193
+ .inner-navbar
194
+ .links-container
195
+ > :global(.navbar-parent)
196
+ > :global(.navbar-parent-trigger:hover),
197
+ header.primary .inner-navbar .header-hero :global(a:hover) {
198
+ color: var(--ui-accent);
199
+ }
200
+
182
201
  .inner-navbar {
183
202
  display: flex;
184
203
  align-items: center;
185
- gap: var(--pui-spacing-4);
204
+ gap: 1rem;
186
205
 
187
206
  margin: 0 auto;
188
- padding: 0 var(--pui-spacing-4);
207
+ padding: 0 1em;
189
208
  height: 100%;
190
209
  width: 100%;
191
- color: var(--pui-color-primary);
210
+ color: var(--ui-primary);
192
211
  }
193
212
 
194
213
  .middle {
195
214
  flex-grow: 1;
196
215
  }
197
216
 
198
- .inner-navbar :global(.responsive-burger) {
199
- flex-shrink: 0;
217
+ /* Without a growing .middle, the first right-side element pushes the group to the
218
+ edge via auto margin. When .middle is present its flex-grow consumes the free
219
+ space first, so these margins resolve to 0 and have no effect. */
220
+ .secondary,
221
+ .right,
222
+ .inner-navbar > :global(.theme-switcher) {
223
+ margin-left: auto;
224
+ }
225
+
226
+ .secondary ~ .right,
227
+ .secondary ~ :global(.theme-switcher),
228
+ .right ~ :global(.theme-switcher) {
229
+ margin-left: 0;
230
+ }
231
+
232
+ .hidden-when-small {
233
+ display: none;
234
+ }
235
+
236
+ .inner-navbar :global(.hamburger) {
237
+ margin-left: auto;
238
+ }
239
+
240
+ @media (max-width: 640px) {
241
+ .hidden-when-small {
242
+ display: block;
243
+ }
244
+
245
+ .inner-navbar :global(.hamburger) {
246
+ display: none;
247
+ }
248
+ }
249
+
250
+ .top-header {
251
+ border-bottom-width: 1px;
252
+ border-bottom-style: solid;
253
+ border-color: var(--border-color);
254
+ height: 1.5rem;
200
255
  }
201
256
 
202
257
  .inner-navbar :global(.cu-icon) {
@@ -208,17 +263,10 @@
208
263
  }
209
264
 
210
265
  .inner-navbar :global(.drawer-btn-left) {
211
- margin-right: var(--pui-spacing-1);
266
+ margin-right: 0.25rem;
212
267
  }
213
268
 
214
269
  .inner-navbar :global(.drawer-btn-right) {
215
- margin-left: var(--pui-spacing-2);
216
- }
217
-
218
- .icon-section {
219
- display: flex;
220
- align-items: center;
221
- gap: var(--pui-spacing-1);
222
- flex-shrink: 0;
270
+ margin-left: 0.5rem;
223
271
  }
224
272
  </style>
@@ -1,26 +1,40 @@
1
- import type { LinkNavbarItem } from '../models/NavbarItem.js';
1
+ import type { NavbarItem } from '../models/NavbarItem.js';
2
2
  import { type Hyperlink } from '../index.js';
3
3
  import type { Snippet } from 'svelte';
4
- interface Props {
5
- drawerHeader?: string | undefined;
4
+ /** `midnight` is a legacy alias for `primary`. */
5
+ export type NavbarVariant = 'default' | 'primary' | 'midnight';
6
+ export interface NavbarProps {
7
+ /** Visual variant. `primary` uses the primary brand colour as the background across all themes */
8
+ variant?: NavbarVariant;
9
+ /** App navigation link displayed as a header */
6
10
  appNav?: Hyperlink;
7
- items?: LinkNavbarItem[];
8
- secondaryItems?: LinkNavbarItem[];
11
+ /** Primary navigation items. Items with `subItems` fold out a vertical sub-list; items with `iconSvg` show a leading icon */
12
+ items?: NavbarItem[];
13
+ /** Secondary navigation items (right side) */
14
+ secondaryItems?: NavbarItem[];
15
+ /** Hide the logo */
16
+ noLogo?: boolean;
17
+ /** Custom URL for the logo link */
18
+ logoHref?: string;
19
+ /** Additional CSS classes */
9
20
  class?: string;
21
+ /** Constrain navbar width to container */
10
22
  inContainer?: boolean;
23
+ /** Custom content for the left section */
24
+ leftSection?: Snippet;
25
+ /** Custom content for the middle section */
11
26
  middleSection?: Snippet;
27
+ /** Custom content for the right section */
12
28
  rightSection?: Snippet;
13
- /** Icons displayed to the left of the ThemeSwitcher, visible even when collapsed on mobile */
14
- iconSection?: Snippet;
15
- /** Enable responsive collapse to burger menu on small screens (default: true) */
16
- responsive?: boolean;
17
- /** Breakpoint in pixels at which the navbar collapses (default: 768) */
18
- responsiveBreakpoint?: number;
29
+ /** Show mobile drawer toggle button */
19
30
  showDrawerButton?: boolean;
31
+ /** Position of the drawer toggle button */
20
32
  drawerButtonPosition?: 'left' | 'right';
33
+ /** Custom icon for the drawer toggle button */
21
34
  drawerButtonIcon?: string;
35
+ /** Callback when drawer toggle is clicked */
22
36
  onDrawerButtonClick?: () => void;
23
37
  }
24
- declare const Navbar: import("svelte").Component<Props, {}, "">;
38
+ declare const Navbar: import("svelte").Component<NavbarProps, {}, "">;
25
39
  type Navbar = ReturnType<typeof Navbar>;
26
40
  export default Navbar;
@@ -1,6 +1,6 @@
1
1
  <!-- <script lang="ts">
2
- import Icon from '../icon/Icon.svelte';
3
- import Link from '../ui/Link.svelte';
2
+ import Icon from "../icon/Icon.svelte";
3
+ import Link from "../ui/Link.svelte";
4
4
  import type { NavbarItem } from "../models/NavbarItem.js";
5
5
 
6
6
  export let item: NavbarItem;
@@ -0,0 +1,182 @@
1
+ <script lang="ts">
2
+ import type { NavbarItem } from '../models/NavbarItem.js';
3
+ import Link from '../ui/Link.svelte';
4
+ import Icon from '../icon/Icon.svelte';
5
+ import { iconChevronDown, iconChevronRight } from '../icon/index.js';
6
+ import { clickOutside } from '../util/ClickOutside.js';
7
+ // Self-import enables recursive rendering of nested sub-lists (Svelte 5 replacement for svelte:self)
8
+ import Self from './NavbarItemView.svelte';
9
+
10
+ export interface NavbarItemViewProps {
11
+ /** The navigation item to render */
12
+ item: NavbarItem;
13
+ /** Nesting depth. 0 = top level (sub-list folds down), >0 = nested (flies out to the side) */
14
+ depth?: number;
15
+ }
16
+
17
+ let { item, depth = 0 }: NavbarItemViewProps = $props();
18
+
19
+ let open = $state(false);
20
+
21
+ const close = () => (open = false);
22
+ </script>
23
+
24
+ {#if 'component' in item}
25
+ {@const Component = item.component}
26
+ <Component {...item.componentProps} />
27
+ {:else if 'href' in item}
28
+ <Link href={item.href} onclick={item.onclick} class="navbar-item {item.class ?? ''}">
29
+ {#if item.iconSvg}
30
+ <Icon svg={item.iconSvg} size="1.1em" class="navbar-item-icon" />
31
+ {/if}
32
+ <span>{item.label}</span>
33
+ </Link>
34
+ {:else}
35
+ <div class="navbar-parent" use:clickOutside={close}>
36
+ <button
37
+ type="button"
38
+ class="navbar-item navbar-parent-trigger {item.class ?? ''}"
39
+ aria-expanded={open}
40
+ aria-haspopup="true"
41
+ onclick={(e) => {
42
+ item.onclick?.(e);
43
+ open = !open;
44
+ }}
45
+ >
46
+ {#if item.iconSvg}
47
+ <Icon svg={item.iconSvg} size="1.1em" class="navbar-item-icon" />
48
+ {/if}
49
+ <span>{item.label}</span>
50
+ {#if item.subItems?.length}
51
+ <Icon
52
+ svg={depth > 0 ? iconChevronRight : iconChevronDown}
53
+ size="0.85em"
54
+ class="navbar-chevron"
55
+ />
56
+ {/if}
57
+ </button>
58
+ {#if open && item.subItems?.length}
59
+ <!-- svelte-ignore a11y_click_events_have_key_events -->
60
+ <!-- svelte-ignore a11y_no_static_element_interactions -->
61
+ <div
62
+ class="navbar-submenu"
63
+ class:flyout={depth > 0}
64
+ style={item.submenuWidth ? `width: ${item.submenuWidth}; min-width: ${item.submenuWidth};` : ''}
65
+ onclick={(e) => {
66
+ // Close the fold-out once an actual link is chosen (but not when toggling a nested parent)
67
+ if ((e.target as HTMLElement).closest('a')) close();
68
+ }}
69
+ >
70
+ {#each item.subItems as subItem}
71
+ <Self item={subItem} depth={depth + 1} />
72
+ {/each}
73
+ </div>
74
+ {/if}
75
+ </div>
76
+ {/if}
77
+
78
+ <style>
79
+ .navbar-parent {
80
+ position: relative;
81
+ display: inline-flex;
82
+ }
83
+
84
+ /* Shared look for links and parent triggers so they line up in the navbar row */
85
+ :global(.navbar-item) {
86
+ display: inline-flex;
87
+ align-items: center;
88
+ gap: 0.4rem;
89
+ }
90
+
91
+ /* Match the global `header a` link styling so triggers and links look identical.
92
+ A <button> doesn't inherit those rules, so set the colours explicitly. */
93
+ .navbar-parent-trigger {
94
+ background: none;
95
+ border: none;
96
+ padding: 0;
97
+ margin: 0;
98
+ font: inherit;
99
+ color: var(--ui-primary);
100
+ cursor: pointer;
101
+ transition: color 200ms;
102
+ }
103
+
104
+ .navbar-parent-trigger:hover {
105
+ color: var(--ui-accent-dark);
106
+ }
107
+
108
+ :global(.dark) .navbar-parent-trigger {
109
+ color: white;
110
+ }
111
+
112
+ :global(.dark) .navbar-parent-trigger:hover {
113
+ color: var(--ui-accent);
114
+ }
115
+
116
+ :global(.navbar-item-icon) {
117
+ flex-shrink: 0;
118
+ }
119
+
120
+ :global(.navbar-chevron) {
121
+ flex-shrink: 0;
122
+ opacity: 0.7;
123
+ }
124
+
125
+ /* Fold-out vertical sub-list */
126
+ .navbar-submenu {
127
+ position: absolute;
128
+ top: 100%;
129
+ left: 0;
130
+ margin-top: 0.5rem;
131
+ display: flex;
132
+ flex-direction: column;
133
+ gap: 0.125rem;
134
+ min-width: 12rem;
135
+ background-color: var(--paper-body-bg);
136
+ border: 1px solid var(--border-color);
137
+ border-radius: 0.375rem;
138
+ box-shadow: 0 8px 16px rgba(0, 0, 0, 0.2);
139
+ z-index: 1000;
140
+ }
141
+
142
+ /* Nested sub-lists fly out to the side instead of downward */
143
+ .navbar-submenu.flyout {
144
+ top: 0;
145
+ left: 100%;
146
+ margin-top: 0;
147
+ margin-left: 0.25rem;
148
+ }
149
+
150
+ /* Items inside the panel always use the panel's own colour scheme,
151
+ regardless of the navbar variant (matches the Dropdown component). */
152
+ .navbar-submenu :global(.navbar-item) {
153
+ width: 100%;
154
+ padding: 0.4rem 0.6rem;
155
+ color: var(--ui-primary);
156
+ text-decoration: none;
157
+ transition: background-color 0.15s ease;
158
+ }
159
+
160
+ .navbar-submenu :global(.navbar-item:first-child) {
161
+ border-top-left-radius: 0.25rem;
162
+ border-top-right-radius: 0.25rem;
163
+ }
164
+
165
+ .navbar-submenu :global(.navbar-item:last-child) {
166
+ border-bottom-left-radius: 0.25rem;
167
+ border-bottom-right-radius: 0.25rem;
168
+ }
169
+
170
+ .navbar-submenu :global(.navbar-item:hover) {
171
+ background-color: var(--border-color);
172
+ color: var(--ui-primary);
173
+ }
174
+
175
+ :global(.dark) .navbar-submenu :global(.navbar-item) {
176
+ color: var(--ui-accent);
177
+ }
178
+
179
+ :global(.dark) .navbar-submenu :global(.navbar-item:hover) {
180
+ color: var(--ui-accent);
181
+ }
182
+ </style>
@@ -0,0 +1,10 @@
1
+ import type { NavbarItem } from '../models/NavbarItem.js';
2
+ export interface NavbarItemViewProps {
3
+ /** The navigation item to render */
4
+ item: NavbarItem;
5
+ /** Nesting depth. 0 = top level (sub-list folds down), >0 = nested (flies out to the side) */
6
+ depth?: number;
7
+ }
8
+ declare const NavbarItemView: import("svelte").Component<NavbarItemViewProps, {}, "">;
9
+ type NavbarItemView = ReturnType<typeof NavbarItemView>;
10
+ export default NavbarItemView;