fluentui-svelte 0.5.0 → 0.7.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 (259) hide show
  1. package/dist/components/app-surface/app-surface.svelte +96 -0
  2. package/dist/components/app-surface/app-surface.svelte.d.ts +22 -0
  3. package/dist/components/app-surface/docs/llms.md +73 -0
  4. package/dist/components/app-surface/types.d.ts +19 -0
  5. package/dist/components/app-surface/types.js +1 -0
  6. package/dist/components/app-window/app-window.d.ts +3 -0
  7. package/dist/components/app-window/app-window.js +3 -0
  8. package/dist/components/app-window/app-window.svelte +193 -0
  9. package/dist/components/app-window/app-window.svelte.d.ts +25 -0
  10. package/dist/components/app-window/docs/llms.md +119 -0
  11. package/dist/components/app-window/types.d.ts +66 -0
  12. package/dist/components/app-window/types.js +1 -0
  13. package/dist/components/auto-suggest-box/auto-suggest-box.svelte +47 -31
  14. package/dist/components/auto-suggest-box/auto-suggest-box.svelte.d.ts +2 -2
  15. package/dist/components/auto-suggest-box/docs/llms.md +34 -33
  16. package/dist/components/auto-suggest-box/option.svelte +6 -4
  17. package/dist/components/auto-suggest-box/types.d.ts +13 -16
  18. package/dist/components/avatar/avatar.svelte +4 -3
  19. package/dist/components/avatar/docs/llms.md +1 -1
  20. package/dist/components/avatar/type.d.ts +1 -1
  21. package/dist/components/badge/badge-icon.svelte +2 -2
  22. package/dist/components/badge/badge.svelte +2 -2
  23. package/dist/components/badge/docs/llms.md +2 -2
  24. package/dist/components/badge/types.d.ts +2 -2
  25. package/dist/components/breadcrumb/breadcrumb-button.svelte +2 -2
  26. package/dist/components/breadcrumb/breadcrumb-divider.svelte +2 -2
  27. package/dist/components/breadcrumb/breadcrumb-item.svelte +2 -2
  28. package/dist/components/breadcrumb/breadcrumb.svelte +10 -5
  29. package/dist/components/breadcrumb/docs/llms.md +11 -11
  30. package/dist/components/breadcrumb/types.d.ts +7 -7
  31. package/dist/components/button/button.svelte +2 -2
  32. package/dist/components/button/docs/llms.md +17 -17
  33. package/dist/components/button/split-button.svelte +7 -7
  34. package/dist/components/button/types.d.ts +5 -5
  35. package/dist/components/calendar-date-picker/calendar-date-picker.svelte +98 -10
  36. package/dist/components/calendar-date-picker/calendar-date-picker.svelte.d.ts +1 -1
  37. package/dist/components/calendar-date-picker/docs/llms.md +19 -14
  38. package/dist/components/calendar-date-picker/types.d.ts +22 -8
  39. package/dist/components/calendar-view/calendar-view-days.svelte +3 -2
  40. package/dist/components/calendar-view/calendar-view-grid.js +8 -3
  41. package/dist/components/calendar-view/calendar-view-item.svelte +10 -4
  42. package/dist/components/calendar-view/calendar-view-months.svelte +3 -2
  43. package/dist/components/calendar-view/calendar-view-years.svelte +3 -2
  44. package/dist/components/calendar-view/calendar-view.svelte +11 -4
  45. package/dist/components/calendar-view/calendar-view.svelte.js +5 -0
  46. package/dist/components/calendar-view/docs/llms.md +20 -19
  47. package/dist/components/calendar-view/types.d.ts +6 -1
  48. package/dist/components/card/card-footer.svelte +2 -2
  49. package/dist/components/card/card-header.svelte +5 -4
  50. package/dist/components/card/card-preview.svelte +13 -2
  51. package/dist/components/card/card.svelte +5 -5
  52. package/dist/components/card/docs/llms.md +22 -21
  53. package/dist/components/card/types.d.ts +8 -4
  54. package/dist/components/checkbox/checkbox.svelte +47 -26
  55. package/dist/components/checkbox/checkbox.svelte.d.ts +3 -24
  56. package/dist/components/checkbox/docs/llms.md +24 -23
  57. package/dist/components/checkbox/types.d.ts +10 -23
  58. package/dist/components/date-picker/date-picker.svelte +98 -27
  59. package/dist/components/date-picker/date-picker.svelte.d.ts +1 -1
  60. package/dist/components/date-picker/docs/llms.md +23 -20
  61. package/dist/components/date-picker/types.d.ts +24 -15
  62. package/dist/components/dialog/dialog-actions.svelte +17 -2
  63. package/dist/components/dialog/dialog-content.svelte +2 -2
  64. package/dist/components/dialog/dialog-content.svelte.d.ts +1 -1
  65. package/dist/components/dialog/dialog-surface.svelte +130 -8
  66. package/dist/components/dialog/dialog-title.svelte +23 -6
  67. package/dist/components/dialog/dialog-trigger.svelte +8 -2
  68. package/dist/components/dialog/dialog-trigger.svelte.d.ts +1 -1
  69. package/dist/components/dialog/dialog.svelte +22 -11
  70. package/dist/components/dialog/docs/llms.md +56 -19
  71. package/dist/components/dialog/types.d.ts +31 -9
  72. package/dist/components/dialog/utils.d.ts +2 -0
  73. package/dist/components/dialog/utils.js +1 -0
  74. package/dist/components/divider/divider.svelte +6 -4
  75. package/dist/components/divider/types.d.ts +1 -1
  76. package/dist/components/dropdown/docs/llms.md +30 -28
  77. package/dist/components/dropdown/dropdown-option.svelte +17 -5
  78. package/dist/components/dropdown/dropdown.svelte +182 -84
  79. package/dist/components/dropdown/dropdown.svelte.d.ts +1 -1
  80. package/dist/components/dropdown/types.d.ts +26 -20
  81. package/dist/components/dropdown-select/docs/llms.md +24 -22
  82. package/dist/components/dropdown-select/dropdown-select-option.svelte +2 -2
  83. package/dist/components/dropdown-select/dropdown-select.svelte +42 -7
  84. package/dist/components/dropdown-select/types.d.ts +4 -4
  85. package/dist/components/expander/docs/llms.md +3 -3
  86. package/dist/components/expander/expander.svelte +13 -8
  87. package/dist/components/expander/types.d.ts +5 -5
  88. package/dist/components/flyout/docs/llms.md +1 -1
  89. package/dist/components/flyout/flyout.svelte +17 -6
  90. package/dist/components/flyout/types.d.ts +1 -1
  91. package/dist/components/hyperlink/docs/llms.md +6 -6
  92. package/dist/components/hyperlink/hyperlink.svelte +13 -4
  93. package/dist/components/hyperlink/types.d.ts +1 -1
  94. package/dist/components/info-bar/docs/llms.md +11 -10
  95. package/dist/components/info-bar/info-bar.svelte +3 -2
  96. package/dist/components/info-bar/types.d.ts +4 -0
  97. package/dist/components/label/docs/llms.md +75 -22
  98. package/dist/components/label/label-context.d.ts +14 -0
  99. package/dist/components/label/label-context.js +10 -0
  100. package/dist/components/label/label.svelte +153 -30
  101. package/dist/components/label/label.svelte.d.ts +1 -1
  102. package/dist/components/label/types.d.ts +48 -4
  103. package/dist/components/list-view/docs/llms.md +103 -33
  104. package/dist/components/list-view/list-view-item-branch.svelte +257 -0
  105. package/dist/components/list-view/list-view-item-branch.svelte.d.ts +4 -0
  106. package/dist/components/list-view/list-view-item.svelte +164 -46
  107. package/dist/components/list-view/list-view-item.svelte.d.ts +5 -5
  108. package/dist/components/list-view/list-view.svelte +73 -25
  109. package/dist/components/list-view/types.d.ts +71 -8
  110. package/dist/components/list-view/utils.d.ts +10 -0
  111. package/dist/components/list-view/utils.js +17 -1
  112. package/dist/components/menu/docs/llms.md +98 -15
  113. package/dist/components/menu/menu-command-bar-item.svelte +61 -0
  114. package/dist/components/menu/menu-command-bar-item.svelte.d.ts +14 -0
  115. package/dist/components/menu/menu-command-bar.svelte +218 -0
  116. package/dist/components/menu/menu-command-bar.svelte.d.ts +21 -0
  117. package/dist/components/menu/menu-group.svelte +6 -3
  118. package/dist/components/menu/menu-item-checkbox.svelte +5 -4
  119. package/dist/components/menu/menu-item-radio.svelte +5 -4
  120. package/dist/components/menu/menu-item-switch.svelte +5 -4
  121. package/dist/components/menu/menu-item.svelte +5 -5
  122. package/dist/components/menu/menu-item.svelte.d.ts +2 -3
  123. package/dist/components/menu/menu-list.svelte +10 -1
  124. package/dist/components/menu/menu-popover.svelte +9 -5
  125. package/dist/components/menu/menu-trigger.svelte +2 -1
  126. package/dist/components/menu/menu.svelte.js +1 -0
  127. package/dist/components/menu/types.d.ts +62 -7
  128. package/dist/components/number-box/docs/llms.md +6 -4
  129. package/dist/components/number-box/number-box.svelte +35 -29
  130. package/dist/components/number-box/number-box.svelte.d.ts +1 -1
  131. package/dist/components/number-box/types.d.ts +1 -1
  132. package/dist/components/persona/docs/llms.md +29 -25
  133. package/dist/components/persona/persona.svelte +8 -6
  134. package/dist/components/persona/types.d.ts +4 -3
  135. package/dist/components/progress-bar/docs/llms.md +13 -13
  136. package/dist/components/progress-bar/progress-bar.svelte +6 -6
  137. package/dist/components/progress-bar/types.d.ts +4 -4
  138. package/dist/components/progress-ring/docs/llms.md +14 -14
  139. package/dist/components/progress-ring/progress-ring.svelte +5 -5
  140. package/dist/components/progress-ring/types.d.ts +3 -3
  141. package/dist/components/radio-button/docs/llms.md +11 -8
  142. package/dist/components/radio-button/radio-button.svelte +38 -12
  143. package/dist/components/radio-button/radio-button.svelte.d.ts +1 -1
  144. package/dist/components/radio-button/types.d.ts +11 -8
  145. package/dist/components/rating/docs/llms.md +111 -0
  146. package/dist/components/rating/rating.svelte +247 -0
  147. package/dist/components/rating/rating.svelte.d.ts +19 -0
  148. package/dist/components/rating/types.d.ts +44 -0
  149. package/dist/components/rating/types.js +1 -0
  150. package/dist/components/side-nav/docs/llms.md +110 -0
  151. package/dist/components/side-nav/side-nav-branch.svelte +43 -0
  152. package/dist/components/side-nav/side-nav-branch.svelte.d.ts +4 -0
  153. package/dist/components/side-nav/side-nav-item.svelte +75 -0
  154. package/dist/components/side-nav/side-nav-item.svelte.d.ts +25 -0
  155. package/dist/components/side-nav/side-nav-list.svelte +32 -0
  156. package/dist/components/side-nav/side-nav-list.svelte.d.ts +7 -0
  157. package/dist/components/side-nav/side-nav.d.ts +2 -0
  158. package/dist/components/side-nav/side-nav.js +2 -0
  159. package/dist/components/side-nav/side-nav.svelte +355 -0
  160. package/dist/components/side-nav/side-nav.svelte.d.ts +24 -0
  161. package/dist/components/side-nav/types.d.ts +149 -0
  162. package/dist/components/side-nav/types.js +1 -0
  163. package/dist/components/skeleton/docs/llms.md +1 -1
  164. package/dist/components/skeleton/skeleton.svelte +2 -2
  165. package/dist/components/skeleton/types.d.ts +1 -1
  166. package/dist/components/slider/docs/llms.md +31 -28
  167. package/dist/components/slider/slider.svelte +126 -61
  168. package/dist/components/slider/slider.svelte.d.ts +1 -3
  169. package/dist/components/slider/types.d.ts +21 -14
  170. package/dist/components/tab-view/docs/llms.md +7 -7
  171. package/dist/components/tab-view/tab-view-tab.svelte +16 -14
  172. package/dist/components/tab-view/tab-view.svelte +16 -9
  173. package/dist/components/tab-view/types.d.ts +6 -6
  174. package/dist/components/table/docs/llms.md +38 -33
  175. package/dist/components/table/table-body.svelte +2 -2
  176. package/dist/components/table/table-cell-actions.svelte +8 -2
  177. package/dist/components/table/table-cell-layout.svelte +2 -2
  178. package/dist/components/table/table-cell.svelte +2 -2
  179. package/dist/components/table/table-header-cell.svelte +2 -2
  180. package/dist/components/table/table-header.svelte +2 -2
  181. package/dist/components/table/table-row.svelte +2 -2
  182. package/dist/components/table/table-selection-cell.svelte +6 -6
  183. package/dist/components/table/table.svelte +2 -2
  184. package/dist/components/table/types.d.ts +11 -11
  185. package/dist/components/tag/docs/llms.md +383 -0
  186. package/dist/components/tag/tag-group.d.ts +2 -0
  187. package/dist/components/tag/tag-group.js +2 -0
  188. package/dist/components/tag/tag-group.svelte +117 -0
  189. package/dist/components/tag/tag-group.svelte.d.ts +20 -0
  190. package/dist/components/tag/tag.svelte +459 -0
  191. package/dist/components/tag/tag.svelte.d.ts +19 -0
  192. package/dist/components/tag/types.d.ts +137 -0
  193. package/dist/components/tag/types.js +1 -0
  194. package/dist/components/tag-picker/docs/llms.md +298 -0
  195. package/dist/components/tag-picker/option-group.svelte +51 -0
  196. package/dist/components/tag-picker/option-group.svelte.d.ts +4 -0
  197. package/dist/components/tag-picker/option.svelte +82 -0
  198. package/dist/components/tag-picker/option.svelte.d.ts +4 -0
  199. package/dist/components/tag-picker/tag-picker.d.ts +2 -0
  200. package/dist/components/tag-picker/tag-picker.js +2 -0
  201. package/dist/components/tag-picker/tag-picker.svelte +716 -0
  202. package/dist/components/tag-picker/tag-picker.svelte.d.ts +21 -0
  203. package/dist/components/tag-picker/types.d.ts +142 -0
  204. package/dist/components/tag-picker/types.js +1 -0
  205. package/dist/components/text-box/docs/llms.md +31 -4
  206. package/dist/components/text-box/text-box-button.svelte +3 -3
  207. package/dist/components/text-box/text-box-button.svelte.d.ts +1 -1
  208. package/dist/components/text-box/text-box.svelte +41 -14
  209. package/dist/components/text-box/types.d.ts +5 -5
  210. package/dist/components/textarea/docs/llms.md +4 -3
  211. package/dist/components/textarea/textarea.svelte +14 -6
  212. package/dist/components/textarea/types.d.ts +2 -4
  213. package/dist/components/time-picker/docs/llms.md +18 -15
  214. package/dist/components/time-picker/time-picker.svelte +133 -33
  215. package/dist/components/time-picker/time-picker.svelte.d.ts +1 -1
  216. package/dist/components/time-picker/types.d.ts +23 -13
  217. package/dist/components/title-bar/docs/llms.md +382 -0
  218. package/dist/components/title-bar/title-bar-left-controls.svelte +215 -0
  219. package/dist/components/title-bar/title-bar-left-controls.svelte.d.ts +22 -0
  220. package/dist/components/title-bar/title-bar-right-controls.svelte +190 -0
  221. package/dist/components/title-bar/title-bar-right-controls.svelte.d.ts +27 -0
  222. package/dist/components/title-bar/title-bar.d.ts +3 -0
  223. package/dist/components/title-bar/title-bar.js +4 -0
  224. package/dist/components/title-bar/title-bar.svelte +224 -0
  225. package/dist/components/title-bar/title-bar.svelte.d.ts +26 -0
  226. package/dist/components/title-bar/types.d.ts +165 -0
  227. package/dist/components/title-bar/types.js +1 -0
  228. package/dist/components/toggle-switch/docs/llms.md +11 -9
  229. package/dist/components/toggle-switch/toggle-switch.svelte +23 -14
  230. package/dist/components/toggle-switch/toggle-switch.svelte.d.ts +1 -1
  231. package/dist/components/toggle-switch/types.d.ts +12 -10
  232. package/dist/components/tooltip/docs/llms.md +1 -1
  233. package/dist/components/tooltip/tooltip.svelte +5 -4
  234. package/dist/components/tooltip/types.d.ts +1 -1
  235. package/dist/components/top-nav/docs/llms.md +1 -1
  236. package/dist/components/top-nav/top-nav-item.svelte +2 -2
  237. package/dist/components/top-nav/top-nav.svelte +2 -2
  238. package/dist/components/top-nav/types.d.ts +2 -2
  239. package/dist/components/tree-view/docs/llms.md +11 -11
  240. package/dist/components/tree-view/tree-view-item-content.svelte +3 -3
  241. package/dist/components/tree-view/tree-view-item.svelte +13 -5
  242. package/dist/components/tree-view/tree-view.svelte +20 -5
  243. package/dist/components/tree-view/tree-view.svelte.d.ts +1 -1
  244. package/dist/components/tree-view/tree-view.svelte.js +31 -3
  245. package/dist/components/tree-view/types.d.ts +7 -3
  246. package/dist/index.d.ts +25 -0
  247. package/dist/index.js +32 -0
  248. package/dist/internal/components/dynamic-carousel/dynamic-carousel.svelte +26 -5
  249. package/dist/internal/components/dynamic-carousel/dynamic-carousel.svelte.d.ts +2 -0
  250. package/dist/internal/constants.d.ts +0 -4
  251. package/dist/internal/constants.js +0 -4002
  252. package/dist/internal/index.d.ts +1 -0
  253. package/dist/internal/index.js +1 -0
  254. package/dist/internal/native-field.svelte.d.ts +44 -0
  255. package/dist/internal/native-field.svelte.js +85 -0
  256. package/dist/internal/utils.d.ts +16 -2
  257. package/dist/internal/utils.js +25 -3
  258. package/dist/types/index.d.ts +3 -3
  259. package/package.json +51 -37
