vuetify 3.9.0-beta.0 → 3.9.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 (337) hide show
  1. package/dist/_component-variables-labs.sass +1 -0
  2. package/dist/json/attributes.json +3590 -3502
  3. package/dist/json/importMap-labs.json +16 -12
  4. package/dist/json/importMap.json +186 -186
  5. package/dist/json/tags.json +31 -4
  6. package/dist/json/web-types.json +6626 -6392
  7. package/dist/vuetify-labs.cjs +1082 -195
  8. package/dist/vuetify-labs.css +4654 -4339
  9. package/dist/vuetify-labs.d.ts +2027 -493
  10. package/dist/vuetify-labs.esm.js +1082 -196
  11. package/dist/vuetify-labs.esm.js.map +1 -1
  12. package/dist/vuetify-labs.js +1082 -195
  13. package/dist/vuetify-labs.min.css +2 -2
  14. package/dist/vuetify.cjs +663 -170
  15. package/dist/vuetify.cjs.map +1 -1
  16. package/dist/vuetify.css +4744 -4671
  17. package/dist/vuetify.d.ts +1575 -267
  18. package/dist/vuetify.esm.js +663 -171
  19. package/dist/vuetify.esm.js.map +1 -1
  20. package/dist/vuetify.js +663 -170
  21. package/dist/vuetify.js.map +1 -1
  22. package/dist/vuetify.min.css +2 -2
  23. package/dist/vuetify.min.js +1182 -1126
  24. package/dist/vuetify.min.js.map +1 -1
  25. package/lib/components/VAutocomplete/VAutocomplete.d.ts +39 -14
  26. package/lib/components/VAutocomplete/VAutocomplete.js +2 -2
  27. package/lib/components/VAutocomplete/VAutocomplete.js.map +1 -1
  28. package/lib/components/VBtn/VBtn.sass +3 -1
  29. package/lib/components/VCarousel/VCarousel.css +0 -1
  30. package/lib/components/VCarousel/VCarousel.js +1 -0
  31. package/lib/components/VCarousel/VCarousel.js.map +1 -1
  32. package/lib/components/VCarousel/VCarousel.sass +0 -1
  33. package/lib/components/VCombobox/VCombobox.d.ts +39 -14
  34. package/lib/components/VCombobox/VCombobox.js +2 -2
  35. package/lib/components/VCombobox/VCombobox.js.map +1 -1
  36. package/lib/components/VDataIterator/composables/items.d.ts +2 -1
  37. package/lib/components/VDataIterator/composables/items.js.map +1 -1
  38. package/lib/components/VDataTable/VDataTable.css +12 -1
  39. package/lib/components/VDataTable/VDataTable.d.ts +20 -38
  40. package/lib/components/VDataTable/VDataTable.sass +12 -2
  41. package/lib/components/VDataTable/VDataTableColumn.d.ts +9 -3
  42. package/lib/components/VDataTable/VDataTableColumn.js +12 -4
  43. package/lib/components/VDataTable/VDataTableColumn.js.map +1 -1
  44. package/lib/components/VDataTable/VDataTableHeaders.d.ts +0 -13
  45. package/lib/components/VDataTable/VDataTableHeaders.js +10 -9
  46. package/lib/components/VDataTable/VDataTableHeaders.js.map +1 -1
  47. package/lib/components/VDataTable/VDataTableRow.js +2 -0
  48. package/lib/components/VDataTable/VDataTableRow.js.map +1 -1
  49. package/lib/components/VDataTable/VDataTableServer.d.ts +10 -23
  50. package/lib/components/VDataTable/VDataTableVirtual.d.ts +10 -23
  51. package/lib/components/VDataTable/composables/headers.d.ts +22 -14
  52. package/lib/components/VDataTable/composables/headers.js +51 -22
  53. package/lib/components/VDataTable/composables/headers.js.map +1 -1
  54. package/lib/components/VDataTable/composables/sort.js +2 -1
  55. package/lib/components/VDataTable/composables/sort.js.map +1 -1
  56. package/lib/components/VDataTable/types.d.ts +4 -2
  57. package/lib/components/VDataTable/types.js.map +1 -1
  58. package/lib/components/VDatePicker/VDatePicker.js +2 -1
  59. package/lib/components/VDatePicker/VDatePicker.js.map +1 -1
  60. package/lib/components/VDatePicker/VDatePickerControls.css +1 -0
  61. package/lib/components/VDatePicker/VDatePickerControls.sass +1 -0
  62. package/lib/components/VDatePicker/VDatePickerMonth.css +3 -8
  63. package/lib/components/VDatePicker/VDatePickerMonth.js +7 -3
  64. package/lib/components/VDatePicker/VDatePickerMonth.js.map +1 -1
  65. package/lib/components/VDatePicker/VDatePickerMonth.sass +3 -8
  66. package/lib/components/VField/VField.js +2 -10
  67. package/lib/components/VField/VField.js.map +1 -1
  68. package/lib/components/VKbd/VKbd.css +14 -5
  69. package/lib/components/VKbd/VKbd.js.map +1 -1
  70. package/lib/components/VKbd/VKbd.scss +26 -0
  71. package/lib/components/VKbd/_variables.scss +12 -6
  72. package/lib/components/VKbd/index.js.map +1 -1
  73. package/lib/components/VList/VList.d.ts +24 -27
  74. package/lib/components/VList/VList.js +1 -5
  75. package/lib/components/VList/VList.js.map +1 -1
  76. package/lib/components/VList/VListGroup.d.ts +13 -0
  77. package/lib/components/VList/VListGroup.js +2 -1
  78. package/lib/components/VList/VListGroup.js.map +1 -1
  79. package/lib/components/VList/VListItem.d.ts +6 -3
  80. package/lib/components/VList/VListItem.js +1 -1
  81. package/lib/components/VList/VListItem.js.map +1 -1
  82. package/lib/components/VNumberInput/VNumberInput.js +4 -10
  83. package/lib/components/VNumberInput/VNumberInput.js.map +1 -1
  84. package/lib/components/VNumberInput/hold.js +4 -0
  85. package/lib/components/VNumberInput/hold.js.map +1 -1
  86. package/lib/components/VOtpInput/VOtpInput.js +17 -14
  87. package/lib/components/VOtpInput/VOtpInput.js.map +1 -1
  88. package/lib/components/VOverlay/locationStrategies.js +1 -1
  89. package/lib/components/VOverlay/locationStrategies.js.map +1 -1
  90. package/lib/components/VSelect/VSelect.d.ts +58 -22
  91. package/lib/components/VSelect/VSelect.js +2 -2
  92. package/lib/components/VSelect/VSelect.js.map +1 -1
  93. package/lib/components/VTextField/VTextField.js +1 -1
  94. package/lib/components/VTextField/VTextField.js.map +1 -1
  95. package/lib/components/VTimePicker/VTimePicker.css +1 -6
  96. package/lib/components/VTimePicker/VTimePicker.sass +1 -6
  97. package/lib/components/VTimePicker/VTimePickerClock.css +5 -4
  98. package/lib/components/VTimePicker/VTimePickerClock.sass +5 -4
  99. package/lib/components/VTimePicker/VTimePickerControls.css +2 -1
  100. package/lib/components/VTimePicker/VTimePickerControls.sass +2 -3
  101. package/lib/components/VTreeview/VTreeview.d.ts +235 -188
  102. package/lib/components/VTreeview/VTreeview.js +13 -12
  103. package/lib/components/VTreeview/VTreeview.js.map +1 -1
  104. package/lib/components/VTreeview/VTreeviewChildren.d.ts +94 -10
  105. package/lib/components/VTreeview/VTreeviewChildren.js +61 -17
  106. package/lib/components/VTreeview/VTreeviewChildren.js.map +1 -1
  107. package/lib/components/VTreeview/VTreeviewGroup.d.ts +13 -0
  108. package/lib/components/VTreeview/VTreeviewItem.css +57 -0
  109. package/lib/components/VTreeview/VTreeviewItem.d.ts +1334 -97
  110. package/lib/components/VTreeview/VTreeviewItem.js +25 -16
  111. package/lib/components/VTreeview/VTreeviewItem.js.map +1 -1
  112. package/lib/components/VTreeview/VTreeviewItem.sass +60 -0
  113. package/lib/components/VTreeview/_variables.scss +15 -0
  114. package/lib/composables/calendar.d.ts +2 -1
  115. package/lib/composables/calendar.js +8 -8
  116. package/lib/composables/calendar.js.map +1 -1
  117. package/lib/composables/date/adapters/vuetify.js +1 -1
  118. package/lib/composables/date/adapters/vuetify.js.map +1 -1
  119. package/lib/composables/filter.d.ts +1 -0
  120. package/lib/composables/filter.js +1 -1
  121. package/lib/composables/filter.js.map +1 -1
  122. package/lib/composables/hotkey/hotkey-parsing.d.ts +15 -0
  123. package/lib/composables/hotkey/hotkey-parsing.js +154 -0
  124. package/lib/composables/hotkey/hotkey-parsing.js.map +1 -0
  125. package/lib/composables/hotkey/hotkey.d.ts +9 -0
  126. package/lib/composables/{hotkey.js → hotkey/hotkey.js} +31 -39
  127. package/lib/composables/hotkey/hotkey.js.map +1 -0
  128. package/lib/composables/hotkey/index.d.ts +1 -0
  129. package/lib/composables/hotkey/index.js +2 -0
  130. package/lib/composables/hotkey/index.js.map +1 -0
  131. package/lib/composables/hotkey/key-aliases.d.ts +14 -0
  132. package/lib/composables/hotkey/key-aliases.js +38 -0
  133. package/lib/composables/hotkey/key-aliases.js.map +1 -0
  134. package/lib/composables/icons.d.ts +11 -0
  135. package/lib/composables/icons.js.map +1 -1
  136. package/lib/composables/index.d.ts +1 -0
  137. package/lib/composables/index.js +1 -0
  138. package/lib/composables/index.js.map +1 -1
  139. package/lib/composables/list-items.d.ts +14 -1
  140. package/lib/composables/list-items.js +9 -3
  141. package/lib/composables/list-items.js.map +1 -1
  142. package/lib/composables/nested/nested.d.ts +7 -4
  143. package/lib/composables/nested/nested.js +24 -14
  144. package/lib/composables/nested/nested.js.map +1 -1
  145. package/lib/composables/nested/selectStrategies.d.ts +2 -1
  146. package/lib/composables/nested/selectStrategies.js +22 -11
  147. package/lib/composables/nested/selectStrategies.js.map +1 -1
  148. package/lib/composables/virtual.js +1 -1
  149. package/lib/composables/virtual.js.map +1 -1
  150. package/lib/entry-bundler.js +1 -1
  151. package/lib/entry-bundler.js.map +1 -1
  152. package/lib/framework.d.ts +91 -66
  153. package/lib/framework.js +1 -1
  154. package/lib/framework.js.map +1 -1
  155. package/lib/iconsets/fa.js +12 -1
  156. package/lib/iconsets/fa.js.map +1 -1
  157. package/lib/iconsets/fa4.js +12 -1
  158. package/lib/iconsets/fa4.js.map +1 -1
  159. package/lib/iconsets/md.js +12 -1
  160. package/lib/iconsets/md.js.map +1 -1
  161. package/lib/iconsets/mdi-svg.js +12 -1
  162. package/lib/iconsets/mdi-svg.js.map +1 -1
  163. package/lib/iconsets/mdi.js +12 -1
  164. package/lib/iconsets/mdi.js.map +1 -1
  165. package/lib/labs/VCalendar/VCalendar.d.ts +33 -33
  166. package/lib/labs/VCalendar/VCalendar.js +10 -10
  167. package/lib/labs/VCalendar/VCalendar.js.map +1 -1
  168. package/lib/labs/VCalendar/VCalendarDay.d.ts +33 -33
  169. package/lib/labs/VCalendar/VCalendarDay.js +1 -1
  170. package/lib/labs/VCalendar/VCalendarDay.js.map +1 -1
  171. package/lib/labs/VCalendar/VCalendarInterval.d.ts +36 -36
  172. package/lib/labs/VCalendar/VCalendarInterval.js +9 -9
  173. package/lib/labs/VCalendar/VCalendarInterval.js.map +1 -1
  174. package/lib/labs/VCalendar/VCalendarIntervalEvent.d.ts +12 -12
  175. package/lib/labs/VCalendar/VCalendarIntervalEvent.js +1 -1
  176. package/lib/labs/VCalendar/VCalendarIntervalEvent.js.map +1 -1
  177. package/lib/labs/VCalendar/VCalendarMonthDay.d.ts +36 -36
  178. package/lib/labs/VCalendar/VCalendarMonthDay.js +4 -4
  179. package/lib/labs/VCalendar/VCalendarMonthDay.js.map +1 -1
  180. package/lib/labs/VHotkey/VHotkey.css +242 -0
  181. package/lib/labs/VHotkey/VHotkey.d.ts +387 -0
  182. package/lib/labs/VHotkey/VHotkey.js +432 -0
  183. package/lib/labs/VHotkey/VHotkey.js.map +1 -0
  184. package/lib/labs/VHotkey/VHotkey.scss +253 -0
  185. package/lib/labs/VHotkey/_variables.scss +43 -0
  186. package/lib/labs/VHotkey/index.d.ts +1 -0
  187. package/lib/labs/VHotkey/index.js +2 -0
  188. package/lib/labs/VHotkey/index.js.map +1 -0
  189. package/lib/labs/VIconBtn/VIconBtn.js +1 -0
  190. package/lib/labs/VIconBtn/VIconBtn.js.map +1 -1
  191. package/lib/labs/VPicker/VPicker.css +4 -0
  192. package/lib/labs/VPicker/VPicker.sass +4 -0
  193. package/lib/labs/components.d.ts +1 -0
  194. package/lib/labs/components.js +1 -0
  195. package/lib/labs/components.js.map +1 -1
  196. package/lib/locale/af.d.ts +18 -0
  197. package/lib/locale/af.js +18 -0
  198. package/lib/locale/af.js.map +1 -1
  199. package/lib/locale/ar.d.ts +18 -0
  200. package/lib/locale/ar.js +18 -0
  201. package/lib/locale/ar.js.map +1 -1
  202. package/lib/locale/az.d.ts +18 -0
  203. package/lib/locale/az.js +18 -0
  204. package/lib/locale/az.js.map +1 -1
  205. package/lib/locale/bg.d.ts +18 -0
  206. package/lib/locale/bg.js +18 -0
  207. package/lib/locale/bg.js.map +1 -1
  208. package/lib/locale/ca.d.ts +18 -0
  209. package/lib/locale/ca.js +18 -0
  210. package/lib/locale/ca.js.map +1 -1
  211. package/lib/locale/ckb.d.ts +18 -0
  212. package/lib/locale/ckb.js +18 -0
  213. package/lib/locale/ckb.js.map +1 -1
  214. package/lib/locale/cs.d.ts +18 -0
  215. package/lib/locale/cs.js +18 -0
  216. package/lib/locale/cs.js.map +1 -1
  217. package/lib/locale/da.d.ts +18 -0
  218. package/lib/locale/da.js +18 -0
  219. package/lib/locale/da.js.map +1 -1
  220. package/lib/locale/de.d.ts +18 -0
  221. package/lib/locale/de.js +18 -0
  222. package/lib/locale/de.js.map +1 -1
  223. package/lib/locale/el.d.ts +18 -0
  224. package/lib/locale/el.js +18 -0
  225. package/lib/locale/el.js.map +1 -1
  226. package/lib/locale/en.d.ts +18 -0
  227. package/lib/locale/en.js +18 -0
  228. package/lib/locale/en.js.map +1 -1
  229. package/lib/locale/es.d.ts +18 -0
  230. package/lib/locale/es.js +18 -0
  231. package/lib/locale/es.js.map +1 -1
  232. package/lib/locale/et.d.ts +18 -0
  233. package/lib/locale/et.js +18 -0
  234. package/lib/locale/et.js.map +1 -1
  235. package/lib/locale/fa.d.ts +18 -0
  236. package/lib/locale/fa.js +18 -0
  237. package/lib/locale/fa.js.map +1 -1
  238. package/lib/locale/fi.d.ts +18 -0
  239. package/lib/locale/fi.js +18 -0
  240. package/lib/locale/fi.js.map +1 -1
  241. package/lib/locale/fr.d.ts +18 -0
  242. package/lib/locale/fr.js +18 -0
  243. package/lib/locale/fr.js.map +1 -1
  244. package/lib/locale/he.d.ts +18 -0
  245. package/lib/locale/he.js +18 -0
  246. package/lib/locale/he.js.map +1 -1
  247. package/lib/locale/hr.d.ts +18 -0
  248. package/lib/locale/hr.js +18 -0
  249. package/lib/locale/hr.js.map +1 -1
  250. package/lib/locale/hu.d.ts +18 -0
  251. package/lib/locale/hu.js +18 -0
  252. package/lib/locale/hu.js.map +1 -1
  253. package/lib/locale/id.d.ts +18 -0
  254. package/lib/locale/id.js +18 -0
  255. package/lib/locale/id.js.map +1 -1
  256. package/lib/locale/it.d.ts +18 -0
  257. package/lib/locale/it.js +18 -0
  258. package/lib/locale/it.js.map +1 -1
  259. package/lib/locale/ja.d.ts +18 -0
  260. package/lib/locale/ja.js +18 -0
  261. package/lib/locale/ja.js.map +1 -1
  262. package/lib/locale/km.d.ts +18 -0
  263. package/lib/locale/km.js +18 -0
  264. package/lib/locale/km.js.map +1 -1
  265. package/lib/locale/ko.d.ts +18 -0
  266. package/lib/locale/ko.js +18 -0
  267. package/lib/locale/ko.js.map +1 -1
  268. package/lib/locale/lt.d.ts +18 -0
  269. package/lib/locale/lt.js +18 -0
  270. package/lib/locale/lt.js.map +1 -1
  271. package/lib/locale/lv.d.ts +18 -0
  272. package/lib/locale/lv.js +18 -0
  273. package/lib/locale/lv.js.map +1 -1
  274. package/lib/locale/nl.d.ts +18 -0
  275. package/lib/locale/nl.js +18 -0
  276. package/lib/locale/nl.js.map +1 -1
  277. package/lib/locale/no.d.ts +18 -0
  278. package/lib/locale/no.js +18 -0
  279. package/lib/locale/no.js.map +1 -1
  280. package/lib/locale/pl.d.ts +18 -0
  281. package/lib/locale/pl.js +18 -0
  282. package/lib/locale/pl.js.map +1 -1
  283. package/lib/locale/pt.d.ts +18 -0
  284. package/lib/locale/pt.js +18 -0
  285. package/lib/locale/pt.js.map +1 -1
  286. package/lib/locale/ro.d.ts +18 -0
  287. package/lib/locale/ro.js +18 -0
  288. package/lib/locale/ro.js.map +1 -1
  289. package/lib/locale/ru.d.ts +18 -0
  290. package/lib/locale/ru.js +18 -0
  291. package/lib/locale/ru.js.map +1 -1
  292. package/lib/locale/sk.d.ts +18 -0
  293. package/lib/locale/sk.js +18 -0
  294. package/lib/locale/sk.js.map +1 -1
  295. package/lib/locale/sl.d.ts +18 -0
  296. package/lib/locale/sl.js +18 -0
  297. package/lib/locale/sl.js.map +1 -1
  298. package/lib/locale/sr-Cyrl.d.ts +18 -0
  299. package/lib/locale/sr-Cyrl.js +18 -0
  300. package/lib/locale/sr-Cyrl.js.map +1 -1
  301. package/lib/locale/sr-Latn.d.ts +18 -0
  302. package/lib/locale/sr-Latn.js +18 -0
  303. package/lib/locale/sr-Latn.js.map +1 -1
  304. package/lib/locale/sv.d.ts +18 -0
  305. package/lib/locale/sv.js +18 -0
  306. package/lib/locale/sv.js.map +1 -1
  307. package/lib/locale/th.d.ts +18 -0
  308. package/lib/locale/th.js +18 -0
  309. package/lib/locale/th.js.map +1 -1
  310. package/lib/locale/tr.d.ts +18 -0
  311. package/lib/locale/tr.js +18 -0
  312. package/lib/locale/tr.js.map +1 -1
  313. package/lib/locale/uk.d.ts +18 -0
  314. package/lib/locale/uk.js +18 -0
  315. package/lib/locale/uk.js.map +1 -1
  316. package/lib/locale/vi.d.ts +18 -0
  317. package/lib/locale/vi.js +18 -0
  318. package/lib/locale/vi.js.map +1 -1
  319. package/lib/locale/zh-Hans.d.ts +18 -0
  320. package/lib/locale/zh-Hans.js +18 -0
  321. package/lib/locale/zh-Hans.js.map +1 -1
  322. package/lib/locale/zh-Hant.d.ts +18 -0
  323. package/lib/locale/zh-Hant.js +18 -0
  324. package/lib/locale/zh-Hant.js.map +1 -1
  325. package/lib/util/helpers.d.ts +3 -0
  326. package/lib/util/helpers.js +4 -0
  327. package/lib/util/helpers.js.map +1 -1
  328. package/lib/util/indentLines.d.ts +17 -0
  329. package/lib/util/indentLines.js +34 -0
  330. package/lib/util/indentLines.js.map +1 -0
  331. package/lib/util/index.d.ts +1 -0
  332. package/lib/util/index.js +1 -0
  333. package/lib/util/index.js.map +1 -1
  334. package/package.json +2 -2
  335. package/lib/components/VKbd/VKbd.sass +0 -15
  336. package/lib/composables/hotkey.d.ts +0 -9
  337. package/lib/composables/hotkey.js.map +0 -1
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * Vuetify v3.9.0-beta.0
2
+ * Vuetify v3.9.0
3
3
  * Forged by John Leider
