reka-ui 2.7.0 → 2.8.2

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 (323) hide show
  1. package/dist/Avatar/AvatarImage.cjs +4 -2
  2. package/dist/Avatar/AvatarImage.cjs.map +1 -1
  3. package/dist/Avatar/AvatarImage.js +4 -2
  4. package/dist/Avatar/AvatarImage.js.map +1 -1
  5. package/dist/Calendar/CalendarCellTrigger.cjs +4 -1
  6. package/dist/Calendar/CalendarCellTrigger.cjs.map +1 -1
  7. package/dist/Calendar/CalendarCellTrigger.js +4 -1
  8. package/dist/Calendar/CalendarCellTrigger.js.map +1 -1
  9. package/dist/Calendar/CalendarRoot.cjs +12 -7
  10. package/dist/Calendar/CalendarRoot.cjs.map +1 -1
  11. package/dist/Calendar/CalendarRoot.js +13 -8
  12. package/dist/Calendar/CalendarRoot.js.map +1 -1
  13. package/dist/Calendar/useCalendar.cjs +32 -2
  14. package/dist/Calendar/useCalendar.cjs.map +1 -1
  15. package/dist/Calendar/useCalendar.js +33 -3
  16. package/dist/Calendar/useCalendar.js.map +1 -1
  17. package/dist/Collection/Collection.cjs +6 -2
  18. package/dist/Collection/Collection.cjs.map +1 -1
  19. package/dist/Collection/Collection.js +6 -2
  20. package/dist/Collection/Collection.js.map +1 -1
  21. package/dist/Combobox/ComboboxContent.cjs +4 -0
  22. package/dist/Combobox/ComboboxContent.cjs.map +1 -1
  23. package/dist/Combobox/ComboboxContent.js +4 -0
  24. package/dist/Combobox/ComboboxContent.js.map +1 -1
  25. package/dist/Combobox/ComboboxContentImpl.cjs +47 -33
  26. package/dist/Combobox/ComboboxContentImpl.cjs.map +1 -1
  27. package/dist/Combobox/ComboboxContentImpl.js +48 -34
  28. package/dist/Combobox/ComboboxContentImpl.js.map +1 -1
  29. package/dist/ContextMenu/ContextMenuContent.cjs +4 -0
  30. package/dist/ContextMenu/ContextMenuContent.cjs.map +1 -1
  31. package/dist/ContextMenu/ContextMenuContent.js +4 -0
  32. package/dist/ContextMenu/ContextMenuContent.js.map +1 -1
  33. package/dist/ContextMenu/ContextMenuRadioGroup.cjs +1 -1
  34. package/dist/ContextMenu/ContextMenuRadioGroup.js +1 -1
  35. package/dist/ContextMenu/ContextMenuRadioItem.cjs +1 -1
  36. package/dist/ContextMenu/ContextMenuRadioItem.js +1 -1
  37. package/dist/ContextMenu/ContextMenuSubContent.cjs +4 -0
  38. package/dist/ContextMenu/ContextMenuSubContent.cjs.map +1 -1
  39. package/dist/ContextMenu/ContextMenuSubContent.js +4 -0
  40. package/dist/ContextMenu/ContextMenuSubContent.js.map +1 -1
  41. package/dist/DatePicker/DatePickerContent.cjs +4 -0
  42. package/dist/DatePicker/DatePickerContent.cjs.map +1 -1
  43. package/dist/DatePicker/DatePickerContent.js +4 -0
  44. package/dist/DatePicker/DatePickerContent.js.map +1 -1
  45. package/dist/DatePicker/DatePickerRoot.cjs +10 -8
  46. package/dist/DatePicker/DatePickerRoot.cjs.map +1 -1
  47. package/dist/DatePicker/DatePickerRoot.js +10 -8
  48. package/dist/DatePicker/DatePickerRoot.js.map +1 -1
  49. package/dist/DateRangePicker/DateRangePickerContent.cjs +4 -0
  50. package/dist/DateRangePicker/DateRangePickerContent.cjs.map +1 -1
  51. package/dist/DateRangePicker/DateRangePickerContent.js +4 -0
  52. package/dist/DateRangePicker/DateRangePickerContent.js.map +1 -1
  53. package/dist/DateRangePicker/DateRangePickerRoot.cjs +10 -8
  54. package/dist/DateRangePicker/DateRangePickerRoot.cjs.map +1 -1
  55. package/dist/DateRangePicker/DateRangePickerRoot.js +11 -9
  56. package/dist/DateRangePicker/DateRangePickerRoot.js.map +1 -1
  57. package/dist/DropdownMenu/DropdownMenuContent.cjs +4 -0
  58. package/dist/DropdownMenu/DropdownMenuContent.cjs.map +1 -1
  59. package/dist/DropdownMenu/DropdownMenuContent.js +4 -0
  60. package/dist/DropdownMenu/DropdownMenuContent.js.map +1 -1
  61. package/dist/DropdownMenu/DropdownMenuRadioGroup.cjs +1 -1
  62. package/dist/DropdownMenu/DropdownMenuRadioGroup.js +1 -1
  63. package/dist/DropdownMenu/DropdownMenuRadioItem.cjs +1 -1
  64. package/dist/DropdownMenu/DropdownMenuRadioItem.js +1 -1
  65. package/dist/DropdownMenu/DropdownMenuSubContent.cjs +4 -0
  66. package/dist/DropdownMenu/DropdownMenuSubContent.cjs.map +1 -1
  67. package/dist/DropdownMenu/DropdownMenuSubContent.js +4 -0
  68. package/dist/DropdownMenu/DropdownMenuSubContent.js.map +1 -1
  69. package/dist/Editable/EditableInput.cjs +1 -1
  70. package/dist/Editable/EditableInput.cjs.map +1 -1
  71. package/dist/Editable/EditableInput.js +1 -1
  72. package/dist/Editable/EditableInput.js.map +1 -1
  73. package/dist/FocusScope/FocusScope.cjs +1 -1
  74. package/dist/FocusScope/FocusScope.cjs.map +1 -1
  75. package/dist/FocusScope/FocusScope.js +2 -2
  76. package/dist/FocusScope/FocusScope.js.map +1 -1
  77. package/dist/FocusScope/stack.cjs +0 -9
  78. package/dist/FocusScope/stack.cjs.map +1 -1
  79. package/dist/FocusScope/stack.js +1 -4
  80. package/dist/FocusScope/stack.js.map +1 -1
  81. package/dist/HoverCard/HoverCardContent.cjs +4 -0
  82. package/dist/HoverCard/HoverCardContent.cjs.map +1 -1
  83. package/dist/HoverCard/HoverCardContent.js +4 -0
  84. package/dist/HoverCard/HoverCardContent.js.map +1 -1
  85. package/dist/HoverCard/HoverCardContentImpl.cjs +4 -0
  86. package/dist/HoverCard/HoverCardContentImpl.cjs.map +1 -1
  87. package/dist/HoverCard/HoverCardContentImpl.js +4 -0
  88. package/dist/HoverCard/HoverCardContentImpl.js.map +1 -1
  89. package/dist/Listbox/ListboxRoot.cjs.map +1 -1
  90. package/dist/Listbox/ListboxRoot.js.map +1 -1
  91. package/dist/Menu/MenuContent.cjs +4 -0
  92. package/dist/Menu/MenuContent.cjs.map +1 -1
  93. package/dist/Menu/MenuContent.js +4 -0
  94. package/dist/Menu/MenuContent.js.map +1 -1
  95. package/dist/Menu/MenuContentImpl.cjs +4 -0
  96. package/dist/Menu/MenuContentImpl.cjs.map +1 -1
  97. package/dist/Menu/MenuContentImpl.js +4 -0
  98. package/dist/Menu/MenuContentImpl.js.map +1 -1
  99. package/dist/Menu/MenuRadioGroup.cjs +1 -1
  100. package/dist/Menu/MenuRadioGroup.cjs.map +1 -1
  101. package/dist/Menu/MenuRadioGroup.js +1 -1
  102. package/dist/Menu/MenuRadioGroup.js.map +1 -1
  103. package/dist/Menu/MenuRadioItem.cjs +1 -1
  104. package/dist/Menu/MenuRadioItem.cjs.map +1 -1
  105. package/dist/Menu/MenuRadioItem.js +1 -1
  106. package/dist/Menu/MenuRadioItem.js.map +1 -1
  107. package/dist/Menu/MenuRootContentModal.cjs +4 -0
  108. package/dist/Menu/MenuRootContentModal.cjs.map +1 -1
  109. package/dist/Menu/MenuRootContentModal.js +4 -0
  110. package/dist/Menu/MenuRootContentModal.js.map +1 -1
  111. package/dist/Menu/MenuRootContentNonModal.cjs +4 -0
  112. package/dist/Menu/MenuRootContentNonModal.cjs.map +1 -1
  113. package/dist/Menu/MenuRootContentNonModal.js +4 -0
  114. package/dist/Menu/MenuRootContentNonModal.js.map +1 -1
  115. package/dist/Menu/MenuSubContent.cjs +4 -0
  116. package/dist/Menu/MenuSubContent.cjs.map +1 -1
  117. package/dist/Menu/MenuSubContent.js +4 -0
  118. package/dist/Menu/MenuSubContent.js.map +1 -1
  119. package/dist/Menubar/MenubarContent.cjs +4 -0
  120. package/dist/Menubar/MenubarContent.cjs.map +1 -1
  121. package/dist/Menubar/MenubarContent.js +4 -0
  122. package/dist/Menubar/MenubarContent.js.map +1 -1
  123. package/dist/Menubar/MenubarRadioGroup.cjs +1 -1
  124. package/dist/Menubar/MenubarRadioGroup.js +1 -1
  125. package/dist/Menubar/MenubarRadioItem.cjs +1 -1
  126. package/dist/Menubar/MenubarRadioItem.js +1 -1
  127. package/dist/Menubar/MenubarSubContent.cjs +4 -0
  128. package/dist/Menubar/MenubarSubContent.cjs.map +1 -1
  129. package/dist/Menubar/MenubarSubContent.js +4 -0
  130. package/dist/Menubar/MenubarSubContent.js.map +1 -1
  131. package/dist/NavigationMenu/NavigationMenuContent.cjs +1 -1
  132. package/dist/NavigationMenu/NavigationMenuContent.js +1 -1
  133. package/dist/NavigationMenu/NavigationMenuContentImpl.cjs +1 -1
  134. package/dist/NavigationMenu/NavigationMenuContentImpl.js +1 -1
  135. package/dist/NavigationMenu/NavigationMenuItem.cjs +1 -1
  136. package/dist/NavigationMenu/NavigationMenuItem.js +1 -1
  137. package/dist/NavigationMenu/NavigationMenuRoot.cjs +7 -5
  138. package/dist/NavigationMenu/NavigationMenuRoot.cjs.map +1 -1
  139. package/dist/NavigationMenu/NavigationMenuRoot.js +8 -6
  140. package/dist/NavigationMenu/NavigationMenuRoot.js.map +1 -1
  141. package/dist/NavigationMenu/NavigationMenuTrigger.cjs +1 -1
  142. package/dist/NavigationMenu/NavigationMenuTrigger.js +1 -1
  143. package/dist/NavigationMenu/NavigationMenuViewport.cjs +1 -1
  144. package/dist/NavigationMenu/NavigationMenuViewport.js +1 -1
  145. package/dist/NumberField/NumberFieldRoot.cjs +6 -1
  146. package/dist/NumberField/NumberFieldRoot.cjs.map +1 -1
  147. package/dist/NumberField/NumberFieldRoot.js +6 -1
  148. package/dist/NumberField/NumberFieldRoot.js.map +1 -1
  149. package/dist/PinInput/PinInputInput.cjs +15 -11
  150. package/dist/PinInput/PinInputInput.cjs.map +1 -1
  151. package/dist/PinInput/PinInputInput.js +15 -11
  152. package/dist/PinInput/PinInputInput.js.map +1 -1
  153. package/dist/Popover/PopoverContent.cjs +4 -0
  154. package/dist/Popover/PopoverContent.cjs.map +1 -1
  155. package/dist/Popover/PopoverContent.js +4 -0
  156. package/dist/Popover/PopoverContent.js.map +1 -1
  157. package/dist/Popover/PopoverContentImpl.cjs +4 -0
  158. package/dist/Popover/PopoverContentImpl.cjs.map +1 -1
  159. package/dist/Popover/PopoverContentImpl.js +4 -0
  160. package/dist/Popover/PopoverContentImpl.js.map +1 -1
  161. package/dist/Popover/PopoverContentModal.cjs +4 -0
  162. package/dist/Popover/PopoverContentModal.cjs.map +1 -1
  163. package/dist/Popover/PopoverContentModal.js +4 -0
  164. package/dist/Popover/PopoverContentModal.js.map +1 -1
  165. package/dist/Popover/PopoverContentNonModal.cjs +4 -0
  166. package/dist/Popover/PopoverContentNonModal.cjs.map +1 -1
  167. package/dist/Popover/PopoverContentNonModal.js +4 -0
  168. package/dist/Popover/PopoverContentNonModal.js.map +1 -1
  169. package/dist/Popper/PopperContent.cjs +10 -2
  170. package/dist/Popper/PopperContent.cjs.map +1 -1
  171. package/dist/Popper/PopperContent.js +10 -2
  172. package/dist/Popper/PopperContent.js.map +1 -1
  173. package/dist/RangeCalendar/RangeCalendarCellTrigger.cjs +8 -2
  174. package/dist/RangeCalendar/RangeCalendarCellTrigger.cjs.map +1 -1
  175. package/dist/RangeCalendar/RangeCalendarCellTrigger.js +8 -2
  176. package/dist/RangeCalendar/RangeCalendarCellTrigger.js.map +1 -1
  177. package/dist/RangeCalendar/RangeCalendarGrid.cjs +2 -1
  178. package/dist/RangeCalendar/RangeCalendarGrid.cjs.map +1 -1
  179. package/dist/RangeCalendar/RangeCalendarGrid.js +2 -1
  180. package/dist/RangeCalendar/RangeCalendarGrid.js.map +1 -1
  181. package/dist/RangeCalendar/RangeCalendarRoot.cjs +30 -16
  182. package/dist/RangeCalendar/RangeCalendarRoot.cjs.map +1 -1
  183. package/dist/RangeCalendar/RangeCalendarRoot.js +31 -17
  184. package/dist/RangeCalendar/RangeCalendarRoot.js.map +1 -1
  185. package/dist/RangeCalendar/useRangeCalendar.cjs +41 -8
  186. package/dist/RangeCalendar/useRangeCalendar.cjs.map +1 -1
  187. package/dist/RangeCalendar/useRangeCalendar.js +41 -8
  188. package/dist/RangeCalendar/useRangeCalendar.js.map +1 -1
  189. package/dist/ScrollArea/ScrollAreaRoot.cjs.map +1 -1
  190. package/dist/ScrollArea/ScrollAreaRoot.js.map +1 -1
  191. package/dist/ScrollArea/ScrollAreaScrollbar.cjs +9 -2
  192. package/dist/ScrollArea/ScrollAreaScrollbar.cjs.map +1 -1
  193. package/dist/ScrollArea/ScrollAreaScrollbar.js +9 -2
  194. package/dist/ScrollArea/ScrollAreaScrollbar.js.map +1 -1
  195. package/dist/ScrollArea/ScrollAreaScrollbarGlimpse.cjs +132 -0
  196. package/dist/ScrollArea/ScrollAreaScrollbarGlimpse.cjs.map +1 -0
  197. package/dist/ScrollArea/ScrollAreaScrollbarGlimpse.js +126 -0
  198. package/dist/ScrollArea/ScrollAreaScrollbarGlimpse.js.map +1 -0
  199. package/dist/Select/SelectContent.cjs +4 -0
  200. package/dist/Select/SelectContent.cjs.map +1 -1
  201. package/dist/Select/SelectContent.js +4 -0
  202. package/dist/Select/SelectContent.js.map +1 -1
  203. package/dist/Select/SelectContentImpl.cjs +4 -0
  204. package/dist/Select/SelectContentImpl.cjs.map +1 -1
  205. package/dist/Select/SelectContentImpl.js +4 -0
  206. package/dist/Select/SelectContentImpl.js.map +1 -1
  207. package/dist/Select/SelectPopperPosition.cjs +4 -0
  208. package/dist/Select/SelectPopperPosition.cjs.map +1 -1
  209. package/dist/Select/SelectPopperPosition.js +4 -0
  210. package/dist/Select/SelectPopperPosition.js.map +1 -1
  211. package/dist/Tabs/TabsContent.cjs +4 -0
  212. package/dist/Tabs/TabsContent.cjs.map +1 -1
  213. package/dist/Tabs/TabsContent.js +5 -1
  214. package/dist/Tabs/TabsContent.js.map +1 -1
  215. package/dist/Tabs/TabsRoot.cjs +11 -1
  216. package/dist/Tabs/TabsRoot.cjs.map +1 -1
  217. package/dist/Tabs/TabsRoot.js +12 -2
  218. package/dist/Tabs/TabsRoot.js.map +1 -1
  219. package/dist/Tabs/TabsTrigger.cjs +1 -1
  220. package/dist/Tabs/TabsTrigger.cjs.map +1 -1
  221. package/dist/Tabs/TabsTrigger.js +1 -1
  222. package/dist/Tabs/TabsTrigger.js.map +1 -1
  223. package/dist/TimeField/TimeFieldInput.cjs +3 -1
  224. package/dist/TimeField/TimeFieldInput.cjs.map +1 -1
  225. package/dist/TimeField/TimeFieldInput.js +3 -1
  226. package/dist/TimeField/TimeFieldInput.js.map +1 -1
  227. package/dist/TimeField/TimeFieldRoot.cjs +24 -2
  228. package/dist/TimeField/TimeFieldRoot.cjs.map +1 -1
  229. package/dist/TimeField/TimeFieldRoot.js +24 -2
  230. package/dist/TimeField/TimeFieldRoot.js.map +1 -1
  231. package/dist/date/calendar.cjs +29 -9
  232. package/dist/date/calendar.cjs.map +1 -1
  233. package/dist/date/calendar.js +25 -11
  234. package/dist/date/calendar.js.map +1 -1
  235. package/dist/date/comparators.cjs +14 -2
  236. package/dist/date/comparators.cjs.map +1 -1
  237. package/dist/date/comparators.js +14 -2
  238. package/dist/date/comparators.js.map +1 -1
  239. package/dist/date/parser.cjs +1 -0
  240. package/dist/date/parser.cjs.map +1 -1
  241. package/dist/date/parser.js +1 -0
  242. package/dist/date/parser.js.map +1 -1
  243. package/dist/date/useDateField.cjs +41 -20
  244. package/dist/date/useDateField.cjs.map +1 -1
  245. package/dist/date/useDateField.js +41 -20
  246. package/dist/date/useDateField.js.map +1 -1
  247. package/dist/date.cjs +1 -0
  248. package/dist/date.d.cts +2 -2
  249. package/dist/date.d.ts +2 -2
  250. package/dist/date.js +2 -2
  251. package/dist/index.cjs +3 -1
  252. package/dist/index.d.cts +1148 -1106
  253. package/dist/index.d.cts.map +1 -1
  254. package/dist/index.d.ts +670 -628
  255. package/dist/index.d.ts.map +1 -1
  256. package/dist/index.js +3 -2
  257. package/dist/index2.d.cts +9 -2
  258. package/dist/index2.d.cts.map +1 -1
  259. package/dist/index2.d.ts +9 -2
  260. package/dist/index2.d.ts.map +1 -1
  261. package/dist/shared/useDateFormatter.cjs +1 -1
  262. package/dist/shared/useDateFormatter.cjs.map +1 -1
  263. package/dist/shared/useDateFormatter.js +1 -1
  264. package/dist/shared/useDateFormatter.js.map +1 -1
  265. package/dist/shared/useForwardExpose.cjs +1 -1
  266. package/dist/shared/useForwardExpose.cjs.map +1 -1
  267. package/dist/shared/useForwardExpose.js +1 -1
  268. package/dist/shared/useForwardExpose.js.map +1 -1
  269. package/dist/shared/useGraceArea.cjs +1 -1
  270. package/dist/shared/useGraceArea.cjs.map +1 -1
  271. package/dist/shared/useGraceArea.js +1 -1
  272. package/dist/shared/useGraceArea.js.map +1 -1
  273. package/package.json +20 -16
  274. package/src/Avatar/AvatarImage.vue +2 -1
  275. package/src/Calendar/CalendarCellTrigger.vue +8 -1
  276. package/src/Calendar/CalendarRoot.vue +19 -7
  277. package/src/Calendar/useCalendar.ts +43 -3
  278. package/src/Collection/Collection.ts +3 -2
  279. package/src/Combobox/ComboboxContentImpl.vue +40 -32
  280. package/src/Combobox/ComboboxRoot.vue +1 -1
  281. package/src/DatePicker/DatePickerRoot.vue +10 -10
  282. package/src/DatePicker/index.ts +4 -4
  283. package/src/DateRangePicker/DateRangePickerRoot.vue +11 -11
  284. package/src/DateRangePicker/index.ts +4 -4
  285. package/src/Editable/EditableInput.vue +1 -1
  286. package/src/FocusScope/FocusScope.vue +2 -2
  287. package/src/Listbox/ListboxFilter.vue +1 -1
  288. package/src/Listbox/ListboxRoot.vue +2 -1
  289. package/src/Menu/MenuRadioGroup.vue +5 -4
  290. package/src/Menu/MenuRadioItem.vue +2 -1
  291. package/src/NavigationMenu/NavigationMenuRoot.vue +10 -6
  292. package/src/NumberField/NumberFieldRoot.vue +6 -1
  293. package/src/PinInput/PinInputInput.vue +25 -18
  294. package/src/Popper/PopperContent.vue +15 -5
  295. package/src/RadioGroup/RadioGroupRoot.vue +1 -1
  296. package/src/RangeCalendar/RangeCalendarCellTrigger.vue +13 -3
  297. package/src/RangeCalendar/RangeCalendarGrid.vue +1 -0
  298. package/src/RangeCalendar/RangeCalendarRoot.vue +46 -30
  299. package/src/RangeCalendar/useRangeCalendar.ts +43 -15
  300. package/src/Rating/RatingItem.vue +52 -0
  301. package/src/Rating/RatingItemIndicator.vue +60 -0
  302. package/src/Rating/RatingRoot.vue +113 -0
  303. package/src/Rating/index.ts +3 -0
  304. package/src/ScrollArea/ScrollAreaRoot.vue +2 -1
  305. package/src/ScrollArea/ScrollAreaScrollbar.vue +9 -0
  306. package/src/ScrollArea/ScrollAreaScrollbarGlimpse.vue +145 -0
  307. package/src/ScrollArea/index.ts +4 -0
  308. package/src/ScrollArea/types.ts +1 -1
  309. package/src/Tabs/TabsContent.vue +6 -1
  310. package/src/Tabs/TabsRoot.vue +14 -1
  311. package/src/Tabs/TabsTrigger.vue +1 -1
  312. package/src/TimeField/TimeFieldInput.vue +6 -1
  313. package/src/TimeField/TimeFieldRoot.vue +25 -2
  314. package/src/Tree/TreeRoot.vue +2 -2
  315. package/src/date/calendar.ts +42 -18
  316. package/src/date/comparators.ts +15 -2
  317. package/src/index.ts +1 -0
  318. package/src/shared/date/parser.ts +10 -0
  319. package/src/shared/date/useDateField.ts +72 -21
  320. package/src/shared/index.ts +1 -1
  321. package/src/shared/useDateFormatter.ts +2 -2
  322. package/src/shared/useForwardExpose.ts +1 -1
  323. package/src/shared/useGraceArea.ts +1 -1