@@ -1,28 +1,29 @@
1
- <script lang="ts" generics="T extends 'div' | 'label' = 'label'">
1
+ <script lang="ts">
2
+ import { claimLabel } from '../label/label-context.js';
2
3
  import CheckmarkFilled from 'fluentui-icons-svelte/CheckmarkFilled.svelte';
3
4
  import SubtractFilled from 'fluentui-icons-svelte/SubtractFilled.svelte';
4
5
  import { PREFIX } from '../../internal/constants.js';
5
6
  import type { CheckboxProps } from './types.js';
6
- import type { PolymorphicProps } from '../../types/index.js';
7
7
 
8
8
  const FALLBACK_ID = $props.id();
9
9
  const COMPONENT_NAME = 'checkbox';
10
10
  const ID = `${PREFIX}${COMPONENT_NAME}-${FALLBACK_ID}`;
11
11
 
12
+ const labelContext = claimLabel(() => id);
13
+
12
14
  let {
13
- ref = $bindable(),
14
- wrapperRef = $bindable(),
15
- checked = $bindable(),
16
- indeterminate = $bindable(),
17
- id = ID,
15
+ ref = $bindable(null),
16
+ wrapperRef = $bindable(null),
17
+ checked = $bindable(null),
18
+ indeterminate = $bindable(null),
19
+ id = labelContext?.fieldId ?? ID,
18
20
  name = id,
19
21
  'aria-hidden': ariaHidden,
20
22
  disabled,
21
- wrapperAs = 'label' as T,
22
23
  wrapperAttributes,
23
24
  children,
24
25
  ...attributes
25
- }: CheckboxProps<T> = $props();
26
+ }: CheckboxProps = $props();
26
27
  </script>