4
4
  * Released under the MIT License.
5
5
  */
@@ -546,6 +546,10 @@ function ensureValidVNode(vnodes) {
546
546
  return child.type !== Fragment || ensureValidVNode(child.children);
547
547
  }) ? vnodes : null;
548
548
  }
549
+ function renderSlot(slot, props, fallback) {
550
+ // TODO: check if slot returns elements: #18308
551
+ return slot?.(props) ?? fallback?.(props);
552
+ }
549
553
  function defer(timeout, cb) {
550
554
  if (!IN_BROWSER || timeout === 0) {
551
555
  cb();
@@ -1620,6 +1624,40 @@ function isPotentiallyScrollable(el) {
1620
1624
  return ['scroll', 'auto'].includes(style.overflowY);
1621
1625
  }
1622
1626
 
1627
+ // Types
1628
+
1629
+ function getIndentLines(_ref) {
1630
+ let {
1631
+ depth,
1632
+ isLast,
1633
+ isLastGroup,
1634
+ leafLinks,
1635
+ separateRoots,
1636
+ parentIndentLines,
1637
+ variant
1638
+ } = _ref;
1639
+ if (!parentIndentLines || !depth) {
1640
+ return {
1641
+ leaf: undefined,
1642
+ node: undefined,
1643
+ children: parentIndentLines
1644
+ };
1645
+ }
1646
+ if (variant === 'simple') {
1647
+ return {
1648
+ leaf: [...parentIndentLines, 'line'],
1649
+ node: [...parentIndentLines, 'line'],
1650
+ children: [...parentIndentLines, 'line']
1651
+ };
1652
+ }
1653
+ const isLastLeaf = isLast && (!isLastGroup || separateRoots || depth > 1);
1654
+ return {
1655
+ leaf: [...parentIndentLines, isLastLeaf ? 'last-leaf' : 'leaf', ...(leafLinks ? ['leaf-link'] : [])],
1656
+ node: [...parentIndentLines, isLastLeaf ? 'last-leaf' : 'leaf'],
1657
+ children: [...parentIndentLines, isLastLeaf ? 'none' : 'line']
1658
+ };
1659
+ }
1660
+
1623
1661
  function isFixedPosition(el) {
1624
1662
  while (el) {
1625
1663
  if (window.getComputedStyle(el).position === 'fixed') {
@@ -2141,6 +2179,24 @@ var en = {
2141
2179
  exclude: 'The {0} character is not allowed',
2142
2180
  notEmpty: 'Please choose at least one value',
2143
2181
  pattern: 'Invalid format'
2182
+ },
2183
+ hotkey: {
2184
+ then: 'then',
2185
+ ctrl: 'Ctrl',
2186
+ command: 'Command',
2187
+ space: 'Space',
2188
+ shift: 'Shift',
2189
+ alt: 'Alt',
2190
+ enter: 'Enter',
2191
+ escape: 'Escape',
2192
+ upArrow: 'Up Arrow',
2193
+ downArrow: 'Down Arrow',
2194
+ leftArrow: 'Left Arrow',
2195
+ rightArrow: 'Right Arrow',
2196
+ backspace: 'Backspace',
2197
+ option: 'Option',
2198
+ plus: 'plus',
2199
+ shortcut: 'Keyboard shortcut: {0}'
2144
2200
  }
2145
2201
  };
2146
2202
 
@@ -4651,7 +4707,18 @@ const aliases = {
4651
4707
  treeviewExpand: 'mdi-menu-right',
4652
4708
  eyeDropper: 'mdi-eyedropper',
4653
4709
  upload: 'mdi-cloud-upload',
4654
- color: 'mdi-palette'
4710
+ color: 'mdi-palette',
4711
+ command: 'mdi-apple-keyboard-command',
4712
+ ctrl: 'mdi-apple-keyboard-control',
4713
+ space: 'mdi-keyboard-space',
4714
+ shift: 'mdi-apple-keyboard-shift',
4715
+ alt: 'mdi-apple-keyboard-option',
4716
+ enter: 'mdi-keyboard-return',
4717
+ arrowup: 'mdi-arrow-up',
4718
+ arrowdown: 'mdi-arrow-down',
4719
+ arrowleft: 'mdi-arrow-left',
4720
+ arrowright: 'mdi-arrow-right',
4721
+ backspace: 'mdi-backspace'
4655
4722
  };
4656
4723
  const mdi = {
4657
4724
  // Not using mergeProps here, functional components merge props by default (?)
@@ -8793,7 +8860,7 @@ const independentSelectStrategy = mandatory => {
8793
8860
  selected.set(id, value ? 'on' : 'off');
8794
8861
  return selected;
8795
8862
  },
8796
- in: (v, children, parents) => {
8863
+ in: (v, children, parents, disabled) => {
8797
8864
  const map = new Map();
8798
8865
  for (const id of v || []) {
8799
8866
  strategy.select({
@@ -8801,7 +8868,8 @@ const independentSelectStrategy = mandatory => {
8801
8868
  value: true,
8802
8869
  selected: map,
8803
8870
  children,
8804
- parents
8871
+ parents,
8872
+ disabled
8805
8873
  });
8806
8874
  }
8807
8875
  return map;
@@ -8833,9 +8901,9 @@ const independentSingleSelectStrategy = mandatory => {
8833
8901
  selected: singleSelected
8834
8902
  });
8835
8903
  },
8836
- in: (v, children, parents) => {
8904
+ in: (v, children, parents, disabled) => {
8837
8905
  if (v?.length) {
8838
- return parentStrategy.in(v.slice(0, 1), children, parents);
8906
+ return parentStrategy.in(v.slice(0, 1), children, parents, disabled);
8839
8907
  }
8840
8908
  return new Map();
8841
8909
  },
@@ -8901,23 +8969,32 @@ const classicSelectStrategy = mandatory => {
8901
8969
  value,
8902
8970
  selected,
8903
8971
  children,
8904
- parents
8972
+ parents,
8973
+ disabled
8905
8974
  } = _ref6;
8906
8975
  id = toRaw(id);
8907
8976
  const original = new Map(selected);
8908
8977
  const items = [id];
8909
8978
  while (items.length) {
8910
8979
  const item = items.shift();
8911
- selected.set(toRaw(item), value ? 'on' : 'off');
8980
+ if (!disabled.has(item)) {
8981
+ selected.set(toRaw(item), value ? 'on' : 'off');
8982
+ }
8912
8983
  if (children.has(item)) {
8913
8984
  items.push(...children.get(item));
8914
8985
  }
8915
8986
  }
8916
8987
  let parent = toRaw(parents.get(id));
8917
8988
  while (parent) {
8918
- const childrenIds = children.get(parent);
8919
- const everySelected = childrenIds.every(cid => selected.get(toRaw(cid)) === 'on');
8920
- const noneSelected = childrenIds.every(cid => !selected.has(toRaw(cid)) || selected.get(toRaw(cid)) === 'off');
8989
+ let everySelected = true;
8990
+ let noneSelected = true;
8991
+ for (const child of children.get(parent)) {
8992
+ const cid = toRaw(child);
8993
+ if (disabled.has(cid)) continue;
8994
+ if (selected.get(cid) !== 'on') everySelected = false;
8995
+ if (selected.has(cid) && selected.get(cid) !== 'off') noneSelected = false;
8996
+ if (!everySelected && !noneSelected) break;
8997
+ }
8921
8998
  selected.set(parent, everySelected ? 'on' : noneSelected ? 'off' : 'indeterminate');
8922
8999
  parent = toRaw(parents.get(parent));
8923
9000
  }
@@ -8934,7 +9011,7 @@ const classicSelectStrategy = mandatory => {
8934
9011
  }
8935
9012
  return selected;
8936
9013
  },
8937
- in: (v, children, parents) => {
9014
+ in: (v, children, parents, disabled) => {
8938
9015
  let map = new Map();
8939
9016
  for (const id of v || []) {
8940
9017
  map = strategy.select({
@@ -8942,7 +9019,8 @@ const classicSelectStrategy = mandatory => {
8942
9019
  value: true,
8943
9020
  selected: map,
8944
9021
  children,
8945
- parents
9022
+ parents,
9023
+ disabled
8946
9024
  });
8947
9025
  }
8948
9026
  return map;
@@ -8989,8 +9067,9 @@ const emptyNested = {
8989
9067
  root: {
8990
9068
  register: () => null,
8991
9069
  unregister: () => null,
8992
- parents: ref(new Map()),
8993
9070
  children: ref(new Map()),
9071
+ parents: ref(new Map()),
9072
+ disabled: ref(new Set()),
8994
9073
  open: () => null,
8995
9074
  openOnSelect: () => null,
8996
9075
  activate: () => null,
@@ -9017,9 +9096,10 @@ const makeNestedProps = propsFactory({
9017
9096
  }, 'nested');
9018
9097
  const useNested = props => {
9019
9098
  let isUnmounted = false;
9020
- const children = ref(new Map());
9021
- const parents = ref(new Map());
9022
- const opened = useProxiedModel(props, 'opened', props.opened, v => new Set(v), v => [...v.values()]);
9099
+ const children = shallowRef(new Map());
9100
+ const parents = shallowRef(new Map());
9101
+ const disabled = shallowRef(new Set());
9102
+ const opened = useProxiedModel(props, 'opened', props.opened, v => new Set(Array.isArray(v) ? v.map(i => toRaw(i)) : v), v => [...v.values()]);
9023
9103
  const activeStrategy = computed(() => {
9024
9104
  if (typeof props.activeStrategy === 'object') return props.activeStrategy;
9025
9105
  if (typeof props.activeStrategy === 'function') return props.activeStrategy(props.mandatory);
@@ -9067,13 +9147,13 @@ const useNested = props => {
9067
9147
  }
9068
9148
  });
9069
9149
  const activated = useProxiedModel(props, 'activated', props.activated, v => activeStrategy.value.in(v, children.value, parents.value), v => activeStrategy.value.out(v, children.value, parents.value));
9070
- const selected = useProxiedModel(props, 'selected', props.selected, v => selectStrategy.value.in(v, children.value, parents.value), v => selectStrategy.value.out(v, children.value, parents.value));
9150
+ const selected = useProxiedModel(props, 'selected', props.selected, v => selectStrategy.value.in(v, children.value, parents.value, disabled.value), v => selectStrategy.value.out(v, children.value, parents.value));
9071
9151
  onBeforeUnmount(() => {
9072
9152
  isUnmounted = true;
9073
9153
  });
9074
9154
  function getPath(id) {
9075
9155
  const path = [];
9076
- let parent = id;
9156
+ let parent = toRaw(id);
9077
9157
  while (parent != null) {
9078
9158
  path.unshift(parent);
9079
9159
  parent = parents.value.get(parent);
@@ -9097,7 +9177,7 @@ const useNested = props => {
9097
9177
  }
9098
9178
  return arr;
9099
9179
  }),
9100
- register: (id, parentId, isGroup) => {
9180
+ register: (id, parentId, isDisabled, isGroup) => {
9101
9181
  if (nodeIds.has(id)) {
9102
9182
  const path = getPath(id).map(String).join(' -> ');
9103
9183
  const newPath = getPath(parentId).concat(id).map(String).join(' -> ');
@@ -9107,6 +9187,7 @@ const useNested = props => {
9107
9187
  nodeIds.add(id);
9108
9188
  }
9109
9189
  parentId && id !== parentId && parents.value.set(id, parentId);
9190
+ isDisabled && disabled.value.add(id);
9110
9191
  isGroup && children.value.set(id, []);
9111
9192
  if (parentId != null) {
9112
9193
  children.value.set(parentId, [...(children.value.get(parentId) || []), id]);
@@ -9116,6 +9197,7 @@ const useNested = props => {
9116
9197
  if (isUnmounted) return;
9117
9198
  nodeIds.delete(id);
9118
9199
  children.value.delete(id);
9200
+ disabled.value.delete(id);
9119
9201
  const parent = parents.value.get(id);
9120
9202
  if (parent) {
9121
9203
  const list = children.value.get(parent) ?? [];
@@ -9165,6 +9247,7 @@ const useNested = props => {
9165
9247
  selected: new Map(selected.value),
9166
9248
  children: children.value,
9167
9249
  parents: parents.value,
9250
+ disabled: disabled.value,
9168
9251
  event
9169
9252
  });
9170
9253
  newSelected && (selected.value = newSelected);
@@ -9207,16 +9290,17 @@ const useNested = props => {
9207
9290
  },
9208
9291
  children,
9209
9292
  parents,
9293
+ disabled,
9210
9294
  getPath
9211
9295
  }
9212
9296
  };
9213
9297
  provide(VNestedSymbol, nested);
9214
9298
  return nested.root;
9215
9299
  };
9216
- const useNestedItem = (id, isGroup) => {
9300
+ const useNestedItem = (id, isDisabled, isGroup) => {
9217
9301
  const parent = inject$1(VNestedSymbol, emptyNested);
9218
9302
  const uidSymbol = Symbol('nested item');
9219
- const computedId = computed(() => toValue(id) ?? uidSymbol);
9303
+ const computedId = computed(() => toRaw(toValue(id)) ?? uidSymbol);
9220
9304
  const item = {
9221
9305
  ...parent,
9222
9306
  id: computedId,
@@ -9225,18 +9309,22 @@ const useNestedItem = (id, isGroup) => {
9225
9309
  isOpen: computed(() => parent.root.opened.value.has(computedId.value)),
9226
9310
  parent: computed(() => parent.root.parents.value.get(computedId.value)),
9227
9311
  activate: (activated, e) => parent.root.activate(computedId.value, activated, e),
9228
- isActivated: computed(() => parent.root.activated.value.has(toRaw(computedId.value))),
9312
+ isActivated: computed(() => parent.root.activated.value.has(computedId.value)),
9229
9313
  select: (selected, e) => parent.root.select(computedId.value, selected, e),
9230
- isSelected: computed(() => parent.root.selected.value.get(toRaw(computedId.value)) === 'on'),
9231
- isIndeterminate: computed(() => parent.root.selected.value.get(toRaw(computedId.value)) === 'indeterminate'),
9314
+ isSelected: computed(() => parent.root.selected.value.get(computedId.value) === 'on'),
9315
+ isIndeterminate: computed(() => parent.root.selected.value.get(computedId.value) === 'indeterminate'),
9232
9316
  isLeaf: computed(() => !parent.root.children.value.get(computedId.value)),
9233
9317
  isGroupActivator: parent.isGroupActivator
9234
9318
  };
9235
9319
  onBeforeMount(() => {
9236
- !parent.isGroupActivator && parent.root.register(computedId.value, parent.id.value, isGroup);
9320
+ if (!parent.isGroupActivator) {
9321
+ parent.root.register(computedId.value, parent.id.value, toValue(isDisabled), isGroup);
9322
+ }
9237
9323
  });
9238
9324
  onBeforeUnmount(() => {
9239
- !parent.isGroupActivator && parent.root.unregister(computedId.value);
9325
+ if (!parent.isGroupActivator) {
9326
+ parent.root.unregister(computedId.value);
9327
+ }
9240
9328
  });
9241
9329
  isGroup && provide(VNestedSymbol, item);
9242
9330
  return item;
@@ -9268,6 +9356,7 @@ const makeVListGroupProps = propsFactory({
9268
9356
  type: IconValue,
9269
9357
  default: '$collapse'
9270
9358
  },
9359
+ disabled: Boolean,
9271
9360
  expandIcon: {
9272
9361
  type: IconValue,
9273
9362
  default: '$expand'
@@ -9293,7 +9382,7 @@ const VListGroup = genericComponent()({
9293
9382
  isOpen,
9294
9383
  open,
9295
9384
  id: _id
9296
- } = useNestedItem(() => props.value, true);
9385
+ } = useNestedItem(() => props.value, () => props.disabled, true);
9297
9386
  const id = computed(() => `v-list-group--id-${String(props.rawId ?? _id.value)}`);
9298
9387
  const list = useList();
9299
9388
  const {
@@ -9463,7 +9552,7 @@ const VListItem = genericComponent()({
9463
9552
  parent,
9464
9553
  openOnSelect,
9465
9554
  id: uid
9466
- } = useNestedItem(id, false);
9555
+ } = useNestedItem(id, () => props.disabled, false);
9467
9556
  const list = useList();
9468
9557
  const isActive = computed(() => props.active !== false && (props.active || link.isActive?.value || (root.activatable.value ? isActivated.value : isSelected.value)));
9469
9558
  const isLink = toRef(() => props.link !== false && link.isLink.value);
@@ -9815,6 +9904,10 @@ const makeItemsProps = propsFactory({
9815
9904
  type: [Boolean, String, Array, Function],
9816
9905
  default: 'props'
9817
9906
  },
9907
+ itemType: {
9908
+ type: [Boolean, String, Array, Function],
9909
+ default: 'type'
9910
+ },
9818
9911
  returnObject: Boolean,
9819
9912
  valueComparator: Function
9820
9913
  }, 'list-items');
@@ -9822,6 +9915,7 @@ function transformItem$3(props, item) {
9822
9915
  const title = getPropertyFromItem(item, props.itemTitle, item);
9823
9916
  const value = getPropertyFromItem(item, props.itemValue, title);
9824
9917
  const children = getPropertyFromItem(item, props.itemChildren);
9918
+ const type = getPropertyFromItem(item, props.itemType, 'item');
9825
9919
  const itemProps = props.itemProps === true ? typeof item === 'object' && item != null && !Array.isArray(item) ? 'children' in item ? omit(item, ['children']) : item : undefined : getPropertyFromItem(item, props.itemProps);
9826
9920
  const _props = {
9827
9921
  title,
@@ -9829,15 +9923,16 @@ function transformItem$3(props, item) {
9829
9923
  ...itemProps
9830
9924
  };
9831
9925
  return {
9926
+ type,
9832
9927
  title: String(_props.title ?? ''),
9833
9928
  value: _props.value,
9834
9929
  props: _props,
9835
- children: Array.isArray(children) ? transformItems$3(props, children) : undefined,
9930
+ children: type === 'item' && Array.isArray(children) ? transformItems$3(props, children) : undefined,
9836
9931
  raw: item
9837
9932
  };
9838
9933
  }
9839
9934
  function transformItems$3(props, items) {
9840
- const _props = pick(props, ['itemTitle', 'itemValue', 'itemChildren', 'itemProps', 'returnObject', 'valueComparator']);
9935
+ const _props = pick(props, ['itemTitle', 'itemValue', 'itemChildren', 'itemProps', 'itemType', 'returnObject', 'valueComparator']);
9841
9936
  const array = [];
9842
9937
  for (const item of items) {
9843
9938
  array.push(transformItem$3(_props, item));
@@ -9879,7 +9974,7 @@ function useItems(props) {
9879
9974
  const _returnObject = props.returnObject;
9880
9975
  const hasValueComparator = !!props.valueComparator;
9881
9976
  const valueComparator = props.valueComparator || deepEqual;
9882
- const _props = pick(props, ['itemTitle', 'itemValue', 'itemChildren', 'itemProps', 'returnObject', 'valueComparator']);
9977
+ const _props = pick(props, ['itemTitle', 'itemValue', 'itemChildren', 'itemProps', 'itemType', 'returnObject', 'valueComparator']);
9883
9978
  const returnValue = [];
9884
9979
  main: for (const v of value) {
9885
9980
  // When the model value is null, return an InternalItem
@@ -9941,7 +10036,7 @@ function useItems(props) {
9941
10036
  function transformItem$2(props, item) {
9942
10037
  const type = getPropertyFromItem(item, props.itemType, 'item');
9943
10038
  const title = isPrimitive(item) ? item : getPropertyFromItem(item, props.itemTitle);
9944
- const value = getPropertyFromItem(item, props.itemValue, undefined);
10039
+ const value = isPrimitive(item) ? item : getPropertyFromItem(item, props.itemValue, undefined);
9945
10040
  const children = getPropertyFromItem(item, props.itemChildren);
9946
10041
  const itemProps = props.itemProps === true ? omit(item, ['children']) : getPropertyFromItem(item, props.itemProps);
9947
10042
  const _props = {
@@ -9999,10 +10094,6 @@ const makeVListProps = propsFactory({
9999
10094
  ...makeDensityProps(),
10000
10095
  ...makeDimensionProps(),
10001
10096
  ...makeElevationProps(),
10002
- itemType: {
10003
- type: String,
10004
- default: 'type'
10005
- },
10006
10097
  ...makeItemsProps(),
10007
10098
  ...makeRoundedProps(),
10008
10099
  ...makeTagProps(),
@@ -10423,7 +10514,7 @@ function connectedLocationStrategy(data, props, contentStyles) {
10423
10514
  });
10424
10515
  if (flipped.isFull) {
10425
10516
  const values = flipped.values();
10426
- if (deepEqual(values.at(-1), values.at(-3))) {
10517
+ if (deepEqual(values.at(-1), values.at(-3)) && !deepEqual(values.at(-1), values.at(-2))) {
10427
10518
  // Flipping is causing a container resize loop
10428
10519
  return;
10429
10520
  }
@@ -12093,11 +12184,7 @@ const VField = genericComponent()({
12093
12184
  default: slots.loader
12094
12185
  }), hasPrepend && createElementVNode("div", {
12095
12186
  "key": "prepend",
12096
- "class": "v-field__prepend-inner",
12097
- "onMousedown": e => {
12098
- e.preventDefault();
12099
- e.stopPropagation();
12100
- }
12187
+ "class": "v-field__prepend-inner"
12101
12188
  }, [props.prependInnerIcon && createVNode(InputIcon, {
12102
12189
  "key": "prepend-icon",
12103
12190
  "name": "prependInner",
@@ -12166,11 +12253,7 @@ const VField = genericComponent()({
12166
12253
  })]), [[vShow, props.dirty]])]
12167
12254
  }), hasAppend && createElementVNode("div", {
12168
12255
  "key": "append",
12169
- "class": "v-field__append-inner",
12170
- "onMousedown": e => {
12171
- e.preventDefault();
12172
- e.stopPropagation();
12173
- }
12256
+ "class": "v-field__append-inner"
12174
12257
  }, [slots['append-inner']?.(slotProps.value), props.appendInnerIcon && createVNode(InputIcon, {
12175
12258
  "key": "append-icon",
12176
12259
  "name": "appendInner",
@@ -12281,7 +12364,7 @@ const VTextField = genericComponent()({
12281
12364
  if (!isFocused.value) focus();
12282
12365
  nextTick(() => {
12283
12366
  if (inputRef.value !== document.activeElement) {
12284
- inputRef.value?.focus();
12367
+ nextTick(() => inputRef.value?.focus());
12285
12368
  }
12286
12369
  });
12287
12370
  }
@@ -12620,7 +12703,7 @@ function useVirtual(props, items) {
12620
12703
  raf = requestAnimationFrame(_calculateVisibleItems);
12621
12704
  }
12622
12705
  function _calculateVisibleItems() {
12623
- if (!containerRef.value || !viewportHeight.value) return;
12706
+ if (!containerRef.value || !viewportHeight.value || !itemHeight.value) return;
12624
12707
  const scrollTop = lastScrollTop - markerOffset;
12625
12708
  const direction = Math.sign(scrollVelocity);
12626
12709
  const startPx = Math.max(0, scrollTop - BUFFER_PX);
@@ -13229,7 +13312,7 @@ const VSelect = genericComponent()({
13229
13312
  key: item.value,
13230
13313
  onClick: () => select(item, null)
13231
13314
  });
13232
- if (item.raw.type === 'divider') {
13315
+ if (item.type === 'divider') {
13233
13316
  return slots.divider?.({
13234
13317
  props: item.raw,
13235
13318
  index
@@ -13237,7 +13320,7 @@ const VSelect = genericComponent()({
13237
13320
  "key": `divider-${index}`
13238
13321
  }), null);
13239
13322
  }
13240
- if (item.raw.type === 'subheader') {
13323
+ if (item.type === 'subheader') {
13241
13324
  return slots.subheader?.({
13242
13325
  props: item.raw,
13243
13326
  index
@@ -13405,7 +13488,7 @@ function filterItems(items, query, options) {
13405
13488
  let match = -1;
13406
13489
  if ((query || customFiltersLength > 0) && !options?.noFilter) {
13407
13490
  if (typeof item === 'object') {
13408
- if (['divider', 'subheader'].includes(item.raw?.type)) {
13491
+ if (item.type === 'divider' || item.type === 'subheader') {
13409
13492
  continue;
13410
13493
  }
13411
13494
  const filterKeys = keys || Object.keys(transformed);
@@ -13847,7 +13930,7 @@ const VAutocomplete = genericComponent()({
13847
13930
  active: highlightFirst.value && index === 0 ? true : undefined,
13848
13931
  onClick: () => select(item, null)
13849
13932
  });
13850
- if (item.raw.type === 'divider') {
13933
+ if (item.type === 'divider') {
13851
13934
  return slots.divider?.({
13852
13935
  props: item.raw,
13853
13936
  index
@@ -13855,7 +13938,7 @@ const VAutocomplete = genericComponent()({
13855
13938
  "key": `divider-${index}`
13856
13939
  }), null);
13857
13940
  }
13858
- if (item.raw.type === 'subheader') {
13941
+ if (item.type === 'subheader') {
13859
13942
  return slots.subheader?.({
13860
13943
  props: item.raw,
13861
13944
  index
@@ -15416,6 +15499,7 @@ const VCarousel = genericComponent()({
15416
15499
  }) : createVNode(VBtn, mergeProps(item, props), null);
15417
15500
  })]
15418
15501
  })]), props.progress && createVNode(VProgressLinear, {
15502
+ "absolute": true,
15419
15503
  "class": "v-carousel__progress",
15420
15504
  "color": typeof props.progress === 'string' ? props.progress : undefined,
15421
15505
  "modelValue": (group.getItemIndex(model.value) + 1) / group.items.value.length * 100
@@ -17502,7 +17586,7 @@ function format(value, formatString, locale, formats) {
17502
17586
  case 'fullDate':
17503
17587
  options = {
17504
17588
  year: 'numeric',
17505
- month: 'long',
17589
+ month: 'short',
17506
17590
  day: 'numeric'
17507
17591
  };
17508
17592
  break;
@@ -18080,6 +18164,317 @@ function useDate() {
18080
18164
  return createInstance(options, locale);
18081
18165
  }
18082
18166
 
18167
+ /**
18168
+ * Centralized key alias mapping for consistent key normalization across the hotkey system.
18169
+ *
18170
+ * This maps various user-friendly aliases to canonical key names that match
18171
+ * KeyboardEvent.key values (in lowercase) where possible.
18172
+ */
18173
+ const keyAliasMap = {
18174
+ // Modifier aliases (from vue-use, other libraries, and current implementation)
18175
+ control: 'ctrl',
18176
+ command: 'cmd',
18177
+ option: 'alt',
18178
+ // Arrow key aliases (common abbreviations)
18179
+ up: 'arrowup',
18180
+ down: 'arrowdown',
18181
+ left: 'arrowleft',
18182
+ right: 'arrowright',
18183
+ // Other common key aliases
18184
+ esc: 'escape',
18185
+ spacebar: ' ',
18186
+ space: ' ',
18187
+ return: 'enter',
18188
+ del: 'delete',
18189
+ // Symbol aliases (existing from hotkey-parsing.ts)
18190
+ minus: '-',
18191
+ hyphen: '-'
18192
+ };
18193
+
18194
+ /**
18195
+ * Normalizes a key string to its canonical form using the alias map.
18196
+ *
18197
+ * @param key - The key string to normalize
18198
+ * @returns The canonical key name in lowercase
18199
+ */
18200
+ function normalizeKey(key) {
18201
+ const lowerKey = key.toLowerCase();
18202
+ return keyAliasMap[lowerKey] || lowerKey;
18203
+ }
18204
+
18205
+ // Utilities
18206
+
18207
+ /**
18208
+ * Splits a single combination string into individual key parts.
18209
+ *
18210
+ * A combination is a set of keys that must be pressed simultaneously.
18211
+ * e.g. `ctrl+k`, `shift--`
18212
+ */
18213
+ function splitKeyCombination(combination) {
18214
+ let isInternal = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
18215
+ if (!combination) {
18216
+ if (!isInternal) consoleWarn('Invalid hotkey combination: empty string provided');
18217
+ return [];
18218
+ }
18219
+
18220
+ // --- VALIDATION ---
18221
+ const startsWithPlusOrUnderscore = combination.startsWith('+') || combination.startsWith('_');
18222
+ const hasInvalidLeadingSeparator =
18223
+ // Starts with a single '+' or '_' followed by a non-separator character (e.g. '+a', '_a')
18224
+ startsWithPlusOrUnderscore && !(combination.startsWith('++') || combination.startsWith('__'));
18225
+ const hasInvalidStructure =
18226
+ // Invalid leading separator patterns
18227
+ combination.length > 1 && hasInvalidLeadingSeparator ||
18228
+ // Disallow literal + or _ keys (they require shift)
18229
+ combination.includes('++') || combination.includes('__') || combination === '+' || combination === '_' ||
18230
+ // Ends with a separator that is not part of a doubled literal
18231
+ combination.length > 1 && (combination.endsWith('+') || combination.endsWith('_')) && combination.at(-2) !== combination.at(-1) ||
18232
+ // Stand-alone doubled separators (dangling)
18233
+ combination === '++' || combination === '--' || combination === '__';
18234
+ if (hasInvalidStructure) {
18235
+ if (!isInternal) consoleWarn(`Invalid hotkey combination: "${combination}" has invalid structure`);
18236
+ return [];
18237
+ }
18238
+ const keys = [];
18239
+ let buffer = '';
18240
+ const flushBuffer = () => {
18241
+ if (buffer) {
18242
+ keys.push(normalizeKey(buffer));
18243
+ buffer = '';
18244
+ }
18245
+ };
18246
+ for (let i = 0; i < combination.length; i++) {
18247
+ const char = combination[i];
18248
+ const nextChar = combination[i + 1];
18249
+ if (char === '+' || char === '_' || char === '-') {
18250
+ if (char === nextChar) {
18251
+ flushBuffer();
18252
+ keys.push(char);
18253
+ i++;
18254
+ } else if (char === '+' || char === '_') {
18255
+ flushBuffer();
18256
+ } else {
18257
+ buffer += char;
18258
+ }
18259
+ } else {
18260
+ buffer += char;
18261
+ }
18262
+ }
18263
+ flushBuffer();
18264
+
18265
+ // Within a combination, `-` is only valid as a literal key (e.g., `ctrl+-`).
18266
+ // `-` cannot be part of a longer key name within a combination.
18267
+ const hasInvalidMinus = keys.some(key => key.length > 1 && key.includes('-') && key !== '--');
18268
+ if (hasInvalidMinus) {
18269
+ if (!isInternal) consoleWarn(`Invalid hotkey combination: "${combination}" has invalid structure`);
18270
+ return [];
18271
+ }
18272
+ if (keys.length === 0 && combination) {
18273
+ return [normalizeKey(combination)];
18274
+ }
18275
+ return keys;
18276
+ }
18277
+
18278
+ /**
18279
+ * Splits a hotkey string into its constituent combination groups.
18280
+ *
18281
+ * A sequence is a series of combinations that must be pressed in order.
18282
+ * e.g. `a-b`, `ctrl+k-p`
18283
+ */
18284
+ function splitKeySequence(str) {
18285
+ if (!str) {
18286
+ consoleWarn('Invalid hotkey sequence: empty string provided');
18287
+ return [];
18288
+ }
18289
+
18290
+ // A sequence is invalid if it starts or ends with a separator,
18291
+ // unless it is part of a combination (e.g., `shift+-`).
18292
+ const hasInvalidStart = str.startsWith('-') && !['---', '--+'].includes(str);
18293
+ const hasInvalidEnd = str.endsWith('-') && !str.endsWith('+-') && !str.endsWith('_-') && str !== '-' && str !== '---';
18294
+ if (hasInvalidStart || hasInvalidEnd) {
18295
+ consoleWarn(`Invalid hotkey sequence: "${str}" contains invalid combinations`);
18296
+ return [];
18297
+ }
18298
+ const result = [];
18299
+ let buffer = '';
18300
+ let i = 0;
18301
+ while (i < str.length) {
18302
+ const char = str[i];
18303
+ if (char === '-') {
18304
+ // Determine if this hyphen is part of the current combination
18305
+ const prevChar = str[i - 1];
18306
+ const prevPrevChar = i > 1 ? str[i - 2] : undefined;
18307
+ const precededBySinglePlusOrUnderscore = (prevChar === '+' || prevChar === '_') && prevPrevChar !== '+';
18308
+ if (precededBySinglePlusOrUnderscore) {
18309
+ // Treat as part of the combination (e.g., 'ctrl+-')
18310
+ buffer += char;
18311
+ i++;
18312
+ } else {
18313
+ // Treat as sequence separator
18314
+ if (buffer) {
18315
+ result.push(buffer);
18316
+ buffer = '';
18317
+ } else {
18318
+ // Empty buffer means we have a literal '-' key
18319
+ result.push('-');
18320
+ }
18321
+ i++;
18322
+ }
18323
+ } else {
18324
+ buffer += char;
18325
+ i++;
18326
+ }
18327
+ }
18328
+
18329
+ // Add final buffer if it exists
18330
+ if (buffer) {
18331
+ result.push(buffer);
18332
+ }
18333
+
18334
+ // Collapse runs of '-' so that every second '-' is removed
18335
+ const collapsed = [];
18336
+ let minusCount = 0;
18337
+ for (const part of result) {
18338
+ if (part === '-') {
18339
+ if (minusCount % 2 === 0) collapsed.push('-');
18340
+ minusCount++;
18341
+ } else {
18342
+ minusCount = 0;
18343
+ collapsed.push(part);
18344
+ }
18345
+ }
18346
+
18347
+ // Validate that each part of the sequence is a valid combination
18348
+ const areAllValid = collapsed.every(s => splitKeyCombination(s, true).length > 0);
18349
+ if (!areAllValid) {
18350
+ consoleWarn(`Invalid hotkey sequence: "${str}" contains invalid combinations`);
18351
+ return [];
18352
+ }
18353
+ return collapsed;
18354
+ }
18355
+
18356
+ // Composables
18357
+
18358
+ // Types
18359
+
18360
+ function useHotkey(keys, callback) {
18361
+ let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
18362
+ if (!IN_BROWSER) return function () {};
18363
+ const {
18364
+ event = 'keydown',
18365
+ inputs = false,
18366
+ preventDefault = true,
18367
+ sequenceTimeout = 1000
18368
+ } = options;
18369
+ const isMac = navigator?.userAgent?.includes('Macintosh') ?? false;
18370
+ let timeout = 0;
18371
+ let keyGroups;
18372
+ let isSequence = false;
18373
+ let groupIndex = 0;
18374
+ function clearTimer() {
18375
+ if (!timeout) return;
18376
+ clearTimeout(timeout);
18377
+ timeout = 0;
18378
+ }
18379
+ function isInputFocused() {
18380
+ if (toValue(inputs)) return false;
18381
+ const activeElement = document.activeElement;
18382
+ return activeElement && (activeElement.tagName === 'INPUT' || activeElement.tagName === 'TEXTAREA' || activeElement.isContentEditable || activeElement.contentEditable === 'true');
18383
+ }
18384
+ function resetSequence() {
18385
+ groupIndex = 0;
18386
+ clearTimer();
18387
+ }
18388
+ function handler(e) {
18389
+ const group = keyGroups[groupIndex];
18390
+ if (!group || isInputFocused()) return;
18391
+ if (!matchesKeyGroup(e, group)) {
18392
+ if (isSequence) resetSequence();
18393
+ return;
18394
+ }
18395
+ if (toValue(preventDefault)) e.preventDefault();
18396
+ if (!isSequence) {
18397
+ callback(e);
18398
+ return;
18399
+ }
18400
+ clearTimer();
18401
+ groupIndex++;
18402
+ if (groupIndex === keyGroups.length) {
18403
+ callback(e);
18404
+ resetSequence();
18405
+ return;
18406
+ }
18407
+ timeout = window.setTimeout(resetSequence, toValue(sequenceTimeout));
18408
+ }
18409
+ function cleanup() {
18410
+ window.removeEventListener(toValue(event), handler);
18411
+ clearTimer();
18412
+ }
18413
+ watch(() => toValue(keys), function (unrefKeys) {
18414
+ cleanup();
18415
+ if (unrefKeys) {
18416
+ const groups = splitKeySequence(unrefKeys.toLowerCase());
18417
+ isSequence = groups.length > 1;
18418
+ keyGroups = groups;
18419
+ resetSequence();
18420
+ window.addEventListener(toValue(event), handler);
18421
+ }
18422
+ }, {
18423
+ immediate: true
18424
+ });
18425
+
18426
+ // Watch for changes in the event type to re-register the listener
18427
+ watch(() => toValue(event), function (newEvent, oldEvent) {
18428
+ if (oldEvent && keyGroups && keyGroups.length > 0) {
18429
+ window.removeEventListener(oldEvent, handler);
18430
+ window.addEventListener(newEvent, handler);
18431
+ }
18432
+ });
18433
+ try {
18434
+ getCurrentInstance('useHotkey');
18435
+ onBeforeUnmount(cleanup);
18436
+ } catch {
18437
+ // Not in Vue setup context
18438
+ }
18439
+ function parseKeyGroup(group) {
18440
+ const MODIFIERS = ['ctrl', 'shift', 'alt', 'meta', 'cmd'];
18441
+
18442
+ // Use the shared combination splitting logic
18443
+ const parts = splitKeyCombination(group.toLowerCase());
18444
+
18445
+ // If the combination is invalid, return empty result
18446
+ if (parts.length === 0) {
18447
+ return {
18448
+ modifiers: Object.fromEntries(MODIFIERS.map(m => [m, false])),
18449
+ actualKey: undefined
18450
+ };
18451
+ }
18452
+ const modifiers = Object.fromEntries(MODIFIERS.map(m => [m, false]));
18453
+ let actualKey;
18454
+ for (const part of parts) {
18455
+ if (MODIFIERS.includes(part)) {
18456
+ modifiers[part] = true;
18457
+ } else {
18458
+ actualKey = part;
18459
+ }
18460
+ }
18461
+ return {
18462
+ modifiers,
18463
+ actualKey
18464
+ };
18465
+ }
18466
+ function matchesKeyGroup(e, group) {
18467
+ const {
18468
+ modifiers,
18469
+ actualKey
18470
+ } = parseKeyGroup(group);
18471
+ const expectCtrl = modifiers.ctrl || !isMac && (modifiers.cmd || modifiers.meta);
18472
+ const expectMeta = isMac && (modifiers.cmd || modifiers.meta);
18473
+ return e.ctrlKey === expectCtrl && e.metaKey === expectMeta && e.shiftKey === modifiers.shift && e.altKey === modifiers.alt && e.key.toLowerCase() === actualKey?.toLowerCase();
18474
+ }
18475
+ return cleanup;
18476
+ }
18477
+
18083
18478
  // Types
18084
18479
 
18085
18480
  const makeVColorPickerProps = propsFactory({
@@ -18626,7 +19021,7 @@ const VCombobox = genericComponent()({
18626
19021
  active: highlightFirst.value && index === 0 ? true : undefined,
18627
19022
  onClick: () => select(item, null)
18628
19023
  });
18629
- if (item.raw.type === 'divider') {
19024
+ if (item.type === 'divider') {
18630
19025
  return slots.divider?.({
18631
19026
  props: item.raw,
18632
19027
  index
@@ -18634,7 +19029,7 @@ const VCombobox = genericComponent()({
18634
19029
  "key": `divider-${index}`
18635
19030
  }), null);
18636
19031
  }
18637
- if (item.raw.type === 'subheader') {
19032
+ if (item.type === 'subheader') {
18638
19033
  return slots.subheader?.({
18639
19034
  props: item.raw,
18640
19035
  index
@@ -19508,7 +19903,8 @@ function sortItems(items, sortByItems, locale, options) {
19508
19903
 
19509
19904
  // Dates should be compared numerically
19510
19905
  if (sortA instanceof Date && sortB instanceof Date) {
19511
- return sortA.getTime() - sortB.getTime();
19906
+ sortA = sortA.getTime();
19907
+ sortB = sortB.getTime();
19512
19908
  }
19513
19909
  [sortA, sortB] = [sortA, sortB].map(s => s != null ? s.toString().toLocaleLowerCase() : s);
19514
19910
  if (sortA !== sortB) {
@@ -20217,10 +20613,15 @@ const VDataTableColumn = defineFunctionalComponent({
20217
20613
  type: String,
20218
20614
  default: 'start'
20219
20615
  },
20220
- fixed: Boolean,
20616
+ fixed: {
20617
+ type: [Boolean, String],
20618
+ default: false
20619
+ },
20221
20620
  fixedOffset: [Number, String],
20621
+ fixedEndOffset: [Number, String],
20222
20622
  height: [Number, String],
20223
20623
  lastFixed: Boolean,
20624
+ firstFixedEnd: Boolean,
20224
20625
  noPadding: Boolean,
20225
20626
  tag: String,
20226
20627
  width: [Number, String],
@@ -20231,11 +20632,13 @@ const VDataTableColumn = defineFunctionalComponent({
20231
20632
  slots
20232
20633
  } = _ref;
20233
20634
  const Tag = props.tag ?? 'td';
20635
+ const fixedSide = typeof props.fixed === 'string' ? props.fixed : props.fixed ? 'start' : 'none';
20234
20636
  return createVNode(Tag, {
20235
- "tabindex": "0",
20236
20637
  "class": normalizeClass(['v-data-table__td', {
20237
- 'v-data-table-column--fixed': props.fixed,
20638
+ 'v-data-table-column--fixed': fixedSide === 'start',
20639
+ 'v-data-table-column--fixed-end': fixedSide === 'end',
20238
20640
  'v-data-table-column--last-fixed': props.lastFixed,
20641
+ 'v-data-table-column--first-fixed-end': props.firstFixedEnd,
20239
20642
  'v-data-table-column--no-padding': props.noPadding,
20240
20643
  'v-data-table-column--nowrap': props.nowrap
20241
20644
  }, `v-data-table-column--align-${props.align}`]),
@@ -20243,7 +20646,8 @@ const VDataTableColumn = defineFunctionalComponent({
20243
20646
  height: convertToUnit(props.height),
20244
20647
  width: convertToUnit(props.width),
20245
20648
  maxWidth: convertToUnit(props.maxWidth),
20246
- left: convertToUnit(props.fixedOffset || null)
20649
+ left: fixedSide === 'start' ? convertToUnit(props.fixedOffset || null) : undefined,
20650
+ right: fixedSide === 'end' ? convertToUnit(props.fixedEndOffset || null) : undefined
20247
20651
  }
20248
20652
  }, {
20249
20653
  default: () => [slots.default?.()]
@@ -20340,20 +20744,28 @@ function getDepth(item) {
20340
20744
  }
20341
20745
  function parseFixedColumns(items) {
20342
20746
  let seenFixed = false;
20343
- function setFixed(item) {
20344
- let parentFixed = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
20747
+ function setFixed(item, side) {
20748
+ let parentFixedSide = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'none';
20345
20749
  if (!item) return;
20346
- if (parentFixed) {
20347
- item.fixed = true;
20750
+ if (parentFixedSide !== 'none') {
20751
+ item.fixed = parentFixedSide;
20348
20752
  }
20349
- if (item.fixed) {
20350
- if (item.children) {
20351
- for (let i = item.children.length - 1; i >= 0; i--) {
20352
- setFixed(item.children[i], true);
20753
+
20754
+ // normalize to simplify logic below
20755
+ if (item.fixed === true) {
20756
+ item.fixed = 'start';
20757
+ }
20758
+ const orderedChildren = side === 'start' ? item.children?.toReversed() : item.children;
20759
+ if (item.fixed === side) {
20760
+ if (orderedChildren) {
20761
+ for (const child of orderedChildren) {
20762
+ setFixed(child, side, side);
20353
20763
  }
20354
20764
  } else {
20355
- if (!seenFixed) {
20765
+ if (!seenFixed && side === 'start') {
20356
20766
  item.lastFixed = true;
20767
+ } else if (!seenFixed && side === 'end') {
20768
+ item.firstFixedEnd = true;
20357
20769
  } else if (isNaN(Number(item.width))) {
20358
20770
  consoleError(`Multiple fixed columns should have a static width (key: ${item.key})`);
20359
20771
  } else {
@@ -20362,36 +20774,57 @@ function parseFixedColumns(items) {
20362
20774
  seenFixed = true;
20363
20775
  }
20364
20776
  } else {
20365
- if (item.children) {
20366
- for (let i = item.children.length - 1; i >= 0; i--) {
20367
- setFixed(item.children[i]);
20777
+ if (orderedChildren) {
20778
+ for (const child of orderedChildren) {
20779
+ setFixed(child, side);
20368
20780
  }
20369
20781
  } else {
20370
20782
  seenFixed = false;
20371
20783
  }
20372
20784
  }
20373
20785
  }
20374
- for (let i = items.length - 1; i >= 0; i--) {
20375
- setFixed(items[i]);
20786
+ for (const item of items.toReversed()) {
20787
+ setFixed(item, 'start');
20788
+ }
20789
+ for (const item of items) {
20790
+ setFixed(item, 'end');
20376
20791
  }
20377
20792
  function setFixedOffset(item) {
20378
- let fixedOffset = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
20379
- if (!item) return fixedOffset;
20793
+ let offset = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
20794
+ if (!item) return offset;
20380
20795
  if (item.children) {
20381
- item.fixedOffset = fixedOffset;
20796
+ item.fixedOffset = offset;
20382
20797
  for (const child of item.children) {
20383
- fixedOffset = setFixedOffset(child, fixedOffset);
20798
+ offset = setFixedOffset(child, offset);
20384
20799
  }
20385
- } else if (item.fixed) {
20386
- item.fixedOffset = fixedOffset;
20387
- fixedOffset += parseFloat(item.width || '0') || 0;
20800
+ } else if (item.fixed && item.fixed !== 'end') {
20801
+ item.fixedOffset = offset;
20802
+ offset += parseFloat(item.width || '0') || 0;
20388
20803
  }
20389
- return fixedOffset;
20804
+ return offset;
20390
20805
  }
20391
20806
  let fixedOffset = 0;
20392
20807
  for (const item of items) {
20393
20808
  fixedOffset = setFixedOffset(item, fixedOffset);
20394
20809
  }
20810
+ function setFixedEndOffset(item) {
20811
+ let offset = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
20812
+ if (!item) return offset;
20813
+ if (item.children) {
20814
+ item.fixedEndOffset = offset;
20815
+ for (const child of item.children) {
20816
+ offset = setFixedEndOffset(child, offset);
20817
+ }
20818
+ } else if (item.fixed === 'end') {
20819
+ item.fixedEndOffset = offset;
20820
+ offset += parseFloat(item.width || '0') || 0;
20821
+ }
20822
+ return offset;
20823
+ }
20824
+ let fixedEndOffset = 0;
20825
+ for (const item of items.toReversed()) {
20826
+ fixedEndOffset = setFixedEndOffset(item, fixedEndOffset);
20827
+ }
20395
20828
  }
20396
20829
  function parse(items, maxDepth) {
20397
20830
  const headers = [];
@@ -20524,7 +20957,6 @@ const makeVDataTableHeadersProps = propsFactory({
20524
20957
  color: String,
20525
20958
  disableSort: Boolean,
20526
20959
  fixedHeader: Boolean,
20527
- lastFixed: Boolean,
20528
20960
  multiSort: Boolean,
20529
20961
  sortAscIcon: {
20530
20962
  type: IconValue,
@@ -20571,11 +21003,12 @@ const VDataTableHeaders = genericComponent()({
20571
21003
  loaderClasses
20572
21004
  } = useLoader(props);
20573
21005
  function getFixedStyles(column, y) {
20574
- if (!(props.sticky || props.fixedHeader) && !(column.fixed || column.lastFixed)) return undefined;
21006
+ if (!(props.sticky || props.fixedHeader) && !column.fixed) return undefined;
21007
+ const fixedSide = typeof column.fixed === 'string' ? column.fixed : column.fixed ? 'start' : 'none';
20575
21008
  return {
20576
21009
  position: 'sticky',
20577
- left: column.fixed || column.lastFixed ? convertToUnit(column.fixedOffset) : undefined,
20578
- right: column.lastFixed ? convertToUnit(column.fixedOffset ?? 0) : undefined,
21010
+ left: fixedSide === 'start' ? convertToUnit(column.fixedOffset) : undefined,
21011
+ right: fixedSide === 'end' ? convertToUnit(column.fixedEndOffset) : undefined,
20579
21012
  top: props.sticky || props.fixedHeader ? `calc(var(--v-table-header-height) * ${y})` : undefined
20580
21013
  };
20581
21014
  }
@@ -20635,14 +21068,15 @@ const VDataTableHeaders = genericComponent()({
20635
21068
  },
20636
21069
  "colspan": column.colspan,
20637
21070
  "rowspan": column.rowspan,
20638
- "onClick": column.sortable ? () => toggleSort(column) : undefined,
20639
21071
  "fixed": column.fixed,
20640
21072
  "nowrap": column.nowrap,
20641
21073
  "lastFixed": column.lastFixed,
20642
- "noPadding": noPadding
20643
- }, headerProps, {
20644
- "onKeydown": event => column.sortable && handleEnterKeyPress(event, column)
20645
- }), {
21074
+ "firstFixedEnd": column.firstFixedEnd,
21075
+ "noPadding": noPadding,
21076
+ "tabindex": column.sortable ? 0 : undefined,
21077
+ "onClick": column.sortable ? () => toggleSort(column) : undefined,
21078
+ "onKeydown": column.sortable ? event => handleEnterKeyPress(event, column) : undefined
21079
+ }, headerProps), {
20646
21080
  default: () => {
20647
21081
  const columnSlotName = `header.${column.key}`;
20648
21082
  const columnSlotProps = {
@@ -20918,7 +21352,9 @@ const VDataTableRow = genericComponent()({
20918
21352
  },
20919
21353
  "fixed": column.fixed,
20920
21354
  "fixedOffset": column.fixedOffset,
21355
+ "fixedEndOffset": column.fixedEndOffset,
20921
21356
  "lastFixed": column.lastFixed,
21357
+ "firstFixedEnd": column.firstFixedEnd,
20922
21358
  "maxWidth": !mobile.value ? column.maxWidth : undefined,
20923
21359
  "noPadding": column.key === 'data-table-select' || column.key === 'data-table-expand',
20924
21360
  "nowrap": column.nowrap,
@@ -22328,10 +22764,9 @@ function useCalendar(props) {
22328
22764
  const date = adapter.setYear(adapter.startOfMonth(adapter.date()), adapter.getYear(year.value));
22329
22765
  return adapter.setMonth(date, value);
22330
22766
  }, v => adapter.getMonth(v));
22331
- const weekDays = computed(() => {
22767
+ const weekdayLabels = computed(() => {
22332
22768
  const firstDayOfWeek = adapter.toJsDate(adapter.startOfWeek(adapter.date(), props.firstDayOfWeek)).getDay();
22333
- // Always generate all days, regardless of props.weekdays
22334
- return [0, 1, 2, 3, 4, 5, 6].map(day => (day + firstDayOfWeek) % 7);
22769
+ return adapter.getWeekdays(props.firstDayOfWeek, props.weekdayFormat).filter((_, i) => props.weekdays.includes((i + firstDayOfWeek) % 7));
22335
22770
  });
22336
22771
  const weeksInMonth = computed(() => {
22337
22772
  const weeks = adapter.getWeekArray(month.value, props.firstDayOfWeek);
@@ -22355,13 +22790,14 @@ function useCalendar(props) {
22355
22790
  });
22356
22791
  function genDays(days, today) {
22357
22792
  return days.filter(date => {
22358
- return weekDays.value.includes(adapter.toJsDate(date).getDay());
22793
+ return props.weekdays.includes(adapter.toJsDate(date).getDay());
22359
22794
  }).map((date, index) => {
22360
22795
  const isoDate = adapter.toISO(date);
22361
22796
  const isAdjacent = !adapter.isSameMonth(date, month.value);
22362
22797
  const isStart = adapter.isSameDay(date, adapter.startOfMonth(month.value));
22363
22798
  const isEnd = adapter.isSameDay(date, adapter.endOfMonth(month.value));
22364
22799
  const isSame = adapter.isSameDay(date, month.value);
22800
+ const weekdaysCount = props.weekdays.length;
22365
22801
  return {
22366
22802
  date,
22367
22803
  formatted: adapter.format(date, 'keyboardDate'),
@@ -22373,8 +22809,8 @@ function useCalendar(props) {
22373
22809
  isSelected: model.value.some(value => adapter.isSameDay(date, value)),
22374
22810
  isStart,
22375
22811
  isToday: adapter.isSameDay(date, today),
22376
- isWeekEnd: index % 7 === 6,
22377
- isWeekStart: index % 7 === 0,
22812
+ isWeekEnd: index % weekdaysCount === weekdaysCount - 1,
22813
+ isWeekStart: index % weekdaysCount === 0,
22378
22814
  isoDate,
22379
22815
  localized: adapter.format(date, 'dayOfMonth'),
22380
22816
  month: adapter.getMonth(date),
@@ -22412,7 +22848,7 @@ function useCalendar(props) {
22412
22848
  if (typeof props.allowedDates === 'function') {
22413
22849
  return !props.allowedDates(date);
22414
22850
  }
22415
- return !props.weekdays.includes(adapter.toJsDate(date).getDay());
22851
+ return false;
22416
22852
  }
22417
22853
  return {
22418
22854
  displayValue,
@@ -22421,7 +22857,7 @@ function useCalendar(props) {
22421
22857
  genDays,
22422
22858
  model,
22423
22859
  weeksInMonth,
22424
- weekDays,
22860
+ weekdayLabels,
22425
22861
  weekNumbers
22426
22862
  };
22427
22863
  }
@@ -22460,7 +22896,8 @@ const VDatePickerMonth = genericComponent()({
22460
22896
  const {
22461
22897
  daysInMonth,
22462
22898
  model,
22463
- weekNumbers
22899
+ weekNumbers,
22900
+ weekdayLabels
22464
22901
  } = useCalendar(props);
22465
22902
  const adapter = useDate();
22466
22903
  const rangeStart = shallowRef();
@@ -22532,7 +22969,10 @@ const VDatePickerMonth = genericComponent()({
22532
22969
  }
22533
22970
  }
22534
22971
  useRender(() => createElementVNode("div", {
22535
- "class": "v-date-picker-month"
22972
+ "class": "v-date-picker-month",
22973
+ "style": {
22974
+ '--v-date-picker-days-in-week': props.weekdays.length
22975
+ }
22536
22976
  }, [props.showWeek && createElementVNode("div", {
22537
22977
  "key": "weeks",
22538
22978
  "class": "v-date-picker-month__weeks"
@@ -22548,7 +22988,7 @@ const VDatePickerMonth = genericComponent()({
22548
22988
  "ref": daysRef,
22549
22989
  "key": daysInMonth.value[0].date?.toString(),
22550
22990
  "class": "v-date-picker-month__days"
22551
- }, [!props.hideWeekdays && adapter.getWeekdays(props.firstDayOfWeek, props.weekdayFormat).map(weekDay => createElementVNode("div", {
22991
+ }, [!props.hideWeekdays && weekdayLabels.value.map(weekDay => createElementVNode("div", {
22552
22992
  "class": normalizeClass(['v-date-picker-month__day', 'v-date-picker-month__weekday'])
22553
22993
  }, [weekDay])), daysInMonth.value.map((item, i) => {
22554
22994
  const slotProps = {
@@ -22931,7 +23371,8 @@ const VDatePicker = genericComponent()({
22931
23371
  }
22932
23372
  function allowedMonths(month) {
22933
23373
  if (typeof props.allowedDates === 'function') {
22934
- const startOfMonth = adapter.parseISO(`${year.value}-${month + 1}-01`);
23374
+ const monthTwoDigits = String(month + 1).padStart(2, '0');
23375
+ const startOfMonth = adapter.parseISO(`${year.value}-${monthTwoDigits}-01`);
22935
23376
  return isAllowedInRange(startOfMonth, adapter.endOfMonth(startOfMonth));
22936
23377
  }
22937
23378
  if (Array.isArray(props.allowedDates) && props.allowedDates.length) {
@@ -25228,6 +25669,8 @@ function useHold(_ref) {
25228
25669
  function holdStart(value) {
25229
25670
  holdStop();
25230
25671
  tick(value);
25672
+ window.addEventListener('pointerup', holdStop);
25673
+ document.addEventListener('blur', holdStop);
25231
25674
  timeout = window.setTimeout(() => {
25232
25675
  interval = window.setInterval(() => tick(value), HOLD_REPEAT);
25233
25676
  }, HOLD_DELAY);
@@ -25235,6 +25678,8 @@ function useHold(_ref) {
25235
25678
  function holdStop() {
25236
25679
  window.clearTimeout(timeout);
25237
25680
  window.clearInterval(interval);
25681
+ window.removeEventListener('pointerup', holdStop);
25682
+ document.removeEventListener('blur', holdStop);
25238
25683
  }
25239
25684
  function tick(value) {
25240
25685
  toggleUpDown(value === 'up');
@@ -25370,7 +25815,7 @@ const VNumberInput = genericComponent()({
25370
25815
  onClick: onControlClick,
25371
25816
  onPointerup: onControlMouseup,
25372
25817
  onPointerdown: onUpControlMousedown,
25373
- onPointercancel: onControlPointerCancel
25818
+ onPointercancel: onControlMouseup
25374
25819
  }
25375
25820
  };
25376
25821
  const decrementSlotProps = {
@@ -25378,7 +25823,7 @@ const VNumberInput = genericComponent()({
25378
25823
  onClick: onControlClick,
25379
25824
  onPointerup: onControlMouseup,
25380
25825
  onPointerdown: onDownControlMousedown,
25381
- onPointercancel: onControlPointerCancel
25826
+ onPointercancel: onControlMouseup
25382
25827
  }
25383
25828
  };
25384
25829
  watch(() => props.precision, () => formatInputValue());
@@ -25459,7 +25904,6 @@ const VNumberInput = genericComponent()({
25459
25904
  const el = e.currentTarget;
25460
25905
  el?.releasePointerCapture(e.pointerId);
25461
25906
  e.preventDefault();
25462
- e.stopPropagation();
25463
25907
  holdStop();
25464
25908
  }
25465
25909
  function onUpControlMousedown(e) {
@@ -25476,11 +25920,6 @@ const VNumberInput = genericComponent()({
25476
25920
  e.stopPropagation();
25477
25921
  holdStart('down');
25478
25922
  }
25479
- function onControlPointerCancel(e) {
25480
- const el = e.currentTarget;
25481
- el?.releasePointerCapture(e.pointerId);
25482
- holdStop();
25483
- }
25484
25923
  function clampModel() {
25485
25924
  if (controlsDisabled.value) return;
25486
25925
  if (!vTextFieldRef.value) return;
@@ -25527,7 +25966,7 @@ const VNumberInput = genericComponent()({
25527
25966
  "onClick": onControlClick,
25528
25967
  "onPointerdown": onUpControlMousedown,
25529
25968
  "onPointerup": onControlMouseup,
25530
- "onPointercancel": onControlPointerCancel,
25969
+ "onPointercancel": onControlMouseup,
25531
25970
  "size": controlNodeSize.value,
25532
25971
  "tabindex": "-1"
25533
25972
  }, null) : createVNode(VDefaultsProvider, {
@@ -25557,7 +25996,7 @@ const VNumberInput = genericComponent()({
25557
25996
  "onClick": onControlClick,
25558
25997
  "onPointerdown": onDownControlMousedown,
25559
25998
  "onPointerup": onControlMouseup,
25560
- "onPointercancel": onControlPointerCancel,
25999
+ "onPointercancel": onControlMouseup,
25561
26000
  "size": controlNodeSize.value,
25562
26001
  "tabindex": "-1"
25563
26002
  }, null) : createVNode(VDefaultsProvider, {
@@ -25704,19 +26143,21 @@ const VOtpInput = genericComponent()({
25704
26143
  const contentRef = ref();
25705
26144
  const inputRef = ref([]);
25706
26145
  const current = computed(() => inputRef.value[focusIndex.value]);
25707
- const intersectScope = effectScope();
25708
- intersectScope.run(() => {
25709
- const {
25710
- intersectionRef,
25711
- isIntersecting
25712
- } = useIntersectionObserver();
25713
- watch(isIntersecting, v => {
25714
- if (!v) return;
25715
- intersectionRef.value?.focus();
25716
- intersectScope.stop();
25717
- });
25718
- watchEffect(() => {
25719
- intersectionRef.value = inputRef.value[0];
26146
+ useToggleScope(() => props.autofocus, () => {
26147
+ const intersectScope = effectScope();
26148
+ intersectScope.run(() => {
26149
+ const {
26150
+ intersectionRef,
26151
+ isIntersecting
26152
+ } = useIntersectionObserver();
26153
+ watchEffect(() => {
26154
+ intersectionRef.value = inputRef.value[0];
26155
+ });
26156
+ watch(isIntersecting, v => {
26157
+ if (!v) return;
26158
+ intersectionRef.value?.focus();
26159
+ intersectScope.stop();
26160
+ });
25720
26161
  });
25721
26162
  });
25722
26163
  function onInput() {
@@ -29727,6 +30168,8 @@ const VTreeviewSymbol = Symbol.for('vuetify:v-treeview');
29727
30168
 
29728
30169
  const makeVTreeviewItemProps = propsFactory({
29729
30170
  loading: Boolean,
30171
+ hideActions: Boolean,
30172
+ indentLines: Array,
29730
30173
  toggleIcon: IconValue,
29731
30174
  ...makeVListItemProps({
29732
30175
  slim: true
@@ -29762,23 +30205,31 @@ const VTreeviewItem = genericComponent()({
29762
30205
  emit('toggleExpand', e);
29763
30206
  }
29764
30207
  useRender(() => {
29765
- const listItemProps = omit(VListItem.filterProps(props), ['onClick']);
29766
- const hasPrepend = slots.prepend || props.toggleIcon;
30208
+ const listItemProps = VListItem.filterProps(props);
30209
+ const hasPrepend = slots.prepend || props.toggleIcon || props.indentLines;
29767
30210
  return createVNode(VListItem, mergeProps({
29768
30211
  "ref": vListItemRef
29769
30212
  }, listItemProps, {
29770
- "active": vListItemRef.value?.isActivated,
30213
+ "active": vListItemRef.value?.isActivated || undefined,
29771
30214
  "class": ['v-treeview-item', {
29772
30215
  'v-treeview-item--activatable-group-activator': isActivatableGroupActivator.value,
29773
30216
  'v-treeview-item--filtered': isFiltered.value
29774
30217
  }, props.class],
29775
30218
  "ripple": false,
29776
- "onClick": props.onClick ?? activateGroupActivator
30219
+ "onClick": activateGroupActivator
29777
30220
  }), {
29778
30221
  ...slots,
29779
30222
  prepend: hasPrepend ? slotProps => {
29780
- return createElementVNode(Fragment, null, [createVNode(VListItemAction, {
29781
- "start": false
30223
+ return createElementVNode(Fragment, null, [props.indentLines && props.indentLines.length > 0 ? createElementVNode("div", {
30224
+ "key": "indent-lines",
30225
+ "class": "v-treeview-indent-lines",
30226
+ "style": {
30227
+ '--v-indent-parts': props.indentLines.length
30228
+ }
30229
+ }, [props.indentLines.map(type => createElementVNode("div", {
30230
+ "class": normalizeClass(`v-treeview-indent-line v-treeview-indent-line--${type}`)
30231
+ }, null))]) : '', !props.hideActions && createVNode(VListItemAction, {
30232
+ "start": true
29782
30233
  }, {
29783
30234
  default: () => [props.toggleIcon ? createVNode(VBtn, {
29784
30235
  "density": "compact",
@@ -29787,13 +30238,11 @@ const VTreeviewItem = genericComponent()({
29787
30238
  "variant": "text",
29788
30239
  "onClick": onClickAction
29789
30240
  }, {
29790
- loader() {
29791
- return createVNode(VProgressCircular, {
29792
- "indeterminate": "disable-shrink",
29793
- "size": "20",
29794
- "width": "2"
29795
- }, null);
29796
- }
30241
+ loader: () => createVNode(VProgressCircular, {
30242
+ "indeterminate": "disable-shrink",
30243
+ "size": "20",
30244
+ "width": "2"
30245
+ }, null)
29797
30246
  }) : createElementVNode("div", {
29798
30247
  "class": "v-treeview-item__level"
29799
30248
  }, null)]
@@ -29801,7 +30250,7 @@ const VTreeviewItem = genericComponent()({
29801
30250
  } : undefined
29802
30251
  });
29803
30252
  });
29804
- return {};
30253
+ return forwardRefs({}, vListItemRef);
29805
30254
  }
29806
30255
  });
29807
30256
 
@@ -29826,14 +30275,20 @@ const makeVTreeviewChildrenProps = propsFactory({
29826
30275
  falseIcon: IconValue,
29827
30276
  trueIcon: IconValue,
29828
30277
  returnObject: Boolean,
30278
+ activatable: Boolean,
29829
30279
  selectable: Boolean,
29830
30280
  selectedColor: String,
29831
30281
  selectStrategy: [String, Function, Object],
29832
30282
  index: Number,
30283
+ isLastGroup: Boolean,
30284
+ separateRoots: Boolean,
30285
+ parentIndentLines: Array,
30286
+ indentLinesVariant: String,
29833
30287
  path: {
29834
30288
  type: Array,
29835
30289
  default: () => []
29836
30290
  },
30291
+ ...pick(makeVTreeviewItemProps(), ['hideActions']),
29837
30292
  ...makeDensityProps()
29838
30293
  }, 'VTreeviewChildren');
29839
30294
  const VTreeviewChildren = genericComponent()({
@@ -29844,7 +30299,8 @@ const VTreeviewChildren = genericComponent()({
29844
30299
  slots
29845
30300
  } = _ref;
29846
30301
  const isLoading = reactive(new Set());
29847
- const isClickOnOpen = computed(() => !props.disabled && (props.openOnClick != null ? props.openOnClick : props.selectable));
30302
+ const activatorItems = ref([]);
30303
+ const isClickOnOpen = computed(() => !props.disabled && (props.openOnClick != null ? props.openOnClick : props.selectable && !props.activatable));
29848
30304
  async function checkChildren(item) {
29849
30305
  try {
29850
30306
  if (!props.items?.length || !props.loadChildren) return;
@@ -29858,22 +30314,35 @@ const VTreeviewChildren = genericComponent()({
29858
30314
  }
29859
30315
  function selectItem(select, isSelected) {
29860
30316
  if (props.selectable) {
29861
- select(!isSelected);
30317
+ select(isSelected);
29862
30318
  }
29863
30319
  }
29864
- return () => slots.default?.() ?? props.items?.map((item, index) => {
30320
+ return () => slots.default?.() ?? props.items?.map((item, index, items) => {
29865
30321
  const {
29866
30322
  children,
29867
30323
  props: itemProps
29868
30324
  } = item;
29869
30325
  const loading = isLoading.has(item.value);
30326
+ const nextItemHasChildren = !!items.at(index + 1)?.children;
30327
+ const depth = props.path?.length ?? 0;
30328
+ const isLast = items.length - 1 === index;
29870
30329
  const treeItemProps = {
29871
30330
  index,
29872
- depth: props.path?.length ?? 0,
30331
+ depth,
29873
30332
  isFirst: index === 0,
29874
- isLast: props.items ? props.items.length - 1 === index : false,
29875
- path: [...props.path, index]
30333
+ isLast,
30334
+ path: [...props.path, index],
30335
+ hideAction: props.hideActions
29876
30336
  };
30337
+ const indentLines = getIndentLines({
30338
+ depth,
30339
+ isLast,
30340
+ isLastGroup: props.isLastGroup,
30341
+ leafLinks: !props.hideActions,
30342
+ separateRoots: props.separateRoots,
30343
+ parentIndentLines: props.parentIndentLines,
30344
+ variant: props.indentLinesVariant
30345
+ });
29877
30346
  const slotsWithItem = {
29878
30347
  prepend: slotProps => createElementVNode(Fragment, null, [props.selectable && (!children || children && !['leaf', 'single-leaf'].includes(props.selectStrategy)) && createElementVNode("div", null, [createVNode(VCheckboxBtn, {
29879
30348
  "key": item.value,
@@ -29886,7 +30355,8 @@ const VTreeviewChildren = genericComponent()({
29886
30355
  "indeterminateIcon": props.indeterminateIcon,
29887
30356
  "falseIcon": props.falseIcon,
29888
30357
  "trueIcon": props.trueIcon,
29889
- "onClick": withModifiers(() => selectItem(slotProps.select, slotProps.isSelected), ['stop']),
30358
+ "onUpdate:modelValue": v => selectItem(slotProps.select, v),
30359
+ "onClick": e => e.stopPropagation(),
29890
30360
  "onKeydown": e => {
29891
30361
  if (!['Enter', 'Space'].includes(e.key)) return;
29892
30362
  e.stopPropagation();
@@ -29933,24 +30403,45 @@ const VTreeviewChildren = genericComponent()({
29933
30403
  ...activatorProps,
29934
30404
  value: itemProps?.value,
29935
30405
  onToggleExpand: [() => checkChildren(item), activatorProps.onClick],
29936
- onClick: isClickOnOpen.value ? [() => checkChildren(item), activatorProps.onClick] : undefined
30406
+ onClick: isClickOnOpen.value ? [() => checkChildren(item), activatorProps.onClick] : () => selectItem(activatorItems.value[index]?.select, !activatorItems.value[index]?.isSelected)
29937
30407
  };
29938
- return createVNode(VTreeviewItem, mergeProps(listItemProps, {
30408
+ return createVNode(VTreeviewItem, mergeProps({
30409
+ "ref": el => activatorItems.value[index] = el
30410
+ }, listItemProps, {
30411
+ "hideActions": props.hideActions,
30412
+ "indentLines": indentLines.node,
29939
30413
  "value": props.returnObject ? item.raw : itemProps.value,
29940
30414
  "loading": loading
29941
30415
  }), slotsWithItem);
29942
30416
  },
29943
30417
  default: () => createVNode(VTreeviewChildren, mergeProps(treeviewChildrenProps, {
29944
30418
  "items": children,
30419
+ "indentLinesVariant": props.indentLinesVariant,
30420
+ "parentIndentLines": indentLines.children,
30421
+ "isLastGroup": nextItemHasChildren,
29945
30422
  "returnObject": props.returnObject
29946
30423
  }), slots)
29947
- }) : slots.item?.({
30424
+ }) : renderSlot(slots.item, {
29948
30425
  props: itemProps,
29949
30426
  item: item.raw,
29950
30427
  internalItem: item
29951
- }) ?? createVNode(VTreeviewItem, mergeProps(itemProps, {
29952
- "value": props.returnObject ? toRaw(item.raw) : itemProps.value
29953
- }), slotsWithItem);
30428
+ }, () => {
30429
+ if (item.type === 'divider') {
30430
+ return renderSlot(slots.divider, {
30431
+ props: item.raw
30432
+ }, () => createVNode(VDivider, item.props, null));
30433
+ }
30434
+ if (item.type === 'subheader') {
30435
+ return renderSlot(slots.subheader, {
30436
+ props: item.raw
30437
+ }, () => createVNode(VListSubheader, item.props, null));
30438
+ }
30439
+ return createVNode(VTreeviewItem, mergeProps(itemProps, {
30440
+ "hideActions": props.hideActions,
30441
+ "indentLines": indentLines.leaf,
30442
+ "value": props.returnObject ? toRaw(item.raw) : itemProps.value
30443
+ }), slotsWithItem);
30444
+ });
29954
30445
  });
29955
30446
  }
29956
30447
  });
@@ -29966,20 +30457,18 @@ function flatten(items) {
29966
30457
  const makeVTreeviewProps = propsFactory({
29967
30458
  fluid: Boolean,
29968
30459
  openAll: Boolean,
30460
+ indentLines: [Boolean, String],
29969
30461
  search: String,
29970
30462
  ...makeFilterProps({
29971
30463
  filterKeys: ['title']
29972
30464
  }),
29973
- ...omit(makeVTreeviewChildrenProps(), ['index', 'path']),
30465
+ ...omit(makeVTreeviewChildrenProps(), ['index', 'path', 'indentLinesVariant', 'parentIndentLines', 'isLastGroup']),
29974
30466
  ...omit(makeVListProps({
29975
30467
  collapseIcon: '$treeviewCollapse',
29976
30468
  expandIcon: '$treeviewExpand',
29977
30469
  slim: true
29978
- }), ['itemType', 'nav', 'openStrategy']),
29979
- modelValue: {
29980
- type: Array,
29981
- default: () => []
29982
- }
30470
+ }), ['nav', 'openStrategy']),
30471
+ modelValue: Array
29983
30472
  }, 'VTreeview');
29984
30473
  const VTreeview = genericComponent()({
29985
30474
  name: 'VTreeview',
@@ -29994,7 +30483,8 @@ const VTreeview = genericComponent()({
29994
30483
  },
29995
30484
  setup(props, _ref) {
29996
30485
  let {
29997
- slots
30486
+ slots,
30487
+ emit
29998
30488
  } = _ref;
29999
30489
  const {
30000
30490
  items
@@ -30003,13 +30493,12 @@ const VTreeview = genericComponent()({
30003
30493
  const baseColor = toRef(() => props.baseColor);
30004
30494
  const color = toRef(() => props.color);
30005
30495
  const activated = useProxiedModel(props, 'activated');
30006
- const model = useProxiedModel(props, 'modelValue');
30007
- const _selected = useProxiedModel(props, 'selected', props.modelValue);
30496
+ const _selected = useProxiedModel(props, 'selected');
30008
30497
  const selected = computed({
30009
- get: () => _selected.value,
30498
+ get: () => props.modelValue ?? _selected.value,
30010
30499
  set(val) {
30011
30500
  _selected.value = val;
30012
- model.value = val;
30501
+ emit('update:modelValue', val);
30013
30502
  }
30014
30503
  });
30015
30504
  const vListRef = ref();
@@ -30075,6 +30564,7 @@ const VTreeview = genericComponent()({
30075
30564
  useRender(() => {
30076
30565
  const listProps = VList.filterProps(props);
30077
30566
  const treeviewChildrenProps = VTreeviewChildren.filterProps(props);
30567
+ const indentLinesVariant = typeof props.indentLines === 'boolean' ? 'default' : props.indentLines;
30078
30568
  return createVNode(VList, mergeProps({
30079
30569
  "ref": vListRef
30080
30570
  }, listProps, {
@@ -30092,7 +30582,9 @@ const VTreeview = genericComponent()({
30092
30582
  default: () => [createVNode(VTreeviewChildren, mergeProps(treeviewChildrenProps, {
30093
30583
  "density": props.density,
30094
30584
  "returnObject": props.returnObject,
30095
- "items": items.value
30585
+ "items": items.value,
30586
+ "parentIndentLines": props.indentLines ? [] : undefined,
30587
+ "indentLinesVariant": indentLinesVariant
30096
30588
  }), slots)]
30097
30589
  });
30098
30590
  });
@@ -30181,7 +30673,7 @@ const VCalendarIntervalEvent = genericComponent()({
30181
30673
  }
30182
30674
  };
30183
30675
  useRender(() => {
30184
- return createElementVNode("div", null, [slots.intervalEvent?.({
30676
+ return createElementVNode("div", null, [slots['interval-event']?.({
30185
30677
  height: calcHeight().height,
30186
30678
  margin: calcHeight().margin,
30187
30679
  eventClass: 'v-calendar-internal-event',
@@ -30278,13 +30770,13 @@ const VCalendarInterval = genericComponent()({
30278
30770
  "style": normalizeStyle(`height: ${convertToUnit(props.intervalHeight)}`)
30279
30771
  }, [createElementVNode("div", mergeProps({
30280
30772
  "class": "v-calendar-day__row-label"
30281
- }, getPrefixedEventHandlers(attrs, ':time', () => props)), [slots.intervalTitle?.({
30773
+ }, getPrefixedEventHandlers(attrs, ':time', () => props)), [slots['interval-title']?.({
30282
30774
  interval: interval.value
30283
30775
  }) ?? (props.index ? props.intervalFormat ? typeof props.intervalFormat === 'string' ? adapter.format(interval.value.start, 'hours12h') : props.intervalFormat(interval.value) : interval.value.label : '12 AM')]), createElementVNode("div", {
30284
30776
  "class": "v-calendar-day__row-hairline"
30285
30777
  }, null), createElementVNode("div", mergeProps({
30286
30778
  "class": ['v-calendar-day__row-content', interval.value.events.some(e => !e.last) ? 'v-calendar-day__row-content-through' : '']
30287
- }, getPrefixedEventHandlers(attrs, ':interval', () => interval.value)), [slots.intervalBody?.({
30779
+ }, getPrefixedEventHandlers(attrs, ':interval', () => interval.value)), [slots['interval-body']?.({
30288
30780
  interval: interval.value
30289
30781
  }) ?? createElementVNode("div", null, [interval.value.events?.map(event => createVNode(VCalendarIntervalEvent, mergeProps({
30290
30782
  "event": event,
@@ -30293,8 +30785,8 @@ const VCalendarInterval = genericComponent()({
30293
30785
  "intervalDuration": props.intervalDuration,
30294
30786
  "intervalHeight": props.intervalHeight
30295
30787
  }, attrs), {
30296
- ...(slots.intervalEvent ? {
30297
- intervalEvent: _ref2 => {
30788
+ ...(slots['interval-event'] ? {
30789
+ 'interval-event': _ref2 => {
30298
30790
  let {
30299
30791
  height,
30300
30792
  margin,
@@ -30302,7 +30794,7 @@ const VCalendarInterval = genericComponent()({
30302
30794
  event,
30303
30795
  interval
30304
30796
  } = _ref2;
30305
- return slots.intervalEvent?.({
30797
+ return slots['interval-event']?.({
30306
30798
  height,
30307
30799
  margin,
30308
30800
  eventClass,
@@ -30316,7 +30808,7 @@ const VCalendarInterval = genericComponent()({
30316
30808
  "style": normalizeStyle(`height: ${convertToUnit(props.intervalHeight)}`)
30317
30809
  }, [createElementVNode("div", mergeProps({
30318
30810
  "class": ['v-calendar-day__row-content', interval.value.events.some(e => !e.last) ? 'v-calendar-day__row-content-through' : '']
30319
- }, getPrefixedEventHandlers(attrs, ':interval', () => interval.value)), [slots.intervalBody?.({
30811
+ }, getPrefixedEventHandlers(attrs, ':interval', () => interval.value)), [slots['interval-body']?.({
30320
30812
  interval: interval.value
30321
30813
  }) ?? interval.value.events?.map(event => createVNode(VCalendarIntervalEvent, mergeProps({
30322
30814
  "event": event,
@@ -30325,8 +30817,8 @@ const VCalendarInterval = genericComponent()({
30325
30817
  "intervalDuration": props.intervalDuration,
30326
30818
  "intervalHeight": props.intervalHeight
30327
30819
  }, attrs), {
30328
- ...(slots.intervalEvent ? {
30329
- intervalEvent: _ref3 => {
30820
+ ...(slots['interval-event'] ? {
30821
+ 'interval-event': _ref3 => {
30330
30822
  let {
30331
30823
  height,
30332
30824
  margin,
@@ -30334,7 +30826,7 @@ const VCalendarInterval = genericComponent()({
30334
30826
  event,
30335
30827
  interval
30336
30828
  } = _ref3;
30337
- return slots.intervalEvent?.({
30829
+ return slots['interval-event']?.({
30338
30830
  height,
30339
30831
  margin,
30340
30832
  eventClass,
@@ -30389,7 +30881,7 @@ const VCalendarDay = genericComponent()({
30389
30881
  }), null)])]), intervals.value.map((_, index) => slots.interval?.(calendarIntervalProps) ?? createVNode(VCalendarInterval, mergeProps({
30390
30882
  "index": index
30391
30883
  }, calendarIntervalProps, attrs, getPrefixedEventHandlers(attrs, ':interval', () => calendarIntervalProps)), {
30392
- ...pick(slots, ['intervalBody', 'intervalEvent', 'intervalTitle'])
30884
+ ...pick(slots, ['interval-body', 'interval-event', 'interval-title'])
30393
30885
  }))]);
30394
30886
  });
30395
30887
  return {
@@ -30533,7 +31025,7 @@ const VCalendarMonthDay = genericComponent()({
30533
31025
  }, getPrefixedEventHandlers(attrs, ':day', () => props)), [!props.day?.isHidden ? createElementVNode("div", {
30534
31026
  "key": "title",
30535
31027
  "class": "v-calendar-weekly__day-label"
30536
- }, [slots.dayTitle?.({
31028
+ }, [slots['day-title']?.({
30537
31029
  title: props.title
30538
31030
  }) ?? createVNode(VBtn, mergeProps({
30539
31031
  "class": props.day?.isToday ? 'v-calendar-weekly__day-label__today' : undefined,
@@ -30546,12 +31038,12 @@ const VCalendarMonthDay = genericComponent()({
30546
31038
  }, getPrefixedEventHandlers(attrs, ':date', () => props)), null)]) : undefined, !props.day?.isHidden ? createElementVNode("div", {
30547
31039
  "key": "content",
30548
31040
  "class": "v-calendar-weekly__day-content"
30549
- }, [slots.dayBody?.({
31041
+ }, [slots['day-body']?.({
30550
31042
  day: props.day,
30551
31043
  events: props.events
30552
31044
  }) ?? createElementVNode("div", null, [createElementVNode("div", {
30553
31045
  "class": "v-calendar-weekly__day-alldayevents-container"
30554
- }, [props.events?.filter(event => event.allDay).map(event => slots.dayEvent ? slots.dayEvent({
31046
+ }, [props.events?.filter(event => event.allDay).map(event => slots['day-event'] ? slots['day-event']({
30555
31047
  day: props.day,
30556
31048
  allDay: true,
30557
31049
  event
@@ -30561,7 +31053,7 @@ const VCalendarMonthDay = genericComponent()({
30561
31053
  "allDay": true
30562
31054
  }, attrs), null))]), createElementVNode("div", {
30563
31055
  "class": "v-calendar-weekly__day-events-container"
30564
- }, [props.events?.filter(event => !event.allDay).map(event => slots.dayEvent ? slots.dayEvent({
31056
+ }, [props.events?.filter(event => !event.allDay).map(event => slots['day-event'] ? slots['day-event']({
30565
31057
  day: props.day,
30566
31058
  event,
30567
31059
  allDay: false
@@ -30606,9 +31098,8 @@ const VCalendar = genericComponent()({
30606
31098
  model,
30607
31099
  displayValue,
30608
31100
  weekNumbers,
30609
- weekDays
31101
+ weekdayLabels
30610
31102
  } = useCalendar(props);
30611
- const dayNames = adapter.getWeekdays();
30612
31103
  function onClickNext() {
30613
31104
  if (props.viewMode === 'month') {
30614
31105
  model.value = [adapter.addMonths(displayValue.value, 1)];
@@ -30646,6 +31137,7 @@ const VCalendar = genericComponent()({
30646
31137
  useRender(() => {
30647
31138
  const calendarDayProps = VCalendarDay.filterProps(props);
30648
31139
  const calendarHeaderProps = VCalendarHeader.filterProps(props);
31140
+ const weekdaysCount = daysInWeek.value.length;
30649
31141
  return createElementVNode("div", {
30650
31142
  "class": normalizeClass(['v-calendar', {
30651
31143
  'v-calendar-monthly': props.viewMode === 'month',
@@ -30667,25 +31159,25 @@ const VCalendar = genericComponent()({
30667
31159
  }), {
30668
31160
  title: slots.title
30669
31161
  }))]), createElementVNode("div", {
30670
- "class": normalizeClass(['v-calendar__container', `days__${weekDays.value.length}`])
31162
+ "class": normalizeClass(['v-calendar__container', `days__${weekdaysCount}`])
30671
31163
  }, [props.viewMode === 'month' && !props.hideDayHeader && createElementVNode("div", {
30672
- "class": normalizeClass(['v-calendar-weekly__head', `days__${weekDays.value.length}`, ...(!props.hideWeekNumber ? ['v-calendar-weekly__head-weeknumbers'] : [])]),
31164
+ "class": normalizeClass(['v-calendar-weekly__head', `days__${weekdaysCount}`, ...(!props.hideWeekNumber ? ['v-calendar-weekly__head-weeknumbers'] : [])]),
30673
31165
  "key": "calendarWeeklyHead"
30674
31166
  }, [!props.hideWeekNumber ? createElementVNode("div", {
30675
31167
  "key": "weekNumber0",
30676
31168
  "class": "v-calendar-weekly__head-weeknumber"
30677
- }, null) : '', weekDays.value.map(weekday => createElementVNode("div", {
31169
+ }, null) : '', weekdayLabels.value.map(weekday => createElementVNode("div", {
30678
31170
  "class": normalizeClass(`v-calendar-weekly__head-weekday${!props.hideWeekNumber ? '-with-weeknumber' : ''}`)
30679
- }, [dayNames[weekday]]))]), props.viewMode === 'month' && createElementVNode("div", {
31171
+ }, [weekday]))]), props.viewMode === 'month' && createElementVNode("div", {
30680
31172
  "key": "VCalendarMonth",
30681
- "class": normalizeClass(['v-calendar-month__days', `days${!props.hideWeekNumber ? '-with-weeknumbers' : ''}__${weekDays.value.length}`, ...(!props.hideWeekNumber ? ['v-calendar-month__weeknumbers'] : [])])
30682
- }, [chunkArray(daysInMonth.value, weekDays.value.length).map((week, wi) => [!props.hideWeekNumber ? createElementVNode("div", mergeProps({
31173
+ "class": normalizeClass(['v-calendar-month__days', `days${!props.hideWeekNumber ? '-with-weeknumbers' : ''}__${weekdaysCount}`, ...(!props.hideWeekNumber ? ['v-calendar-month__weeknumbers'] : [])])
31174
+ }, [chunkArray(daysInMonth.value, weekdaysCount).map((week, wi) => [!props.hideWeekNumber ? createElementVNode("div", mergeProps({
30683
31175
  "class": "v-calendar-month__weeknumber"
30684
31176
  }, getPrefixedEventHandlers(attrs, ':weekNumber', () => ({
30685
31177
  weekNumber: weekNumbers.value[wi],
30686
31178
  week
30687
31179
  }))), [weekNumbers.value[wi]]) : '', week.map(day => createVNode(VCalendarMonthDay, mergeProps({
30688
- "key": day.date.getTime()
31180
+ "key": adapter.toJsDate(day.date).getTime()
30689
31181
  }, calendarDayProps, {
30690
31182
  "day": day,
30691
31183
  "title": adapter.format(day.date, 'dayOfMonth'),
@@ -30702,7 +31194,7 @@ const VCalendar = genericComponent()({
30702
31194
  "dayIndex": i,
30703
31195
  "events": props.events?.filter(e => adapter.isSameDay(e.start, day.date) || adapter.isSameDay(e.end, day.date))
30704
31196
  }, attrs), {
30705
- ...pick(slots, ['interval', 'intervalBody', 'intervalEvent', 'intervalTitle'])
31197
+ ...pick(slots, ['interval', 'interval-body', 'interval-event', 'interval-title'])
30706
31198
  })), props.viewMode === 'day' && (slots['day-interval'] ? slots['day-interval']({
30707
31199
  day: genDays([displayValue.value], adapter.date())[0],
30708
31200
  dayIndex: 0,
@@ -31617,6 +32109,7 @@ const VIconBtn = genericComponent()({
31617
32109
  opacity: props.opacity
31618
32110
  };
31619
32111
  return createVNode(props.tag, {
32112
+ "type": props.tag === 'button' ? 'button' : undefined,
31620
32113
  "class": normalizeClass([{
31621
32114
  'v-icon-btn': true,
31622
32115
  'v-icon-btn--active': isActive.value,
@@ -32275,6 +32768,398 @@ const VPullToRefresh = genericComponent()({
32275
32768
  }
32276
32769
  });
32277
32770
 
32771
+ // Types
32772
+
32773
+ // Display mode types for different visual representations
32774
+
32775
+ // Extended variant type that includes our custom 'contained' variant
32776
+
32777
+ // Key display tuple: [mode, content] where content is string or IconValue
32778
+
32779
+ // Key tuple: [mode, content] where content is string or IconValue
32780
+
32781
+ function processKey(config, requestedMode, isMac) {
32782
+ const keyCfg = isMac && config.mac ? config.mac : config.default;
32783
+
32784
+ // 1. Resolve the safest display mode for the current platform
32785
+ const mode = (() => {
32786
+ // Non-Mac platforms rarely use icons – prefer text
32787
+ if (requestedMode === 'icon' && !isMac) return 'text';
32788
+
32789
+ // If the requested mode lacks an asset, fall back to text
32790
+ if (requestedMode === 'icon' && !keyCfg.icon) return 'text';
32791
+ if (requestedMode === 'symbol' && !keyCfg.symbol) return 'text';
32792
+ return requestedMode;
32793
+ })();
32794
+
32795
+ // 2. Pick value for the chosen mode, defaulting to text representation
32796
+ let value = keyCfg[mode] ?? keyCfg.text;
32797
+
32798
+ // 3. Guard against icon tokens leaking into text mode (e.g. "$ctrl")
32799
+ if (mode === 'text' && typeof value === 'string' && value.startsWith('$') && !value.startsWith('$vuetify.')) {
32800
+ value = value.slice(1).toUpperCase(); // "$ctrl" → "CTRL"
32801
+ }
32802
+ return mode === 'icon' ? ['icon', value] : [mode, value];
32803
+ }
32804
+ const hotkeyMap = {
32805
+ ctrl: {
32806
+ mac: {
32807
+ symbol: '⌃',
32808
+ icon: '$ctrl',
32809
+ text: '$vuetify.hotkey.ctrl'
32810
+ },
32811
+ default: {
32812
+ text: 'Ctrl'
32813
+ }
32814
+ },
32815
+ meta: {
32816
+ mac: {
32817
+ symbol: '⌘',
32818
+ icon: '$command',
32819
+ text: '$vuetify.hotkey.command'
32820
+ },
32821
+ default: {
32822
+ text: 'Ctrl'
32823
+ }
32824
+ },
32825
+ cmd: {
32826
+ mac: {
32827
+ symbol: '⌘',
32828
+ icon: '$command',
32829
+ text: '$vuetify.hotkey.command'
32830
+ },
32831
+ default: {
32832
+ text: 'Ctrl'
32833
+ }
32834
+ },
32835
+ shift: {
32836
+ mac: {
32837
+ symbol: '⇧',
32838
+ icon: '$shift',
32839
+ text: '$vuetify.hotkey.shift'
32840
+ },
32841
+ default: {
32842
+ text: 'Shift'
32843
+ }
32844
+ },
32845
+ alt: {
32846
+ mac: {
32847
+ symbol: '⌥',
32848
+ icon: '$alt',
32849
+ text: '$vuetify.hotkey.option'
32850
+ },
32851
+ default: {
32852
+ text: 'Alt'
32853
+ }
32854
+ },
32855
+ enter: {
32856
+ default: {
32857
+ symbol: '↵',
32858
+ icon: '$enter',
32859
+ text: '$vuetify.hotkey.enter'
32860
+ }
32861
+ },
32862
+ arrowup: {
32863
+ default: {
32864
+ symbol: '↑',
32865
+ icon: '$arrowup',
32866
+ text: '$vuetify.hotkey.upArrow'
32867
+ }
32868
+ },
32869
+ arrowdown: {
32870
+ default: {
32871
+ symbol: '↓',
32872
+ icon: '$arrowdown',
32873
+ text: '$vuetify.hotkey.downArrow'
32874
+ }
32875
+ },
32876
+ arrowleft: {
32877
+ default: {
32878
+ symbol: '←',
32879
+ icon: '$arrowleft',
32880
+ text: '$vuetify.hotkey.leftArrow'
32881
+ }
32882
+ },
32883
+ arrowright: {
32884
+ default: {
32885
+ symbol: '→',
32886
+ icon: '$arrowright',
32887
+ text: '$vuetify.hotkey.rightArrow'
32888
+ }
32889
+ },
32890
+ backspace: {
32891
+ default: {
32892
+ symbol: '⌫',
32893
+ icon: '$backspace',
32894
+ text: '$vuetify.hotkey.backspace'
32895
+ }
32896
+ },
32897
+ escape: {
32898
+ default: {
32899
+ text: '$vuetify.hotkey.escape'
32900
+ }
32901
+ },
32902
+ ' ': {
32903
+ mac: {
32904
+ symbol: '␣',
32905
+ icon: '$space',
32906
+ text: '$vuetify.hotkey.space'
32907
+ },
32908
+ default: {
32909
+ text: '$vuetify.hotkey.space'
32910
+ }
32911
+ },
32912
+ '-': {
32913
+ default: {
32914
+ text: '-'
32915
+ }
32916
+ }
32917
+ };
32918
+
32919
+ // Create custom variant props that extend the base variant props with our 'contained' option
32920
+ const makeVHotkeyVariantProps = propsFactory({
32921
+ variant: {
32922
+ type: String,
32923
+ default: 'elevated',
32924
+ validator: v => ['elevated', 'flat', 'tonal', 'outlined', 'text', 'plain', 'contained'].includes(v)
32925
+ }
32926
+ }, 'VHotkeyVariant');
32927
+ const makeVHotkeyProps = propsFactory({
32928
+ // String representing keyboard shortcuts (e.g., "ctrl+k", "meta+shift+p")
32929
+ keys: String,
32930
+ // How to display keys: 'symbol' uses special characters (⌘, ⌃), 'icon' uses SVG icons, 'text' uses words
32931
+ displayMode: {
32932
+ type: String,
32933
+ default: 'icon'
32934
+ },
32935
+ // Custom key mapping configuration. Users can import and modify the exported hotkeyMap as needed
32936
+ keyMap: {
32937
+ type: Object,
32938
+ default: () => hotkeyMap
32939
+ },
32940
+ platform: {
32941
+ type: String,
32942
+ default: 'auto'
32943
+ },
32944
+ inline: Boolean,
32945
+ disabled: Boolean,
32946
+ prefix: String,
32947
+ suffix: String,
32948
+ ...makeComponentProps(),
32949
+ ...makeThemeProps(),
32950
+ ...makeBorderProps(),
32951
+ ...makeRoundedProps(),
32952
+ ...makeElevationProps(),
32953
+ ...makeVHotkeyVariantProps(),
32954
+ color: String
32955
+ }, 'VHotkey');
32956
+ class Delineator {
32957
+ constructor(delineator) {
32958
+ if (['and', 'then'].includes(delineator)) this.val = delineator;else {
32959
+ throw new Error('Not a valid delineator');
32960
+ }
32961
+ }
32962
+ isEqual(d) {
32963
+ return this.val === d.val;
32964
+ }
32965
+ }
32966
+ function isDelineator(value) {
32967
+ return value instanceof Delineator;
32968
+ }
32969
+ function isString(value) {
32970
+ return typeof value === 'string';
32971
+ }
32972
+ function getKeyText(keyMap, key, isMac) {
32973
+ const lowerKey = key.toLowerCase();
32974
+ if (lowerKey in keyMap) {
32975
+ const result = processKey(keyMap[lowerKey], 'text', isMac);
32976
+ return typeof result[1] === 'string' ? result[1] : String(result[1]);
32977
+ }
32978
+ return key.toUpperCase();
32979
+ }
32980
+ function applyDisplayModeToKey(keyMap, mode, key, isMac) {
32981
+ const lowerKey = key.toLowerCase();
32982
+ if (lowerKey in keyMap) {
32983
+ const result = processKey(keyMap[lowerKey], mode, isMac);
32984
+ if (result[0] === 'text' && typeof result[1] === 'string' && result[1].startsWith('$') && !result[1].startsWith('$vuetify.')) {
32985
+ return ['text', result[1].replace('$', '').toUpperCase(), key];
32986
+ }
32987
+ return [...result, key];
32988
+ }
32989
+ return ['text', key.toUpperCase(), key];
32990
+ }
32991
+ const VHotkey = genericComponent()({
32992
+ name: 'VHotkey',
32993
+ props: makeVHotkeyProps(),
32994
+ setup(props) {
32995
+ const {
32996
+ t
32997
+ } = useLocale();
32998
+ const {
32999
+ themeClasses
33000
+ } = provideTheme(props);
33001
+ const {
33002
+ rtlClasses
33003
+ } = useRtl();
33004
+ const {
33005
+ borderClasses
33006
+ } = useBorder(props);
33007
+ const {
33008
+ roundedClasses
33009
+ } = useRounded(props);
33010
+ const {
33011
+ elevationClasses
33012
+ } = useElevation(props);
33013
+ const isContainedVariant = computed(() => props.variant === 'contained');
33014
+ const effectiveVariantProps = computed(() => ({
33015
+ ...props,
33016
+ variant: isContainedVariant.value ? 'elevated' : props.variant
33017
+ }));
33018
+ const {
33019
+ colorClasses,
33020
+ colorStyles,
33021
+ variantClasses
33022
+ } = useVariant(effectiveVariantProps);
33023
+ const isMac = computed(() => props.platform === 'auto' ? typeof navigator !== 'undefined' && /macintosh/i.test(navigator.userAgent) : props.platform === 'mac');
33024
+ const effectiveDisplayMode = computed(() => props.displayMode);
33025
+ const AND_DELINEATOR = new Delineator('and'); // For + separators
33026
+ const THEN_DELINEATOR = new Delineator('then'); // For - separators
33027
+
33028
+ const effectiveKeyMap = computed(() => props.keyMap);
33029
+ const keyCombinations = computed(() => {
33030
+ if (!props.keys) return [];
33031
+
33032
+ // Split by spaces to handle multiple key combinations
33033
+ // Example: "ctrl+k meta+p" -> ["ctrl+k", "meta+p"]
33034
+ return props.keys.split(' ').map(combination => {
33035
+ // Use the shared sequence splitting logic
33036
+ const sequenceGroups = splitKeySequence(combination);
33037
+
33038
+ // Process each sequence group
33039
+ return sequenceGroups.flatMap((group, groupIndex) => {
33040
+ // Use the shared key combination splitting logic
33041
+ const keyParts = splitKeyCombination(group);
33042
+ const parts = keyParts.reduce((acc, part, index) => {
33043
+ if (index !== 0) {
33044
+ // Add AND delineator between keys
33045
+ return [...acc, AND_DELINEATOR, part];
33046
+ }
33047
+ return [...acc, part];
33048
+ }, []);
33049
+
33050
+ // Add THEN delineator between sequence groups
33051
+ const result = parts.map(key => {
33052
+ if (isString(key)) {
33053
+ return applyDisplayModeToKey(effectiveKeyMap.value, effectiveDisplayMode.value, key, isMac.value);
33054
+ }
33055
+ return key;
33056
+ });
33057
+
33058
+ // Add sequence separator if not the last group
33059
+ if (groupIndex < sequenceGroups.length - 1) {
33060
+ result.push(THEN_DELINEATOR);
33061
+ }
33062
+ return result;
33063
+ });
33064
+ });
33065
+ });
33066
+ const accessibleLabel = computed(() => {
33067
+ if (!props.keys) return '';
33068
+
33069
+ // Convert the parsed key combinations into readable text
33070
+ const readableShortcuts = keyCombinations.value.map(combination => {
33071
+ const readableParts = [];
33072
+ for (const key of combination) {
33073
+ if (isDelineator(key)) {
33074
+ if (AND_DELINEATOR.isEqual(key)) {
33075
+ readableParts.push(t('$vuetify.hotkey.plus'));
33076
+ } else if (THEN_DELINEATOR.isEqual(key)) {
33077
+ readableParts.push(t('$vuetify.hotkey.then'));
33078
+ }
33079
+ } else {
33080
+ // Always use text representation for screen readers
33081
+ const textKey = key[0] === 'icon' || key[0] === 'symbol' ? applyDisplayModeToKey(mergeDeep(hotkeyMap, props.keyMap), 'text', String(key[1]), isMac.value)[1] : key[1];
33082
+ readableParts.push(translateKey(textKey));
33083
+ }
33084
+ }
33085
+ return readableParts.join(' ');
33086
+ });
33087
+ const shortcutText = readableShortcuts.join(', ');
33088
+ return t('$vuetify.hotkey.shortcut', shortcutText);
33089
+ });
33090
+ function translateKey(key) {
33091
+ return key.startsWith('$vuetify.') ? t(key) : key;
33092
+ }
33093
+ function getKeyTooltip(key) {
33094
+ if (effectiveDisplayMode.value === 'text') return undefined;
33095
+ const textKey = getKeyText(effectiveKeyMap.value, String(key[2]), isMac.value);
33096
+ return translateKey(textKey);
33097
+ }
33098
+ function renderKey(key, keyIndex, isContained) {
33099
+ const KeyComponent = isContained ? 'kbd' : VKbd;
33100
+ const keyClasses = ['v-hotkey__key', `v-hotkey__key-${key[0]}`, ...(isContained ? ['v-hotkey__key--nested'] : [borderClasses.value, roundedClasses.value, elevationClasses.value, colorClasses.value])];
33101
+ return createVNode(KeyComponent, {
33102
+ "key": keyIndex,
33103
+ "class": normalizeClass(keyClasses),
33104
+ "style": normalizeStyle(isContained ? undefined : colorStyles.value),
33105
+ "aria-hidden": "true",
33106
+ "title": getKeyTooltip(key)
33107
+ }, {
33108
+ default: () => [key[0] === 'icon' ? createVNode(VIcon, {
33109
+ "icon": key[1],
33110
+ "aria-hidden": "true"
33111
+ }, null) : translateKey(key[1])]
33112
+ });
33113
+ }
33114
+ function renderDivider(key, keyIndex) {
33115
+ return createElementVNode("span", {
33116
+ "key": keyIndex,
33117
+ "class": "v-hotkey__divider",
33118
+ "aria-hidden": "true"
33119
+ }, [AND_DELINEATOR.isEqual(key) ? '+' : t('$vuetify.hotkey.then')]);
33120
+ }
33121
+ useRender(() => createElementVNode("div", {
33122
+ "class": normalizeClass(['v-hotkey', {
33123
+ 'v-hotkey--disabled': props.disabled,
33124
+ 'v-hotkey--inline': props.inline,
33125
+ 'v-hotkey--contained': isContainedVariant.value
33126
+ }, themeClasses.value, rtlClasses.value, variantClasses.value, props.class]),
33127
+ "style": normalizeStyle(props.style),
33128
+ "role": "img",
33129
+ "aria-label": accessibleLabel.value
33130
+ }, [isContainedVariant.value ? createVNode(VKbd, {
33131
+ "key": "contained",
33132
+ "class": normalizeClass(['v-hotkey__contained-wrapper', borderClasses.value, roundedClasses.value, elevationClasses.value, colorClasses.value]),
33133
+ "style": normalizeStyle(colorStyles.value),
33134
+ "aria-hidden": "true"
33135
+ }, {
33136
+ default: () => [props.prefix && createElementVNode("span", {
33137
+ "key": "contained-prefix",
33138
+ "class": "v-hotkey__prefix"
33139
+ }, [props.prefix]), keyCombinations.value.map((combination, comboIndex) => createElementVNode("span", {
33140
+ "class": "v-hotkey__combination",
33141
+ "key": comboIndex
33142
+ }, [combination.map((key, keyIndex) => isDelineator(key) ? renderDivider(key, keyIndex) : renderKey(key, keyIndex, true)), comboIndex < keyCombinations.value.length - 1 && createElementVNode("span", {
33143
+ "aria-hidden": "true"
33144
+ }, [createTextVNode("\xA0")])])), props.suffix && createElementVNode("span", {
33145
+ "key": "contained-suffix",
33146
+ "class": "v-hotkey__suffix"
33147
+ }, [props.suffix])]
33148
+ }) : createElementVNode(Fragment, null, [props.prefix && createElementVNode("span", {
33149
+ "key": "prefix",
33150
+ "class": "v-hotkey__prefix"
33151
+ }, [props.prefix]), keyCombinations.value.map((combination, comboIndex) => createElementVNode("span", {
33152
+ "class": "v-hotkey__combination",
33153
+ "key": comboIndex
33154
+ }, [combination.map((key, keyIndex) => isDelineator(key) ? renderDivider(key, keyIndex) : renderKey(key, keyIndex, false)), comboIndex < keyCombinations.value.length - 1 && createElementVNode("span", {
33155
+ "aria-hidden": "true"
33156
+ }, [createTextVNode("\xA0")])])), props.suffix && createElementVNode("span", {
33157
+ "key": "suffix",
33158
+ "class": "v-hotkey__suffix"
33159
+ }, [props.suffix])])]));
33160
+ }
33161
+ });
33162
+
32278
33163
  var components = /*#__PURE__*/Object.freeze({
32279
33164
  __proto__: null,
32280
33165
  VAlert: VAlert,
@@ -32363,6 +33248,7 @@ var components = /*#__PURE__*/Object.freeze({
32363
33248
  VFileUploadItem: VFileUploadItem,
32364
33249
  VFooter: VFooter,
32365
33250
  VForm: VForm,
33251
+ VHotkey: VHotkey,
32366
33252
  VHover: VHover,
32367
33253
  VIcon: VIcon,
32368
33254
  VIconBtn: VIconBtn,
@@ -32786,7 +33672,7 @@ function createVuetify$1() {
32786
33672
  };
32787
33673
  });
32788
33674
  }
32789
- const version$1 = "3.9.0-beta.0";
33675
+ const version$1 = "3.9.0";
32790
33676
  createVuetify$1.version = version$1;
32791
33677
 
32792
33678
  // Vue's inject() can only be used in setup
@@ -33084,7 +33970,7 @@ var index = /*#__PURE__*/Object.freeze({
33084
33970
 
33085
33971
  /* eslint-disable local-rules/sort-imports */
33086
33972
 
33087
- const version = "3.9.0-beta.0";
33973
+ const version = "3.9.0";
33088
33974
 
33089
33975
  /* eslint-disable local-rules/sort-imports */
33090
33976
 
@@ -33097,5 +33983,5 @@ const createVuetify = function () {
33097
33983
  });
33098
33984
  };
33099
33985
 
33100
- export { index as blueprints, components, createVuetify, directives, useDate, useDefaults, useDisplay, useGoTo, useLayout, useLocale, useRtl, useTheme, version };
33986
+ export { index as blueprints, components, createVuetify, directives, useDate, useDefaults, useDisplay, useGoTo, useHotkey, useLayout, useLocale, useRtl, useTheme, version };
33101
33987
  //# sourceMappingURL=vuetify-labs.esm.js.map