@@ -0,0 +1,113 @@
1
+ <script lang="ts">
2
+ import type { RadioGroupRootProps } from '@/RadioGroup'
3
+ import { reactiveOmit, useVModel } from '@vueuse/core'
4
+ import { RadioGroupRoot } from '@/RadioGroup'
5
+ import { createContext, useForwardExpose } from '@/shared'
6
+
7
+ export interface RatingRootContext {
8
+ modelValue: Ref<number>
9
+ items: ComputedRef<number[]>
10
+ hoveredRating: Ref<number>
11
+ disabled: Ref<boolean>
12
+ step: Ref<number>
13
+ changeModelValue: (rating: number) => void
14
+ changeHoveredRating: (rating: number) => void
15
+ }
16
+
17
+ export interface RatingRootProps extends Omit<RadioGroupRootProps, 'modelValue' | 'defaultValue'> {
18
+ /**
19
+ * The value of the tab that should be active when initially rendered. Use when you do not need to control the state of the tabs
20
+ */
21
+ defaultValue?: number
22
+ /** The controlled value of the tab to activate. Can be bind as `v-model`. */
23
+ modelValue?: number
24
+ length?: number
25
+ clearable?: boolean
26
+ hoverable?: boolean
27
+ step?: 1 | 0.5 | 0.25 | 0.1
28
+
29
+ }
30
+ export type RatingRootEmits = {
31
+ /** Event handler called when the value changes */
32
+ 'update:modelValue': [payload: number]
33
+ }
34
+
35
+ export const [injectRatingRootContext, provideRatingRootContext]
36
+ = createContext<RatingRootContext>('RatingRoot')
37
+ </script>
38
+
39
+ <script setup lang="ts">
40
+ import type { ComputedRef, Ref } from 'vue'
41
+ import { computed, ref, toRefs } from 'vue'
42
+
43
+ const props = withDefaults(defineProps<RatingRootProps>(), {
44
+ orientation: 'horizontal',
45
+ length: 5,
46
+ step: 1,
47
+ })
48
+ const emits = defineEmits<RatingRootEmits>()
49
+
50
+ defineSlots<{
51
+ default?: (props: {
52
+ modelValue: number | undefined
53
+ items: number[]
54
+ }) => any
55
+ }>()
56
+
57
+ const { length, disabled, clearable, hoverable, step } = toRefs(props)
58
+
59
+ useForwardExpose()
60
+
61
+ const modelValue = useVModel<RatingRootProps, 'modelValue', 'update:modelValue'>(props, 'modelValue', emits, {
62
+ defaultValue: props.defaultValue,
63
+ passive: (props.modelValue === undefined) as false,
64
+ }) as Ref<number>
65
+
66
+ const items = computed(() => {
67
+ return Array.from({ length: length.value }, (_, i) => i + 1)
68
+ })
69
+
70
+ const hoveredRating = ref<number>(0)
71
+
72
+ function changeModelValue(rating: number) {
73
+ if (disabled.value)
74
+ return
75
+
76
+ if (clearable.value && modelValue.value === rating) {
77
+ hoveredRating.value = 0
78
+ modelValue.value = 0
79
+ }
80
+ else {
81
+ modelValue.value = rating
82
+ }
83
+ }
84
+
85
+ function changeHoveredRating(rating: number) {
86
+ if (disabled.value || !hoverable.value)
87
+ return
88
+
89
+ hoveredRating.value = rating
90
+ }
91
+
92
+ provideRatingRootContext({
93
+ modelValue,
94
+ items,
95
+ hoveredRating,
96
+ disabled,
97
+ step,
98
+ changeModelValue,
99
+ changeHoveredRating,
100
+ })
101
+ </script>
102
+
103
+ <template>
104
+ <RadioGroupRoot
105
+ v-bind="reactiveOmit(props, 'length', 'clearable', 'hoverable', 'step')"
106
+ :disabled="disabled"
107
+ >
108
+ <slot
109
+ :items="items"
110
+ :model-value="modelValue"
111
+ />
112
+ </RadioGroupRoot>
113
+ </template>
@@ -0,0 +1,3 @@
1
+ export { default as RatingItem, type RatingItemProps } from './RatingItem.vue'
2
+ export { default as RatingItemIndicator } from './RatingItemIndicator.vue'
3
+ export { default as RatingRoot, type RatingRootProps } from './RatingRoot.vue'
@@ -35,7 +35,8 @@ export interface ScrollAreaRootProps extends PrimitiveProps {
35
35
  * `auto` - means that scrollbars are visible when content is overflowing on the corresponding orientation. <br>
36
36
  * `always` - means that scrollbars are always visible regardless of whether the content is overflowing.<br>
37
37
  * `scroll` - means that scrollbars are visible when the user is scrolling along its corresponding orientation.<br>
38
- * `hover` - when the user is scrolling along its corresponding orientation and when the user is hovering over the scroll area.
38
+ * `hover` - when the user is scrolling along its corresponding orientation and when the user is hovering over the scroll area.<br>
39
+ * `glimpse` - a hybrid approach that briefly shows scrollbars when the user enters the scroll area, then hides them until further interaction.
39
40
  */
40
41
  type?: ScrollType
41
42
  /** The reading direction of the combobox when applicable. <br> If omitted, inherits globally from `ConfigProvider` or assumes LTR (left-to-right) reading mode. */
@@ -34,6 +34,7 @@ import {
34
34
  } from 'vue'
35
35
  import { injectScrollAreaRootContext } from './ScrollAreaRoot.vue'
36
36
  import ScrollAreaScrollbarAuto from './ScrollAreaScrollbarAuto.vue'
37
+ import ScrollAreaScrollbarGlimpse from './ScrollAreaScrollbarGlimpse.vue'
37
38
  import ScrollAreaScrollbarHover from './ScrollAreaScrollbarHover.vue'
38
39
  import ScrollAreaScrollbarScroll from './ScrollAreaScrollbarScroll.vue'
39
40
  import ScrollAreaScrollbarVisible from './ScrollAreaScrollbarVisible.vue'
@@ -94,6 +95,14 @@ provideScrollAreaScrollbarContext({
94
95
  >
95
96
  <slot />
96
97
  </ScrollAreaScrollbarScroll>
98
+ <ScrollAreaScrollbarGlimpse
99
+ v-else-if="rootContext.type.value === 'glimpse'"
100
+ v-bind="$attrs"
101
+ :ref="forwardRef"
102
+ :force-mount="forceMount"
103
+ >
104
+ <slot />
105
+ </ScrollAreaScrollbarGlimpse>
97
106
  <ScrollAreaScrollbarAuto
98
107
  v-else-if="rootContext.type.value === 'auto'"
99
108
  v-bind="$attrs"
@@ -0,0 +1,145 @@
1
+ <script lang="ts">
2
+ import type { ScrollAreaScrollbarAutoProps } from './ScrollAreaScrollbarAuto.vue'
3
+
4
+ export interface ScrollAreaScrollbarGlimpseProps extends ScrollAreaScrollbarAutoProps {}
5
+ </script>
6
+
7
+ <script setup lang="ts">
8
+ import { useDebounceFn } from '@vueuse/core'
9
+ import { computed, onMounted, onUnmounted, watchEffect } from 'vue'
10
+ import { Presence } from '@/Presence'
11
+ import { useForwardExpose } from '@/shared'
12
+ import { useStateMachine } from '../shared/useStateMachine'
13
+ import { injectScrollAreaRootContext } from './ScrollAreaRoot.vue'
14
+ import { injectScrollAreaScrollbarContext } from './ScrollAreaScrollbar.vue'
15
+ import ScrollAreaScrollbarAuto from './ScrollAreaScrollbarAuto.vue'
16
+
17
+ defineOptions({
18
+ inheritAttrs: false,
19
+ })
20
+
21
+ defineProps<ScrollAreaScrollbarGlimpseProps>()
22
+
23
+ const rootContext = injectScrollAreaRootContext()
24
+ const scrollbarContext = injectScrollAreaScrollbarContext()
25
+
26
+ const { forwardRef } = useForwardExpose()
27
+
28
+ const { state, dispatch } = useStateMachine('hidden', {
29
+ hidden: {
30
+ POINTER_ENTER: 'glimpse',
31
+ SCROLL: 'scrolling',
32
+ },
33
+ glimpse: {
34
+ HIDE: 'hidden',
35
+ POINTER_LEAVE: 'hidden',
36
+ SCROLL: 'scrolling',
37
+ POINTER_ENTER: 'glimpse',
38
+ },
39
+ scrolling: {
40
+ SCROLL_END: 'idle',
41
+ POINTER_ENTER: 'interacting',
42
+ },
43
+ interacting: {
44
+ SCROLL: 'interacting',
45
+ POINTER_LEAVE: 'idle',
46
+ },
47
+ idle: {
48
+ HIDE: 'hidden',
49
+ SCROLL: 'scrolling',
50
+ POINTER_ENTER: 'interacting',
51
+ },
52
+ })
53
+
54
+ const visible = computed(() => state.value !== 'hidden')
55
+
56
+ function handlePointerEnter() {
57
+ dispatch('POINTER_ENTER')
58
+ }
59
+
60
+ function handlePointerLeave() {
61
+ dispatch('POINTER_LEAVE')
62
+ }
63
+
64
+ const debounceScrollEnd = useDebounceFn(() => dispatch('SCROLL_END'), 100)
65
+
66
+ watchEffect((onCleanup) => {
67
+ if (state.value === 'glimpse') {
68
+ const timeId = window.setTimeout(
69
+ () => dispatch('HIDE'),
70
+ rootContext.scrollHideDelay.value,
71
+ )
72
+
73
+ onCleanup(() => {
74
+ window.clearTimeout(timeId)
75
+ })
76
+ }
77
+ })
78
+
79
+ watchEffect((onCleanup) => {
80
+ if (state.value === 'idle') {
81
+ const timeId = window.setTimeout(
82
+ () => dispatch('HIDE'),
83
+ rootContext.scrollHideDelay.value,
84
+ )
85
+
86
+ onCleanup(() => {
87
+ window.clearTimeout(timeId)
88
+ })
89
+ }
90
+ })
91
+
92
+ watchEffect((onCleanup) => {
93
+ const viewport = rootContext.viewport.value
94
+ const scrollDirection = scrollbarContext.isHorizontal.value
95
+ ? 'scrollLeft'
96
+ : 'scrollTop'
97
+
98
+ if (viewport) {
99
+ let prevScrollPos = viewport[scrollDirection]
100
+ const handleScroll = () => {
101
+ const scrollPos = viewport[scrollDirection]
102
+ const hasScrollInDirectionChanged = prevScrollPos !== scrollPos
103
+ if (hasScrollInDirectionChanged) {
104
+ dispatch('SCROLL')
105
+ debounceScrollEnd()
106
+ }
107
+ prevScrollPos = scrollPos
108
+ }
109
+ viewport.addEventListener('scroll', handleScroll)
110
+
111
+ onCleanup(() => {
112
+ viewport.removeEventListener('scroll', handleScroll)
113
+ })
114
+ }
115
+ })
116
+
117
+ onMounted(() => {
118
+ const scrollArea = rootContext.scrollArea.value
119
+
120
+ if (scrollArea) {
121
+ scrollArea.addEventListener('pointerenter', handlePointerEnter)
122
+ scrollArea.addEventListener('pointerleave', handlePointerLeave)
123
+ }
124
+ })
125
+
126
+ onUnmounted(() => {
127
+ const scrollArea = rootContext.scrollArea.value
128
+ if (scrollArea) {
129
+ scrollArea.removeEventListener('pointerenter', handlePointerEnter)
130
+ scrollArea.removeEventListener('pointerleave', handlePointerLeave)
131
+ }
132
+ })
133
+ </script>
134
+
135
+ <template>
136
+ <Presence :present="forceMount || visible">
137
+ <ScrollAreaScrollbarAuto
138
+ v-bind="$attrs"
139
+ :ref="forwardRef"
140
+ :data-state="visible ? 'visible' : 'hidden'"
141
+ >
142
+ <slot />
143
+ </ScrollAreaScrollbarAuto>
144
+ </Presence>
145
+ </template>
@@ -12,6 +12,10 @@ export {
12
12
  default as ScrollAreaScrollbar,
13
13
  type ScrollAreaScrollbarProps,
14
14
  } from './ScrollAreaScrollbar.vue'
15
+ export {
16
+ default as ScrollAreaScrollbarGlimpse,
17
+ type ScrollAreaScrollbarGlimpseProps,
18
+ } from './ScrollAreaScrollbarGlimpse.vue'
15
19
  export {
16
20
  default as ScrollAreaThumb,
17
21
  type ScrollAreaThumbProps,
@@ -9,4 +9,4 @@ export interface Sizes {
9
9
  }
10
10
  }
11
11
 
12
- export type ScrollType = 'auto' | 'always' | 'scroll' | 'hover'
12
+ export type ScrollType = 'auto' | 'always' | 'scroll' | 'hover' | 'glimpse'
@@ -15,7 +15,7 @@ export interface TabsContentProps extends PrimitiveProps {
15
15
  </script>
16
16
 
17
17
  <script setup lang="ts">
18
- import { computed, onMounted, ref } from 'vue'
18
+ import { computed, onBeforeUnmount, onMounted, ref } from 'vue'
19
19
  import { Presence } from '@/Presence'
20
20
  import { Primitive } from '@/Primitive'
21
21
  import { injectTabsRootContext } from './TabsRoot.vue'
@@ -33,10 +33,15 @@ const isSelected = computed(() => props.value === rootContext.modelValue.value)
33
33
  const isMountAnimationPreventedRef = ref(isSelected.value)
34
34
 
35
35
  onMounted(() => {
36
+ rootContext.registerContent(props.value)
36
37
  requestAnimationFrame(() => {
37
38
  isMountAnimationPreventedRef.value = false
38
39
  })
39
40
  })
41
+
42
+ onBeforeUnmount(() => {
43
+ rootContext.unregisterContent(props.value)
44
+ })
40
45
  </script>
41
46
 
42
47
  <template>
@@ -14,6 +14,9 @@ export interface TabsRootContext {
14
14
  activationMode: 'automatic' | 'manual'
15
15
  baseId: string
16
16
  tabsList: Ref<HTMLElement | undefined>
17
+ contentIds: Ref<Set<StringOrNumber>>
18
+ registerContent: (value: StringOrNumber) => void
19
+ unregisterContent: (value: StringOrNumber) => void
17
20
  }
18
21
 
19
22
  export interface TabsRootProps<T extends StringOrNumber = StringOrNumber> extends PrimitiveProps {
@@ -55,7 +58,7 @@ export const [injectTabsRootContext, provideTabsRootContext]
55
58
  </script>
56
59
 
57
60
  <script setup lang="ts" generic="T extends StringOrNumber = StringOrNumber">
58
- import { ref, toRefs } from 'vue'
61
+ import { ref, shallowRef, toRefs } from 'vue'
59
62
  import { Primitive } from '@/Primitive'
60
63
 
61
64
  const props = withDefaults(defineProps<TabsRootProps<T>>(), {
@@ -82,6 +85,7 @@ const modelValue = useVModel<TabsRootProps<T>, 'modelValue', 'update:modelValue'
82
85
  })
83
86
 
84
87
  const tabsList = ref<HTMLElement>()
88
+ const contentIds = shallowRef<Set<StringOrNumber>>(new Set())
85
89
 
86
90
  provideTabsRootContext({
87
91
  modelValue,
@@ -94,6 +98,15 @@ provideTabsRootContext({
94
98
  activationMode: props.activationMode,
95
99
  baseId: useId(undefined, 'reka-tabs'),
96
100
  tabsList,
101
+ contentIds,
102
+ registerContent: (value: StringOrNumber) => {
103
+ contentIds.value = new Set([...contentIds.value, value])
104
+ },
105
+ unregisterContent: (value: StringOrNumber) => {
106
+ const newSet = new Set(contentIds.value)
107
+ newSet.delete(value)
108
+ contentIds.value = newSet
109
+ },
97
110
  })
98
111
  </script>
99
112
 
@@ -27,7 +27,7 @@ const { forwardRef } = useForwardExpose()
27
27
  const rootContext = injectTabsRootContext()
28
28
 
29
29
  const triggerId = computed(() => makeTriggerId(rootContext.baseId, props.value))
30
- const contentId = computed(() => makeContentId(rootContext.baseId, props.value))
30
+ const contentId = computed(() => rootContext.contentIds.value.has(props.value) ? makeContentId(rootContext.baseId, props.value) : undefined)
31
31
 
32
32
  const isSelected = computed(() => props.value === rootContext.modelValue.value)
33
33
  </script>
@@ -23,6 +23,7 @@ const lastKeyZero = ref(false)
23
23
  const {
24
24
  handleSegmentClick,
25
25
  handleSegmentKeydown,
26
+ handleSegmentFocusOut,
26
27
  attributes,
27
28
  } = useDateField({
28
29
  hasLeftFocus,
@@ -30,6 +31,7 @@ const {
30
31
  placeholder: rootContext.placeholder,
31
32
  hourCycle: rootContext.hourCycle,
32
33
  step: rootContext.step,
34
+ stepSnapping: rootContext.stepSnapping,
33
35
  segmentValues: rootContext.segmentValues,
34
36
  formatter: rootContext.formatter,
35
37
  part: props.part,
@@ -59,7 +61,10 @@ const isInvalid = computed(() => rootContext.isInvalid.value)
59
61
  v-on="part !== 'literal' ? {
60
62
  mousedown: handleSegmentClick,
61
63
  keydown: handleSegmentKeydown,
62
- focusout: () => { hasLeftFocus = true },
64
+ focusout: () => {
65
+ hasLeftFocus = true
66
+ handleSegmentFocusOut()
67
+ },
63
68
  focusin: (e: FocusEvent) => {
64
69
  rootContext.setFocusedElement(e.target as HTMLElement)
65
70
  },
@@ -32,6 +32,7 @@ type TimeFieldRootContext = {
32
32
  formatter: Formatter
33
33
  hourCycle: HourCycle
34
34
  step: Ref<DateStep>
35
+ stepSnapping: Ref<boolean>
35
36
  segmentValues: Ref<SegmentValueObj>
36
37
  segmentContents: Ref<{ part: SegmentPart, value: string }[]>
37
38
  elements: Ref<Set<HTMLElement>>
@@ -52,6 +53,8 @@ export interface TimeFieldRootProps extends PrimitiveProps, FormFieldProps {
52
53
  hourCycle?: HourCycle
53
54
  /** The stepping interval for the time fields. Defaults to `1`. */
54
55
  step?: DateStep
56
+ /** Whether to enforce snapping the value to the nearest step increment after input. Defaults to `false`. */
57
+ stepSnapping?: boolean
55
58
  /** The granularity to use for formatting times. Defaults to minute if a Time is provided, otherwise defaults to minute. The field will render segments for each part of the date up to and including the specified granularity */
56
59
  granularity?: 'hour' | 'minute' | 'second'
57
60
  /** Whether or not to hide the time zone segment of the field */
@@ -107,6 +110,7 @@ const props = withDefaults(defineProps<TimeFieldRootProps>(), {
107
110
  readonly: false,
108
111
  placeholder: undefined,
109
112
  isDateUnavailable: undefined,
113
+ stepSnapping: false,
110
114
  })
111
115
  const emits = defineEmits<TimeFieldRootEmits>()
112
116
  defineSlots<{
@@ -120,7 +124,7 @@ defineSlots<{
120
124
  }) => any
121
125
  }>()
122
126
 
123
- const { disabled, readonly, granularity, defaultValue, minValue, maxValue, dir: propDir, locale: propLocale } = toRefs(props)
127
+ const { disabled, readonly, granularity, defaultValue, minValue, maxValue, stepSnapping, dir: propDir, locale: propLocale } = toRefs(props)
124
128
  const locale = useLocale(propLocale)
125
129
  const dir = useDirection(propDir)
126
130
 
@@ -218,7 +222,25 @@ const allSegmentContent = computed(() => createContent({
218
222
  isTimeValue: true,
219
223
  }))
220
224
 
221
- const segmentContents = computed(() => allSegmentContent.value.arr)
225
+ const segmentContents = computed(() => {
226
+ const contents = allSegmentContent.value.arr
227
+
228
+ // Convert hour values for 12-hour display
229
+ if (props.hourCycle === 12) {
230
+ return contents.map((segment) => {
231
+ if (segment.part === 'hour' && 'hour' in segmentValues.value) {
232
+ const hour = segmentValues.value.hour
233
+ if (hour !== null) {
234
+ const displayHour = hour === 0 ? 12 : hour > 12 ? hour - 12 : hour
235
+ return { ...segment, value: displayHour.toString() }
236
+ }
237
+ }
238
+ return segment
239
+ })
240
+ }
241
+
242
+ return contents
243
+ })
222
244
 
223
245
  const editableSegmentContents = computed(() => segmentContents.value.filter(({ part }) => part !== 'literal'))
224
246
 
@@ -298,6 +320,7 @@ provideTimeFieldRootContext({
298
320
  formatter,
299
321
  hourCycle: props.hourCycle,
300
322
  step,
323
+ stepSnapping,
301
324
  readonly,
302
325
  segmentValues,
303
326
  isInvalid,
@@ -4,13 +4,13 @@ import { createContext, getActiveElement, useDirection, useSelectionBehavior, us
4
4
  import { flatten } from './utils'
5
5
 
6
6
  export interface TreeRootProps<T = Record<string, any>, U extends Record<string, any> = Record<string, any>, M extends boolean = false> extends PrimitiveProps {
7
- /** The controlled value of the tree. Can be binded with with `v-model`. */
7
+ /** The controlled value of the tree. Can be binded with `v-model`. */
8
8
  modelValue?: M extends true ? U[] : U
9
9
  /** The value of the tree when initially rendered. Use when you do not need to control the state of the tree */
10
10
  defaultValue?: M extends true ? U[] : U
11
11
  /** List of items */
12
12
  items?: T[]
13
- /** The controlled value of the expanded item. Can be binded with with `v-model`. */
13
+ /** The controlled value of the expanded item. Can be binded with `v-model`. */
14
14
  expanded?: string[]
15
15
  /** The value of the expanded tree when initially rendered. Use when you do not need to control the state of the expanded tree */
16
16
  defaultExpanded?: string[]
@@ -5,12 +5,14 @@
5
5
  import type { DateValue, DayOfWeek } from '@internationalized/date'
6
6
  import type { Grid } from './types'
7
7
  import type { DateRange } from '@/shared'
8
- import { CalendarDate, endOfMonth, endOfYear, getDayOfWeek, startOfMonth, startOfYear } from '@internationalized/date'
8
+ import { CalendarDate, endOfMonth, endOfYear, getDayOfWeek, startOfMonth, startOfWeek, startOfYear } from '@internationalized/date'
9
9
  import { getDaysInMonth, getLastFirstDayOfWeek, getNextLastDayOfWeek } from './comparators'
10
10
  import { chunk } from './utils'
11
11
 
12
12
  export type WeekDayFormat = 'narrow' | 'short' | 'long'
13
13
 
14
+ export type WeekStartsOn = 0 | 1 | 2 | 3 | 4 | 5 | 6
15
+
14
16
  export type CreateSelectProps = {
15
17
  /**
16
18
  * The date object representing the date (usually the first day of the month/year).
@@ -27,7 +29,7 @@ export type CreateMonthProps = {
27
29
  /**
28
30
  * The day of the week to start the calendar on (0 for Sunday, 1 for Monday, etc.).
29
31
  */
30
- weekStartsOn: number
32
+ weekStartsOn: WeekStartsOn
31
33
 
32
34
  /**
33
35
  * Whether to always render 6 weeks in the calendar, even if the month doesn't
@@ -219,24 +221,46 @@ export function createDateRange({ start, end }: DateRange): DateValue[] {
219
221
  return dates
220
222
  }
221
223
 
224
+ /**
225
+ * It's better to use `getWeekStart` from `@internationalized/date`,
226
+ * but sadly it is not yet exported from the package.
227
+ * And the `Intl.Locale` API is not supported well enough yet.
228
+ */
229
+ export function getWeekStartsOn(locale: string): WeekStartsOn {
230
+ // Jan 6, 2025 is a Monday (ISO day = 1)
231
+ const monday = new CalendarDate(2025, 1, 6)
232
+ const dayOfWeek = getDayOfWeek(monday, locale)
233
+ // dayOfWeek tells us Monday's position in the locale's week (0-indexed)
234
+ // If Monday is position 0 → week starts Monday (1)
235
+ // If Monday is position 1 → week starts Sunday (0)
236
+ return (1 - dayOfWeek + 7) % 7 as WeekStartsOn
237
+ }
238
+
222
239
  /**
223
240
  * Returns the locale-specific week number
224
241
  */
225
242
  export function getWeekNumber(date: DateValue, locale: string = 'en-US', firstDayOfWeek?: DayOfWeek): number {
226
- const firstDayOfYear = new CalendarDate(date.year, 1, 1)
227
-
228
- const firstDayOfYearWeekday = getDayOfWeek(firstDayOfYear, locale, firstDayOfWeek)
229
-
230
- const firstWeekStart = firstDayOfYear.subtract({ days: firstDayOfYearWeekday })
231
-
232
- // If date is before the first week start It belongs to the last week of the previous year
233
- if (date.compare(firstWeekStart) < 0) {
234
- const prevYearDate = new CalendarDate(date.year - 1, 12, 31)
235
- return getWeekNumber(prevYearDate, locale, firstDayOfWeek)
236
- }
237
-
238
- const days = getDaysBetween(firstWeekStart, date)
239
-
240
- // Week number is days divided by 7 plus 1
241
- return Math.floor(days.length / 7) + 1
243
+ const jan1 = new CalendarDate(date.year, 1, 1)
244
+
245
+ // Detect ISO locale by comparing JS day of week with locale day of week
246
+ const usesISOWeek = jan1.toDate('UTC').getUTCDay() !== getDayOfWeek(jan1, locale)
247
+ const weekStartsOn = firstDayOfWeek ?? (usesISOWeek ? 'mon' : 'sun')
248
+ const firstWeekContainsDate = usesISOWeek ? 4 : 1
249
+
250
+ // Find the "deciding day" - its year determines which year's week numbering to use
251
+ const dayOfWeek = getDayOfWeek(date, locale, weekStartsOn)
252
+ const decidingDay = date.add({ days: 7 - firstWeekContainsDate - dayOfWeek })
253
+ const weekYear = decidingDay.year
254
+
255
+ // Calculate week number from week 1 start
256
+ const week1Ref = new CalendarDate(weekYear, 1, firstWeekContainsDate)
257
+ const week1Start = startOfWeek(week1Ref, locale, weekStartsOn)
258
+ const currentWeekStart = startOfWeek(date, locale, weekStartsOn)
259
+
260
+ const MS_PER_WEEK = 7 * 24 * 60 * 60 * 1000
261
+ const daysDiff = Math.round(
262
+ (currentWeekStart.toDate('UTC').getTime() - week1Start.toDate('UTC').getTime())
263
+ / MS_PER_WEEK,
264
+ )
265
+ return daysDiff + 1
242
266
  }
@@ -143,7 +143,13 @@ export function getLastFirstDayOfWeek<T extends DateValue = DateValue>(
143
143
  firstDayOfWeek: number,
144
144
  locale: string,
145
145
  ): T {
146
- const day = getDayOfWeek(date, locale)
146
+ /**
147
+ * "firstDayOfWeek" is fixed to 0(Sunday) to avoid confusion regarding locales.
148
+ * This also aligns with other date libraries, e.g., date-fns.
149
+ *
150
+ * #see https://github.com/unovue/reka-ui/issues/2157
151
+ */
152
+ const day = getDayOfWeek(date, locale, 'sun')
147
153
 
148
154
  if (firstDayOfWeek > day)
149
155
  return date.subtract({ days: day + 7 - firstDayOfWeek }) as T
@@ -159,7 +165,14 @@ export function getNextLastDayOfWeek<T extends DateValue = DateValue>(
159
165
  firstDayOfWeek: number,
160
166
  locale: string,
161
167
  ): T {
162
- const day = getDayOfWeek(date, locale)
168
+ /**
169
+ * "firstDayOfWeek" is fixed to 0(Sunday) to avoid confusion regarding locales.
170
+ * This also aligns with other date libraries, e.g., date-fns.
171
+ *
172
+ * #see https://github.com/unovue/reka-ui/issues/2157
173
+ */
174
+ const day = getDayOfWeek(date, locale, 'sun')
175
+
163
176
  const lastDayOfWeek = firstDayOfWeek === 0 ? 6 : firstDayOfWeek - 1
164
177
 
165
178
  if (day === lastDayOfWeek)
package/src/index.ts CHANGED
@@ -42,6 +42,7 @@ export {
42
42
  type DateValue,
43
43
  type Formatter,
44
44
  type SegmentPart,
45
+ type TimeValue,
45
46
  useBodyScrollLock,
46
47
  useDateFormatter,
47
48
  useDirection,
@@ -197,6 +197,16 @@ function createContentArr(props: CreateContentArrProps) {
197
197
  if (segment.part === 'timeZoneName' && (!isZonedDateTime(props.dateRef) || hideTimeZone))
198
198
  return false
199
199
 
200
+ // In some locales (e.g., zh-TW), the time zone is represented with square brackets.
201
+ // We also filter out these literals that are just brackets.
202
+ // @see https://github.com/unovue/reka-ui/issues/1670
203
+ if (
204
+ (!isZonedDateTime(props.dateRef) || hideTimeZone)
205
+ && segment.part === 'literal' && ['[', ']'].includes(segment.value.trim())
206
+ ) {
207
+ return false
208
+ }
209
+
200
210
  return true
201
211
  })
202
212