27
28
 
28
29
  <!--
@@ -38,17 +39,13 @@
38
39
  import { Checkbox } from 'fluentui-svelte';
39
40
  </script>
40
41
 
41
- <Checkbox label="Checkbox label" />
42
+ <Checkbox>Checkbox label</Checkbox>
42
43
  ```
43
44
  -->
44
45
 
45
- <svelte:element
46
- this={wrapperAs}
47
- bind:this={wrapperRef}
48
- {...wrapperAttributes as PolymorphicProps<T>}
49
- class={['fs-checkbox', wrapperAttributes?.class, wrapperAs === 'label' && 'label-wrapper']}
50
- >
46
+ <div {...wrapperAttributes} class={['fs-checkbox', wrapperAttributes?.class]} bind:this={wrapperRef}>
51
47
  <input
48
+ {...attributes}
52
49
  {id}
53
50
  {name}
54
51
  {disabled}
@@ -56,15 +53,18 @@
56
53
  aria-hidden={ariaHidden}
57
54
  bind:checked
58
55
  bind:this={ref}
59
- {indeterminate}
60
- {...attributes}
56
+ bind:indeterminate
57
+ data-indeterminate={indeterminate || undefined}
61
58
  />
62
59
  <div style="pointer-events: none;" aria-hidden="true">
63
60
  <SubtractFilled class="indeterminate" />
64
61
  <CheckmarkFilled class="checked" />
65
62
  </div>
66
- {@render children?.()}
67
- </svelte:element>
63
+ <!-- Inside a Label, the Label names the field instead. -->
64
+ {#if children && !labelContext}
65
+ <label for={id}>{@render children()}</label>
66
+ {/if}
67
+ </div>
68
68
 
69
69
  <style>
70
70
  .fs-checkbox {
@@ -74,11 +74,10 @@
74
74
  outline: none;
75
75
  cursor: pointer;
76
76
  position: relative;
77
- gap: 0.75rem;
78
77
  &:has(input:focus-visible) {
79
78
  outline: 0.125rem var(--fs-focus-stroke-outer) solid;
80
79
  outline-offset: 0.125rem;
81
- &.label-wrapper {
80
+ &:has(> label) {
82
81
  border-radius: 0.063rem;
83
82
  outline-offset: 0.313rem;
84
83
  }
@@ -90,21 +89,27 @@
90
89
  background-color: var(--fs-control-alt-fill-quaternary);
91
90
  border-color: var(--fs-control-strong-disabled);
92
91
  }
92
+ & > label {
93
+ padding-inline-start: 0.75rem;
94
+ cursor: inherit;
95
+ }
93
96
  & input {
94
97
  position: absolute;
95
98
  inset: 0;
99
+ width: 1.25rem;
100
+ margin: 0;
96
101
  border: unset;
97
102
  outline: 0 !important;
98
103
  opacity: 0;
99
104
  appearance: none;
100
105
  -webkit-appearance: none;
101
106
  -moz-appearance: none;
102
- &:indeterminate + div :global(svg.indeterminate),
107
+ &:is(:indeterminate, [data-indeterminate]) + div :global(svg.indeterminate),
103
108
  &:checked + div :global(svg.checked) {
104
109
  mask-size: 100% 100%;
105
110
  transition: var(--fs-slower-duration, 1s) cubic-bezier(0.55, 0, 0, 1) mask-size;
106
111
  }
107
- &:is(:checked, :indeterminate) {
112
+ &:is(:checked, :indeterminate, [data-indeterminate]) {
108
113
  & + div {
109
114
  background-color: var(--fs-accent-fill-default);
110
115
  border-color: var(--fs-accent-fill-default);
@@ -130,7 +135,21 @@
130
135
  &:checked + div :global(svg.checked) {
131
136
  width: 1rem;
132
137
  }
133
- &:indeterminate + div :global(svg.indeterminate) {
138
+ &:is(:user-invalid, [aria-invalid='true']) {
139
+ & + div {
140
+ border-color: var(--fs-system-critical);
141
+ color: var(--fs-system-critical) !important;
142
+ & + label {
143
+ color: var(--fs-system-critical);
144
+ }
145
+ }
146
+ &:hover {
147
+ & + div {
148
+ border-color: var(--fs-system-critical);
149
+ }
150
+ }
151
+ }
152
+ &:is(:indeterminate, [data-indeterminate]) + div :global(svg.indeterminate) {
134
153
  width: 0.8rem;
135
154
  }
136
155
  }
@@ -146,11 +165,13 @@
146
165
  justify-content: center;
147
166
  & :global(svg) {
148
167
  width: 0;
149
- fill: var(--fs-text-on-accent-primary);
150
168
  transform-origin: 80% 20%;
151
169
  mask-image: linear-gradient(black, black);
152
170
  mask-repeat: no-repeat;
153
171
  mask-size: 0% 100%;
172
+ & :global(path) {
173
+ fill: var(--fs-text-on-accent-primary);
174
+ }
154
175
  }
155
176
  }
156
177
  &:has(input:disabled) {
@@ -1,25 +1,4 @@
1
1
  import type { CheckboxProps } from './types.ts';
2
- declare function $$render<T extends 'div' | 'label' = 'label'>(): {
3
- props: CheckboxProps<T>;
4
- exports: {};
5
- bindings: "ref" | "checked" | "indeterminate" | "wrapperRef";
6
- slots: {};
7
- events: {};
8
- };
9
- declare class __sveltets_Render<T extends 'div' | 'label' = 'label'> {
10
- props(): ReturnType<typeof $$render<T>>['props'];
11
- events(): ReturnType<typeof $$render<T>>['events'];
12
- slots(): ReturnType<typeof $$render<T>>['slots'];
13
- bindings(): "ref" | "checked" | "indeterminate" | "wrapperRef";
14
- exports(): {};
15
- }
16
- interface $$IsomorphicComponent {
17
- new <T extends 'div' | 'label' = 'label'>(options: import('svelte').ComponentConstructorOptions<ReturnType<__sveltets_Render<T>['props']>>): import('svelte').SvelteComponent<ReturnType<__sveltets_Render<T>['props']>, ReturnType<__sveltets_Render<T>['events']>, ReturnType<__sveltets_Render<T>['slots']>> & {
18
- $$bindings?: ReturnType<__sveltets_Render<T>['bindings']>;
19
- } & ReturnType<__sveltets_Render<T>['exports']>;
20
- <T extends 'div' | 'label' = 'label'>(internal: unknown, props: ReturnType<__sveltets_Render<T>['props']> & {}): ReturnType<__sveltets_Render<T>['exports']>;
21
- z_$$bindings?: ReturnType<__sveltets_Render<any>['bindings']>;
22
- }
23
2
  /**
24
3
  * The Fluent UI Checkbox is a customizable input element that allows users to select one or more options from a set.
25
4
  * It is designed to be consistent with the Fluent Design System.
@@ -32,9 +11,9 @@ interface $$IsomorphicComponent {
32
11
  * import { Checkbox } from 'fluentui-svelte';
33
12
  * </script>
34
13
  *
35
- * <Checkbox label="Checkbox label" />
14
+ * <Checkbox>Checkbox label</Checkbox>
36
15
  * ```
37
16
  */
38
- declare const Checkbox: $$IsomorphicComponent;
39
- type Checkbox<T extends 'div' | 'label' = 'label'> = InstanceType<typeof Checkbox<T>>;
17
+ declare const Checkbox: import("svelte").Component<CheckboxProps, {}, "ref" | "checked" | "indeterminate" | "wrapperRef">;
18
+ type Checkbox = ReturnType<typeof Checkbox>;
40
19
  export default Checkbox;
@@ -9,7 +9,7 @@ Represents a control that a user can select (check) or clear (uncheck). A CheckB
9
9
  import { Checkbox } from 'fluentui-svelte';
10
10
  </script>
11
11
 
12
- <Checkbox wrapperAs="label">Default</Checkbox>
12
+ <Checkbox>Default</Checkbox>
13
13
  ```
14
14
 
15
15
  ## Component API
@@ -20,12 +20,12 @@ A brief explanation of the props that really need explaining. You can see the re
20
20
 
21
21
  ### Label
22
22
 
23
- To display a visible label, set `wrapperAs="label"` and pass the label text as children. The wrapper then renders as a `<label>` element that wraps the input.
23
+ Pass the label text as children. The root is a `<div>` and the text renders in a separate `<label>` associated with the checkbox through `for` and `id`. Inside a `Label`, it is not rendered: the Label names the checkbox.
24
24
 
25
25
  ```svelte
26
26
  <Checkbox />
27
- <Checkbox wrapperAs="label">FluentUI Checkbox</Checkbox>
28
- <Checkbox wrapperAs="label">Another Checkbox</Checkbox>
27
+ <Checkbox>FluentUI Checkbox</Checkbox>
28
+ <Checkbox>Another Checkbox</Checkbox>
29
29
  ```
30
30
 
31
31
  ### Checked
@@ -33,8 +33,8 @@ To display a visible label, set `wrapperAs="label"` and pass the label text as c
33
33
  The `checked` prop determines whether the checkbox is checked or not. It accepts a boolean value.
34
34
 
35
35
  ```svelte
36
- <Checkbox wrapperAs="label">Unchecked</Checkbox>
37
- <Checkbox wrapperAs="label" checked>Checked</Checkbox>
36
+ <Checkbox>Unchecked</Checkbox>
37
+ <Checkbox checked>Checked</Checkbox>
38
38
  ```
39
39
 
40
40
  ### Indeterminate
@@ -42,7 +42,7 @@ The `checked` prop determines whether the checkbox is checked or not. It accepts
42
42
  The `indeterminate` prop sets the checkbox to an indeterminate state, which is useful for representing a mixed selection.
43
43
 
44
44
  ```svelte
45
- <Checkbox wrapperAs="label" indeterminate>Indeterminate</Checkbox>
45
+ <Checkbox indeterminate>Indeterminate</Checkbox>
46
46
  ```
47
47
 
48
48
  ### Disabled
@@ -50,8 +50,8 @@ The `indeterminate` prop sets the checkbox to an indeterminate state, which is u
50
50
  The `disabled` prop disables the checkbox, preventing user interaction. It accepts a boolean value.
51
51
 
52
52
  ```svelte
53
- <Checkbox wrapperAs="label" disabled>Disabled</Checkbox>
54
- <Checkbox wrapperAs="label" checked disabled>Checked & Disabled</Checkbox>
53
+ <Checkbox disabled>Disabled</Checkbox>
54
+ <Checkbox checked disabled>Checked & Disabled</Checkbox>
55
55
  ```
56
56
 
57
57
  ### Value
@@ -59,26 +59,27 @@ The `disabled` prop disables the checkbox, preventing user interaction. It accep
59
59
  The `value` prop sets the value of the checkbox input. It is useful when the checkbox is part of a form submission.
60
60
 
61
61
  ```svelte
62
- <Checkbox wrapperAs="label" value="checkbox-value">Checkbox with Value</Checkbox>
62
+ <Checkbox value="checkbox-value">Checkbox with Value</Checkbox>
63
63
  ```
64
64
 
65
+ HTML attributes, including class, id and ARIA attributes, apply to the control element. Bind ref to access that control. Use wrapperAttributes and wrapperRef for the outer container.
66
+
65
67
  ## Checkbox Props
66
68
 
67
69
  <!-- DO NOT EDIT THIS SECTION (propsmith generated) -->
68
70
  <!-- props:CheckboxProps -->
69
71
 
70
- | Name | Type | Default | Description |
71
- | ----------------------------------------------- | ------------------------------------------ | --------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------- |
72
- | `ref` _bindable_ | `HTMLInputElement` | | The DOM reference of the checkbox element. |
73
- | `wrapperAs` | `'div'` &#124; `'label'` | `'label'` | The DOM element used to wrap the checkbox. `label` associates the children with the input; switch to `div` when the field is wrapped in a `<Label>` of its own. |
74
- | `wrapperRef` _bindable_ | `HTMLDivElement` &#124; `HTMLLabelElement` | | The DOM reference of the checkbox wrapper element. |
75
- | `wrapperAttributes` | `PolymorphicProps` | | The attributes to spread on the wrapper element. |
76
- | `indeterminate` _bindable_ | `boolean` | | Renders the checkbox in its mixed state, neither checked nor unchecked. |
77
- | `name` | `string` &#124; `null` | `id` | The name submitted with the form. Falls back to the id of the checkbox. |
78
- | `group` | `string` &#124; `null` | | The value of the group of checkboxes this input belongs to. |
79
- | `checked` _bindable_ | `boolean` | | Whether the checkbox is checked. |
80
- | `disabled` | `boolean` | | Disables the user interaction. |
81
- | `children` | `Snippet` | | The content of the label. Only rendered when wrapperAs is set to label. |
82
- | `HTMLInputAttributes` without `on:`, `children` | | | |
72
+ | Name | Type | Default | Description |
73
+ | ----------------------------------------------- | -------------------------------- | ------- | ------------------------------------------------------------------------------------------- |
74
+ | `ref` _bindable_ | `HTMLInputElement` &#124; `null` | | The DOM reference of the checkbox element. |
75
+ | `wrapperRef` _bindable_ | `HTMLDivElement` &#124; `null` | | The DOM reference of the checkbox wrapper element. |
76
+ | `wrapperAttributes` | `HTMLAttributes` | | The attributes to spread on the wrapper element. |
77
+ | `indeterminate` _bindable_ | `boolean` &#124; `null` | | Renders the checkbox in its mixed state, neither checked nor unchecked. |
78
+ | `name` | `string` &#124; `null` | `id` | The name submitted with the form. Falls back to the id of the checkbox. |
79
+ | `group` | `string` &#124; `null` | | The value of the group of checkboxes this input belongs to. |
80
+ | `checked` _bindable_ | `boolean` &#124; `null` | | Whether the checkbox is checked. |
81
+ | `disabled` | `boolean` | | Disables the user interaction. |
82
+ | `children` | `Snippet` | | The content of the label associated with the checkbox. Inside a `Label`, it is not rendered |
83
+ | `HTMLInputAttributes` without `on:`, `children` | | | |
83
84
 
84
85
  <!-- /props:CheckboxProps -->
@@ -1,32 +1,23 @@
1
- import type { HTMLInputAttributes } from 'svelte/elements';
2
- import type { PolymorphicProps } from '../../types/index.js';
1
+ import type { HTMLAttributes, HTMLInputAttributes } from 'svelte/elements';
3
2
  import type { Snippet } from 'svelte';
4
3
  /** @propsmith CheckboxProps */
5
- export type CheckboxProps<T extends 'div' | 'label' = 'div'> = {
4
+ export type CheckboxProps = {
6
5
  /** The DOM reference of the checkbox element.
7
6
  * @bindable
8
7
  */
9
- ref?: HTMLInputElement;
10
- /** The DOM element used to wrap the checkbox. `label` associates the children with the
11
- * input; switch to `div` when the field is wrapped in a `<Label>` of its own.
12
- * @default 'label'
13
- * @type 'div' | 'label'
14
- * @default 'div'
15
- */
16
- wrapperAs?: T;
8
+ ref?: HTMLInputElement | null;
17
9
  /** The DOM reference of the checkbox wrapper element.
18
- * @type HTMLDivElement | HTMLLabelElement
19
10
  * @bindable
20
11
  */
21
- wrapperRef?: WrapperRef[T];
12
+ wrapperRef?: HTMLDivElement | null;
22
13
  /** The attributes to spread on the wrapper element.
23
- * @type PolymorphicProps
14
+ * @type HTMLAttributes
24
15
  */
25
- wrapperAttributes?: PolymorphicProps<T>;
16
+ wrapperAttributes?: HTMLAttributes<HTMLDivElement>;
26
17
  /** Renders the checkbox in its mixed state, neither checked nor unchecked.
27
18
  * @bindable
28
19
  */
29
- indeterminate?: boolean;
20
+ indeterminate?: boolean | null;
30
21
  /** The name submitted with the form. Falls back to the id of the checkbox.
31
22
  * @default id
32
23
  */
@@ -36,15 +27,11 @@ export type CheckboxProps<T extends 'div' | 'label' = 'div'> = {
36
27
  /** Whether the checkbox is checked.
37
28
  * @bindable
38
29
  */
39
- checked?: boolean;
30
+ checked?: boolean | null;
40
31
  /** Disables the user interaction. */
41
32
  disabled?: boolean;
42
- /** The content of the label. Only rendered when wrapperAs is set to label.
33
+ /** The content of the label associated with the checkbox. Inside a `Label`, it is not rendered
43
34
  * @type Snippet
44
35
  */
45
- children?: T extends 'label' ? Snippet : never;
36
+ children?: Snippet;
46
37
  } & Omit<HTMLInputAttributes, 'on:' | 'children'>;
47
- export type WrapperRef = {
48
- label: HTMLLabelElement;
49
- div: HTMLDivElement;
50
- };
@@ -1,14 +1,17 @@
1
1
  <script lang="ts">
2
+ import { claimLabel } from '../label/label-context.js';
2
3
  import type { DatePickerProps } from './types.js';
3
4
  import { Flyout, Button, Divider } from '../../index.js';
4
5
  import { on } from 'svelte/events';
5
6
  import { tick } from 'svelte';
6
7
  import { PREFIX } from '../../internal/constants.js';
7
- import { floating } from '../../internal/index.js';
8
+ import { dispatchFieldEvents, floating, invokeHandlers, NativeField } from '../../internal/index.js';
8
9
  import { flip, hide, offset, shift } from '@floating-ui/dom';
9
10
  import DynamicCarousel from '../../internal/components/dynamic-carousel/dynamic-carousel.svelte';
10
11
  import { CheckmarkRegular, DismissRegular } from 'fluentui-icons-svelte';
11
12
 
13
+ const labelContext = claimLabel(() => id);
14
+
12
15
  let {
13
16
  format = 'dd/MM/yyyy',
14
17
  value = $bindable(''),
@@ -21,24 +24,43 @@
21
24
  disabledDates = [],
22
25
  disabledMonths = [],
23
26
  disabledYears = [],
24
- ref = $bindable(),
25
- wrapperRef = $bindable(),
27
+ id = labelContext?.fieldId,
28
+ name = id,
29
+ ref = $bindable(null),
30
+ buttonRef = $bindable(null),
31
+ buttonAttributes,
32
+ wrapperRef = $bindable(null),
26
33
  wrapperAttributes,
27
- inputElement = $bindable(),
28
- inputProps,
34
+ disabled,
35
+ readonly,
36
+ onfocus,
37
+ onblur,
29
38
  popupLabel = 'Choose a date',
39
+ columnLabels,
30
40
  ...attributes
31
41
  }: DatePickerProps = $props();
32
42
 
33
43
  const FALLBACK_ID = $props.id();
34
44
  const POPUP_ID = `${PREFIX}datepicker-${FALLBACK_ID}-popup`;
35
45
 
36
- let popupRef: HTMLElement | undefined = $state();
46
+ let popupRef: HTMLElement | null = $state(null);
47
+
48
+ const native = new NativeField(
49
+ () => ref,
50
+ () => buttonRef,
51
+ labelContext
52
+ );
37
53
 
38
54
  /** Closing always hands the focus back, so the keyboard never lands nowhere. */
39
55
  function closePopup() {
40
56
  open = false;
41
- ref?.focus();
57
+ buttonRef?.focus();
58
+ }
59
+
60
+ /** A label activates the native input it belongs to, which hands the activation to the button. */
61
+ function openFromField() {
62
+ buttonRef?.focus();
63
+ open = !readonly;
42
64
  }
43
65
 
44
66
  // Escape has to work from inside the popup too, and the popup is not a descendant
@@ -78,13 +100,16 @@
78
100
  'November',
79
101
  'December'
80
102
  ];
81
- const LABELS: Record<Column, string> = { month: 'Month', day: 'Day', year: 'Year' };
103
+ // Name the columns on the trigger while there is no date, and the listboxes of the popup.
104
+ const labels: Record<Column, string> = $derived({ month: 'Month', day: 'Day', year: 'Year', ...columnLabels });
82
105
 
83
106
  // Working selection (actual values). Kept in sync with `value` while the popup is closed,
84
107
  // so each open starts from the committed value and Cancel/dismiss discards edits.
85
- let month = $state(new Date().getMonth()); // 0-11
86
- let day = $state(new Date().getDate()); // 1-31 (raw intent; clamped for display via effectiveDay)
87
- let year = $state(new Date().getFullYear());
108
+ // It starts from `value`, so a popup rendered open on the server shows it too.
109
+ const initial = parseValue(value);
110
+ let month = $state(initial.mo); // 0-11
111
+ let day = $state(initial.d); // 1-31 (raw intent; clamped for display via effectiveDay)
112
+ let year = $state(initial.y);
88
113
 
89
114
  // Descending list of selectable years within [minYear, maxYear].
90
115
  const yearsList = $derived(Array.from({ length: Math.max(0, maxYear - minYear) + 1 }, (_, i) => maxYear - i));
@@ -156,7 +181,11 @@
156
181
  });
157
182
 
158
183
  function confirm() {
159
- value = `${year}-${pad(month + 1)}-${pad(effectiveDay)}`;
184
+ const next = `${year}-${pad(month + 1)}-${pad(effectiveDay)}`;
185
+ if (next !== value) {
186
+ value = next;
187
+ dispatchFieldEvents(ref);
188
+ }
160
189
  closePopup();
161
190
  }
162
191
 
@@ -166,25 +195,27 @@
166
195
 
167
196
  // Trigger label per column
168
197
  function display(col: Column): string {
169
- if (!hasValue) return LABELS[col];
198
+ if (!hasValue) return labels[col];
170
199
  if (col === 'month') return MONTH_NAMES[committed.mo];
171
200
  if (col === 'day') return pad(committed.d);
172
201
  return String(committed.y);
173
202
  }
174
203
  </script>
175
204
 
176
- <div class="fs-date-picker-wrapper" bind:this={wrapperRef} {...wrapperAttributes}>
177
- <!-- A real button: Enter and Space, the disabled state and High Contrast styling all
178
- come for free, and the hidden input cannot live inside it. -->
205
+ <div {...wrapperAttributes} class={['fs-date-picker-wrapper', wrapperAttributes?.class]} bind:this={wrapperRef}>
179
206
  <button
207
+ {...buttonAttributes}
208
+ {...native.aria(attributes, buttonAttributes, 'button')}
180
209
  type="button"
181
- class="fs-date-picker"
210
+ class={['fs-date-picker', buttonAttributes?.class]}
211
+ {disabled}
182
212
  aria-haspopup="dialog"
183
213
  aria-expanded={open}
184
214
  aria-controls={open ? POPUP_ID : undefined}
185
- onclick={() => (open = !open)}
186
- bind:this={ref}
187
- {...attributes}
215
+ onclick={(e) => invokeHandlers(e, [], [() => (open = !readonly && !open), buttonAttributes?.onclick])}
216
+ onfocus={(e) => invokeHandlers(e, [], [onfocus, buttonAttributes?.onfocus])}
217
+ onblur={(e) => invokeHandlers(e, [], [onblur, buttonAttributes?.onblur])}
218
+ bind:this={buttonRef}
188
219
  >
189
220
  {#each columns as col, idx (col)}
190
221
  {#if idx > 0}
@@ -194,17 +225,33 @@
194
225
  {/each}
195
226
  </button>
196
227
 
197
- <!-- Carries the value into a form. `hidden` keeps it out of the tab order and out of
198
- the accessibility tree, and a hidden control is still submitted. -->
199
- <input type="date" hidden {value} bind:this={inputElement} {...inputProps} />
228
+ <!-- The field of the form: submitted, validated and reset like any date input,
229
+ behind the button and out of the tab order, since the button is what people use. See `NativeField`. -->
230
+ <input
231
+ {...attributes}
232
+ {name}
233
+ {id}
234
+ min={attributes.min ?? `${String(minYear).padStart(4, '0')}-01-01`}
235
+ max={attributes.max ?? `${String(maxYear).padStart(4, '0')}-12-31`}
236
+ class="native-field"
237
+ aria-hidden={native.reported ? undefined : 'true'}
238
+ type="date"
239
+ tabindex={-1}
240
+ {disabled}
241
+ {readonly}
242
+ bind:value
243
+ bind:this={ref}
244
+ onclick={openFromField}
245
+ />
200
246
  </div>
201
247
 
202
248
  {#if open}
203
249
  <Flyout
204
- {@attach floating(ref, {
250
+ {@attach floating(buttonRef, {
205
251
  placement: 'bottom',
206
252
  middleware: [
207
253
  offset(({ rects }) => {
254
+ // Place over the reference element
208
255
  return -rects.reference.height / 2 - rects.floating.height / 2;
209
256
  }),
210
257
  flip(),
@@ -213,7 +260,6 @@
213
260
  ],
214
261
  strategy: 'fixed'
215
262
  })}
216
- reference={ref}
217
263
  id={POPUP_ID}
218
264
  role="dialog"
219
265
  aria-modal="true"
@@ -228,6 +274,7 @@
228
274
  <div class="carousel-col col-{col}">
229
275
  {#if col === 'month'}
230
276
  <DynamicCarousel
277
+ label={labels.month}
231
278
  values={MONTH_NAMES}
232
279
  selectedIndex={month}
233
280
  disabledIndices={disabledMonthIdx}
@@ -236,6 +283,7 @@
236
283
  {:else if col === 'day'}
237
284
  {#key `${year}-${month}`}
238
285
  <DynamicCarousel
286
+ label={labels.day}
239
287
  values={dayList}
240
288
  selectedIndex={effectiveDay - 1}
241
289
  disabledIndices={disabledDayIdx}
@@ -244,6 +292,7 @@
244
292
  {/key}
245
293
  {:else}
246
294
  <DynamicCarousel
295
+ label={labels.year}
247
296
  values={yearStrings}
248
297
  selectedIndex={yearIdx}
249
298
  disabledIndices={disabledYearIdx}
@@ -265,12 +314,34 @@
265
314
  {/if}
266
315
 
267
316
  <style>
268
- /* Layout-neutral: the button keeps the box the wrapper used to have. */
317
+ /* The box of the button, which the native field covers so its validation message points at the button. */
269
318
  .fs-date-picker-wrapper {
270
- display: contents;
319
+ display: flex;
320
+ position: relative;
321
+ inline-size: fit-content;
322
+ }
323
+ .fs-date-picker-wrapper:has(> .native-field:is(:user-invalid, [aria-invalid='true'])) {
324
+ & .picker-content {
325
+ color: var(--fs-system-critical);
326
+ }
327
+ & .fs-date-picker::after,
328
+ & :global(.fs-divider) {
329
+ background: var(--fs-system-critical);
330
+ }
331
+ }
332
+ .native-field {
333
+ position: absolute;
334
+ inset: 0;
335
+ inline-size: 100%;
336
+ block-size: 100%;
337
+ margin: 0;
338
+ box-sizing: border-box;
339
+ opacity: 0;
340
+ pointer-events: none;
271
341
  }
272
342
  .fs-date-picker {
273
343
  display: flex;
344
+ flex: 1 1 auto;
274
345
  position: relative;
275
346
  border-radius: var(--fs-control-border-radius);
276
347
  font-size: var(--fs-body-font-size);
@@ -1,4 +1,4 @@
1
1
  import type { DatePickerProps } from './types.ts';
2
- declare const DatePicker: import("svelte").Component<DatePickerProps, {}, "ref" | "value" | "wrapperRef" | "open" | "inputElement">;
2
+ declare const DatePicker: import("svelte").Component<DatePickerProps, {}, "ref" | "value" | "open" | "wrapperRef" | "buttonRef">;
3
3
  type DatePicker = ReturnType<typeof DatePicker>;
4
4
  export default DatePicker;