@vuetify/nightly 3.8.8-master.2025-06-10 → 3.8.9-dev.2025-06-12

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 (180) hide show
  1. package/CHANGELOG.md +44 -19
  2. package/dist/json/attributes.json +2771 -2411
  3. package/dist/json/importMap-labs.json +32 -28
  4. package/dist/json/importMap.json +128 -128
  5. package/dist/json/tags.json +96 -1
  6. package/dist/json/web-types.json +5703 -4391
  7. package/dist/vuetify-labs.cjs +635 -146
  8. package/dist/vuetify-labs.css +4248 -4214
  9. package/dist/vuetify-labs.d.ts +9097 -1977
  10. package/dist/vuetify-labs.esm.js +636 -147
  11. package/dist/vuetify-labs.esm.js.map +1 -1
  12. package/dist/vuetify-labs.js +635 -146
  13. package/dist/vuetify-labs.min.css +2 -2
  14. package/dist/vuetify.cjs +383 -135
  15. package/dist/vuetify.cjs.map +1 -1
  16. package/dist/vuetify.css +5999 -5965
  17. package/dist/vuetify.d.ts +1586 -1085
  18. package/dist/vuetify.esm.js +384 -136
  19. package/dist/vuetify.esm.js.map +1 -1
  20. package/dist/vuetify.js +383 -135
  21. package/dist/vuetify.js.map +1 -1
  22. package/dist/vuetify.min.css +2 -2
  23. package/dist/vuetify.min.js +1219 -1203
  24. package/dist/vuetify.min.js.map +1 -1
  25. package/lib/components/VAlert/VAlert.css +6 -1
  26. package/lib/components/VAlert/VAlert.d.ts +35 -0
  27. package/lib/components/VAlert/VAlert.js +15 -10
  28. package/lib/components/VAlert/VAlert.js.map +1 -1
  29. package/lib/components/VAlert/VAlert.sass +7 -1
  30. package/lib/components/VAppBar/VAppBar.d.ts +15 -3
  31. package/lib/components/VAppBar/VAppBarNavIcon.d.ts +20 -10
  32. package/lib/components/VAutocomplete/VAutocomplete.d.ts +154 -103
  33. package/lib/components/VAutocomplete/VAutocomplete.js +21 -3
  34. package/lib/components/VAutocomplete/VAutocomplete.js.map +1 -1
  35. package/lib/components/VBadge/VBadge.d.ts +60 -0
  36. package/lib/components/VBadge/VBadge.js +7 -2
  37. package/lib/components/VBadge/VBadge.js.map +1 -1
  38. package/lib/components/VBtn/VBtn.d.ts +20 -10
  39. package/lib/components/VBtnGroup/VBtnGroup.css +30 -7
  40. package/lib/components/VBtnGroup/VBtnGroup.d.ts +58 -32
  41. package/lib/components/VBtnGroup/VBtnGroup.js +7 -3
  42. package/lib/components/VBtnGroup/VBtnGroup.js.map +1 -1
  43. package/lib/components/VBtnGroup/VBtnGroup.sass +44 -17
  44. package/lib/components/VBtnToggle/VBtnToggle.d.ts +25 -0
  45. package/lib/components/VCard/VCard.d.ts +20 -10
  46. package/lib/components/VCheckbox/VCheckbox.d.ts +23 -13
  47. package/lib/components/VCheckbox/VCheckboxBtn.d.ts +20 -10
  48. package/lib/components/VChip/VChip.d.ts +20 -10
  49. package/lib/components/VChipGroup/VChipGroup.d.ts +10 -0
  50. package/lib/components/VCombobox/VCombobox.d.ts +154 -103
  51. package/lib/components/VCombobox/VCombobox.js +22 -3
  52. package/lib/components/VCombobox/VCombobox.js.map +1 -1
  53. package/lib/components/VDataTable/VDataTable.d.ts +60 -0
  54. package/lib/components/VDataTable/VDataTableHeaders.d.ts +13 -0
  55. package/lib/components/VDataTable/VDataTableHeaders.js +4 -2
  56. package/lib/components/VDataTable/VDataTableHeaders.js.map +1 -1
  57. package/lib/components/VDataTable/VDataTableServer.d.ts +42 -0
  58. package/lib/components/VDataTable/VDataTableVirtual.d.ts +42 -0
  59. package/lib/components/VDatePicker/VDatePicker.d.ts +10 -0
  60. package/lib/components/VDatePicker/VDatePickerMonth.d.ts +10 -0
  61. package/lib/components/VDatePicker/VDatePickerMonth.js +1 -1
  62. package/lib/components/VDatePicker/VDatePickerMonth.js.map +1 -1
  63. package/lib/components/VExpansionPanel/VExpansionPanel.d.ts +20 -10
  64. package/lib/components/VExpansionPanel/VExpansionPanelTitle.d.ts +20 -10
  65. package/lib/components/VExpansionPanel/VExpansionPanels.d.ts +20 -10
  66. package/lib/components/VFab/VFab.d.ts +20 -10
  67. package/lib/components/VField/VField.d.ts +3 -3
  68. package/lib/components/VFileInput/VFileInput.d.ts +15 -15
  69. package/lib/components/VInfiniteScroll/VInfiniteScroll.d.ts +9 -3
  70. package/lib/components/VInfiniteScroll/VInfiniteScroll.js +29 -0
  71. package/lib/components/VInfiniteScroll/VInfiniteScroll.js.map +1 -1
  72. package/lib/components/VInput/VInput.d.ts +4 -4
  73. package/lib/components/VList/VList.d.ts +13 -0
  74. package/lib/components/VList/VList.js +4 -1
  75. package/lib/components/VList/VList.js.map +1 -1
  76. package/lib/components/VList/VListChildren.js.map +1 -1
  77. package/lib/components/VList/VListItem.d.ts +23 -10
  78. package/lib/components/VList/VListItem.js +7 -3
  79. package/lib/components/VList/VListItem.js.map +1 -1
  80. package/lib/components/VList/list.d.ts +9 -2
  81. package/lib/components/VList/list.js +7 -0
  82. package/lib/components/VList/list.js.map +1 -1
  83. package/lib/components/VNumberInput/VNumberInput.d.ts +103 -89
  84. package/lib/components/VNumberInput/VNumberInput.js +19 -4
  85. package/lib/components/VNumberInput/VNumberInput.js.map +1 -1
  86. package/lib/components/VOtpInput/VOtpInput.js +2 -1
  87. package/lib/components/VOtpInput/VOtpInput.js.map +1 -1
  88. package/lib/components/VOverlay/VOverlay.css +1 -1
  89. package/lib/components/VOverlay/_variables.scss +1 -1
  90. package/lib/components/VRadio/VRadio.d.ts +20 -10
  91. package/lib/components/VRadioGroup/VRadioGroup.d.ts +23 -13
  92. package/lib/components/VRangeSlider/VRangeSlider.d.ts +3 -3
  93. package/lib/components/VSelect/VSelect.d.ts +171 -107
  94. package/lib/components/VSelect/VSelect.js +21 -3
  95. package/lib/components/VSelect/VSelect.js.map +1 -1
  96. package/lib/components/VSelectionControl/VSelectionControl.d.ts +20 -10
  97. package/lib/components/VSelectionControlGroup/VSelectionControlGroup.d.ts +28 -14
  98. package/lib/components/VSlideGroup/VSlideGroup.d.ts +10 -0
  99. package/lib/components/VSlideGroup/VSlideGroup.js +2 -1
  100. package/lib/components/VSlideGroup/VSlideGroup.js.map +1 -1
  101. package/lib/components/VSlider/VSlider.d.ts +3 -3
  102. package/lib/components/VSlider/VSliderThumb.d.ts +20 -10
  103. package/lib/components/VStepper/VStepperItem.d.ts +28 -14
  104. package/lib/components/VSwitch/VSwitch.d.ts +23 -13
  105. package/lib/components/VTable/VTable.css +6 -0
  106. package/lib/components/VTable/VTable.d.ts +55 -24
  107. package/lib/components/VTable/VTable.js +9 -2
  108. package/lib/components/VTable/VTable.js.map +1 -1
  109. package/lib/components/VTable/VTable.sass +14 -0
  110. package/lib/components/VTable/_variables.scss +1 -0
  111. package/lib/components/VTabs/VTab.d.ts +56 -28
  112. package/lib/components/VTabs/VTabs.d.ts +10 -0
  113. package/lib/components/VTextField/VTextField.d.ts +27 -27
  114. package/lib/components/VTextarea/VTextarea.d.ts +15 -15
  115. package/lib/components/VToolbar/VToolbar.d.ts +15 -3
  116. package/lib/components/VToolbar/VToolbar.js +6 -3
  117. package/lib/components/VToolbar/VToolbar.js.map +1 -1
  118. package/lib/composables/calendar.d.ts +6 -0
  119. package/lib/composables/calendar.js +2 -1
  120. package/lib/composables/calendar.js.map +1 -1
  121. package/lib/composables/date/DateAdapter.d.ts +3 -3
  122. package/lib/composables/date/DateAdapter.js.map +1 -1
  123. package/lib/composables/date/adapters/string.d.ts +54 -0
  124. package/lib/composables/date/adapters/string.js +153 -0
  125. package/lib/composables/date/adapters/string.js.map +1 -0
  126. package/lib/composables/date/adapters/vuetify.d.ts +1 -1
  127. package/lib/composables/date/adapters/vuetify.js +4 -4
  128. package/lib/composables/date/adapters/vuetify.js.map +1 -1
  129. package/lib/composables/date/date.d.ts +3 -3
  130. package/lib/composables/date/index.d.ts +1 -0
  131. package/lib/composables/date/index.js +1 -0
  132. package/lib/composables/date/index.js.map +1 -1
  133. package/lib/composables/filter.js +3 -0
  134. package/lib/composables/filter.js.map +1 -1
  135. package/lib/composables/iconSizes.d.ts +28 -0
  136. package/lib/composables/iconSizes.js +23 -0
  137. package/lib/composables/iconSizes.js.map +1 -0
  138. package/lib/composables/mask.d.ts +38 -0
  139. package/lib/composables/mask.js +183 -0
  140. package/lib/composables/mask.js.map +1 -0
  141. package/lib/composables/theme.d.ts +6 -1
  142. package/lib/composables/theme.js +94 -26
  143. package/lib/composables/theme.js.map +1 -1
  144. package/lib/composables/virtual.js +6 -1
  145. package/lib/composables/virtual.js.map +1 -1
  146. package/lib/directives/ripple/index.d.ts +2 -1
  147. package/lib/directives/ripple/index.js +12 -7
  148. package/lib/directives/ripple/index.js.map +1 -1
  149. package/lib/entry-bundler.d.ts +3 -3
  150. package/lib/entry-bundler.js +1 -1
  151. package/lib/entry-bundler.js.map +1 -1
  152. package/lib/framework.d.ts +72 -56
  153. package/lib/framework.js +1 -1
  154. package/lib/framework.js.map +1 -1
  155. package/lib/labs/VCalendar/VCalendar.d.ts +10 -0
  156. package/lib/labs/VColorInput/VColorInput.d.ts +3 -3
  157. package/lib/labs/VDateInput/VDateInput.d.ts +97 -87
  158. package/lib/labs/VFileUpload/VFileUpload.d.ts +3 -3
  159. package/lib/labs/VFileUpload/VFileUploadItem.d.ts +20 -10
  160. package/lib/labs/VIconBtn/VIconBtn.d.ts +29 -29
  161. package/lib/labs/VIconBtn/VIconBtn.js +7 -11
  162. package/lib/labs/VIconBtn/VIconBtn.js.map +1 -1
  163. package/lib/labs/VMaskInput/VMaskInput.d.ts +6993 -0
  164. package/lib/labs/VMaskInput/VMaskInput.js +67 -0
  165. package/lib/labs/VMaskInput/VMaskInput.js.map +1 -0
  166. package/lib/labs/VMaskInput/index.d.ts +1 -0
  167. package/lib/labs/VMaskInput/index.js +2 -0
  168. package/lib/labs/VMaskInput/index.js.map +1 -0
  169. package/lib/labs/VStepperVertical/VStepperVertical.d.ts +20 -10
  170. package/lib/labs/VStepperVertical/VStepperVerticalItem.d.ts +20 -10
  171. package/lib/labs/VTreeview/VTreeview.d.ts +13 -0
  172. package/lib/labs/VTreeview/VTreeviewItem.d.ts +20 -10
  173. package/lib/labs/components.d.ts +1 -0
  174. package/lib/labs/components.js +1 -0
  175. package/lib/labs/components.js.map +1 -1
  176. package/lib/labs/entry-bundler.d.ts +3 -3
  177. package/lib/util/globals.d.ts +1 -0
  178. package/lib/util/globals.js +1 -0
  179. package/lib/util/globals.js.map +1 -1
  180. package/package.json +3 -1
package/dist/vuetify.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * Vuetify v3.8.8-master.2025-06-10
2
+ * Vuetify v3.8.9-dev.2025-06-12
3
3
  * Forged by John Leider
4
4
  * Released under the MIT License.
5
5
  */
@@ -14,6 +14,7 @@
14
14
  const SUPPORTS_INTERSECTION = IN_BROWSER && 'IntersectionObserver' in window;
15
15
  const SUPPORTS_TOUCH = IN_BROWSER && ('ontouchstart' in window || window.navigator.maxTouchPoints > 0);
16
16
  const SUPPORTS_EYE_DROPPER = IN_BROWSER && 'EyeDropper' in window;
17
+ const SUPPORTS_MATCH_MEDIA = IN_BROWSER && 'matchMedia' in window && typeof window.matchMedia === 'function';
17
18
 
18
19
  function _classPrivateFieldInitSpec(e, t, a) { _checkPrivateRedeclaration(e, t), t.set(e, a); }
19
20
  function _checkPrivateRedeclaration(e, t) { if (t.has(e)) throw new TypeError("Cannot initialize the same private elements twice on an object"); }
@@ -2835,6 +2836,7 @@
2835
2836
  function genDefaults$1() {
2836
2837
  return {
2837
2838
  defaultTheme: 'light',
2839
+ prefix: 'v-',
2838
2840
  variations: {
2839
2841
  colors: [],
2840
2842
  lighten: 0,
@@ -2916,7 +2918,10 @@
2916
2918
  }
2917
2919
  }
2918
2920
  },
2919
- stylesheetId: 'vuetify-theme-stylesheet'
2921
+ stylesheetId: 'vuetify-theme-stylesheet',
2922
+ scoped: false,
2923
+ unimportant: false,
2924
+ utilities: true
2920
2925
  };
2921
2926
  }
2922
2927
  function parseThemeOptions() {
@@ -2939,21 +2944,21 @@
2939
2944
  function createCssClass(lines, selector, content, scope) {
2940
2945
  lines.push(`${getScopedSelector(selector, scope)} {\n`, ...content.map(line => ` ${line};\n`), '}\n');
2941
2946
  }
2942
- function genCssVariables(theme) {
2947
+ function genCssVariables(theme, prefix) {
2943
2948
  const lightOverlay = theme.dark ? 2 : 1;
2944
2949
  const darkOverlay = theme.dark ? 1 : 2;
2945
2950
  const variables = [];
2946
2951
  for (const [key, value] of Object.entries(theme.colors)) {
2947
2952
  const rgb = parseColor(value);
2948
- variables.push(`--v-theme-${key}: ${rgb.r},${rgb.g},${rgb.b}`);
2953
+ variables.push(`--${prefix}theme-${key}: ${rgb.r},${rgb.g},${rgb.b}`);
2949
2954
  if (!key.startsWith('on-')) {
2950
- variables.push(`--v-theme-${key}-overlay-multiplier: ${getLuma(value) > 0.18 ? lightOverlay : darkOverlay}`);
2955
+ variables.push(`--${prefix}theme-${key}-overlay-multiplier: ${getLuma(value) > 0.18 ? lightOverlay : darkOverlay}`);
2951
2956
  }
2952
2957
  }
2953
2958
  for (const [key, value] of Object.entries(theme.variables)) {
2954
2959
  const color = typeof value === 'string' && value.startsWith('#') ? parseColor(value) : undefined;
2955
2960
  const rgb = color ? `${color.r}, ${color.g}, ${color.b}` : undefined;
2956
- variables.push(`--v-${key}: ${rgb ?? value}`);
2961
+ variables.push(`--${prefix}${key}: ${rgb ?? value}`);
2957
2962
  }
2958
2963
  return variables;
2959
2964
  }
@@ -2997,7 +3002,8 @@
2997
3002
  const scopeSelector = `:where(${scope})`;
2998
3003
  return selector === ':root' ? scopeSelector : `${scopeSelector} ${selector}`;
2999
3004
  }
3000
- function upsertStyles(styleEl, styles) {
3005
+ function upsertStyles(id, cspNonce, styles) {
3006
+ const styleEl = getOrCreateStyleElement(id, cspNonce);
3001
3007
  if (!styleEl) return;
3002
3008
  styleEl.innerHTML = styles;
3003
3009
  }
@@ -3017,8 +3023,17 @@
3017
3023
  // Composables
3018
3024
  function createTheme(options) {
3019
3025
  const parsedOptions = parseThemeOptions(options);
3020
- const name = vue.shallowRef(parsedOptions.defaultTheme);
3026
+ const _name = vue.shallowRef(parsedOptions.defaultTheme);
3021
3027
  const themes = vue.ref(parsedOptions.themes);
3028
+ const systemName = vue.shallowRef('light');
3029
+ const name = vue.computed({
3030
+ get() {
3031
+ return _name.value === 'system' ? systemName.value : _name.value;
3032
+ },
3033
+ set(val) {
3034
+ _name.value = val;
3035
+ }
3036
+ });
3022
3037
  const computedThemes = vue.computed(() => {
3023
3038
  const acc = {};
3024
3039
  for (const [name, original] of Object.entries(themes.value)) {
@@ -3039,28 +3054,49 @@
3039
3054
  const current = vue.toRef(() => computedThemes.value[name.value]);
3040
3055
  const styles = vue.computed(() => {
3041
3056
  const lines = [];
3057
+ const important = parsedOptions.unimportant ? '' : ' !important';
3058
+ const scoped = parsedOptions.scoped ? parsedOptions.prefix : '';
3042
3059
  if (current.value?.dark) {
3043
3060
  createCssClass(lines, ':root', ['color-scheme: dark'], parsedOptions.scope);
3044
3061
  }
3045
- createCssClass(lines, ':root', genCssVariables(current.value), parsedOptions.scope);
3062
+ createCssClass(lines, ':root', genCssVariables(current.value, parsedOptions.prefix), parsedOptions.scope);
3046
3063
  for (const [themeName, theme] of Object.entries(computedThemes.value)) {
3047
- createCssClass(lines, `.v-theme--${themeName}`, [`color-scheme: ${theme.dark ? 'dark' : 'normal'}`, ...genCssVariables(theme)], parsedOptions.scope);
3048
- }
3049
- const bgLines = [];
3050
- const fgLines = [];
3051
- const colors = new Set(Object.values(computedThemes.value).flatMap(theme => Object.keys(theme.colors)));
3052
- for (const key of colors) {
3053
- if (key.startsWith('on-')) {
3054
- createCssClass(fgLines, `.${key}`, [`color: rgb(var(--v-theme-${key})) !important`], parsedOptions.scope);
3055
- } else {
3056
- createCssClass(bgLines, `.bg-${key}`, [`--v-theme-overlay-multiplier: var(--v-theme-${key}-overlay-multiplier)`, `background-color: rgb(var(--v-theme-${key})) !important`, `color: rgb(var(--v-theme-on-${key})) !important`], parsedOptions.scope);
3057
- createCssClass(fgLines, `.text-${key}`, [`color: rgb(var(--v-theme-${key})) !important`], parsedOptions.scope);
3058
- createCssClass(fgLines, `.border-${key}`, [`--v-border-color: var(--v-theme-${key})`], parsedOptions.scope);
3064
+ createCssClass(lines, `.${parsedOptions.prefix}theme--${themeName}`, [`color-scheme: ${theme.dark ? 'dark' : 'normal'}`, ...genCssVariables(theme, parsedOptions.prefix)], parsedOptions.scope);
3065
+ }
3066
+ if (parsedOptions.utilities) {
3067
+ const bgLines = [];
3068
+ const fgLines = [];
3069
+ const colors = new Set(Object.values(computedThemes.value).flatMap(theme => Object.keys(theme.colors)));
3070
+ for (const key of colors) {
3071
+ if (key.startsWith('on-')) {
3072
+ createCssClass(fgLines, `.${key}`, [`color: rgb(var(--${parsedOptions.prefix}theme-${key}))${important}`], parsedOptions.scope);
3073
+ } else {
3074
+ createCssClass(bgLines, `.${scoped}bg-${key}`, [`--${parsedOptions.prefix}theme-overlay-multiplier: var(--${parsedOptions.prefix}theme-${key}-overlay-multiplier)`, `background-color: rgb(var(--${parsedOptions.prefix}theme-${key}))${important}`, `color: rgb(var(--${parsedOptions.prefix}theme-on-${key}))${important}`], parsedOptions.scope);
3075
+ createCssClass(fgLines, `.${scoped}text-${key}`, [`color: rgb(var(--${parsedOptions.prefix}theme-${key}))${important}`], parsedOptions.scope);
3076
+ createCssClass(fgLines, `.${scoped}border-${key}`, [`--${parsedOptions.prefix}border-color: var(--${parsedOptions.prefix}theme-${key})`], parsedOptions.scope);
3077
+ }
3059
3078
  }
3079
+ lines.push(...bgLines, ...fgLines);
3060
3080
  }
3061
- lines.push(...bgLines, ...fgLines);
3062
3081
  return lines.map((str, i) => i === 0 ? str : ` ${str}`).join('');
3063
3082
  });
3083
+ const themeClasses = vue.toRef(() => parsedOptions.isDisabled ? undefined : `${parsedOptions.prefix}theme--${name.value}`);
3084
+ const themeNames = vue.toRef(() => Object.keys(computedThemes.value));
3085
+ if (SUPPORTS_MATCH_MEDIA) {
3086
+ const media = window.matchMedia('(prefers-color-scheme: dark)');
3087
+ function updateSystemName() {
3088
+ systemName.value = media.matches ? 'dark' : 'light';
3089
+ }
3090
+ updateSystemName();
3091
+ media.addEventListener('change', updateSystemName, {
3092
+ passive: true
3093
+ });
3094
+ if (vue.getCurrentScope()) {
3095
+ vue.onScopeDispose(() => {
3096
+ media.removeEventListener('change', updateSystemName);
3097
+ });
3098
+ }
3099
+ }
3064
3100
  function install(app) {
3065
3101
  if (parsedOptions.isDisabled) return;
3066
3102
  const head = app._context.provides.usehead;
@@ -3098,22 +3134,55 @@
3098
3134
  updateStyles();
3099
3135
  }
3100
3136
  function updateStyles() {
3101
- upsertStyles(getOrCreateStyleElement(parsedOptions.stylesheetId, parsedOptions.cspNonce), styles.value);
3137
+ upsertStyles(parsedOptions.stylesheetId, parsedOptions.cspNonce, styles.value);
3102
3138
  }
3103
3139
  }
3104
3140
  }
3105
- const themeClasses = vue.toRef(() => parsedOptions.isDisabled ? undefined : `v-theme--${name.value}`);
3141
+ function change(themeName) {
3142
+ if (!themeNames.value.includes(themeName)) {
3143
+ consoleWarn(`Theme "${themeName}" not found on the Vuetify theme instance`);
3144
+ return;
3145
+ }
3146
+ name.value = themeName;
3147
+ }
3148
+ function cycle() {
3149
+ let themeArray = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : themeNames.value;
3150
+ const currentIndex = themeArray.indexOf(name.value);
3151
+ const nextIndex = currentIndex === -1 ? 0 : (currentIndex + 1) % themeArray.length;
3152
+ change(themeArray[nextIndex]);
3153
+ }
3154
+ function toggle() {
3155
+ let themeArray = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : ['light', 'dark'];
3156
+ cycle(themeArray);
3157
+ }
3158
+ const globalName = new Proxy(name, {
3159
+ get(target, prop) {
3160
+ return target[prop];
3161
+ },
3162
+ set(target, prop, val) {
3163
+ if (prop === 'value') {
3164
+ deprecate(`theme.global.name.value = ${val}`, `theme.change('${val}')`);
3165
+ }
3166
+ // @ts-expect-error
3167
+ target[prop] = val;
3168
+ return true;
3169
+ }
3170
+ });
3106
3171
  return {
3107
3172
  install,
3173
+ change,
3174
+ cycle,
3175
+ toggle,
3108
3176
  isDisabled: parsedOptions.isDisabled,
3109
3177
  name,
3110
3178
  themes,
3111
3179
  current,
3112
3180
  computedThemes,
3181
+ prefix: parsedOptions.prefix,
3113
3182
  themeClasses,
3114
3183
  styles,
3115
3184
  global: {
3116
- name,
3185
+ name: globalName,
3117
3186
  current
3118
3187
  }
3119
3188
  };
@@ -3124,7 +3193,7 @@
3124
3193
  if (!theme) throw new Error('Could not find Vuetify theme injection');
3125
3194
  const name = vue.toRef(() => props.theme ?? theme.name.value);
3126
3195
  const current = vue.toRef(() => theme.themes.value[name.value]);
3127
- const themeClasses = vue.toRef(() => theme.isDisabled ? undefined : `v-theme--${name.value}`);
3196
+ const themeClasses = vue.toRef(() => theme.isDisabled ? undefined : `${theme.prefix}theme--${name.value}`);
3128
3197
  const newTheme = {
3129
3198
  ...theme,
3130
3199
  name,
@@ -4228,7 +4297,10 @@
4228
4297
  default: 'default',
4229
4298
  validator: v => allowedDensities$1.includes(v)
4230
4299
  },
4231
- extended: Boolean,
4300
+ extended: {
4301
+ type: Boolean,
4302
+ default: null
4303
+ },
4232
4304
  extensionHeight: {
4233
4305
  type: [Number, String],
4234
4306
  default: 48
@@ -4276,7 +4348,7 @@
4276
4348
  const {
4277
4349
  rtlClasses
4278
4350
  } = useRtl();
4279
- const isExtended = vue.shallowRef(!!(props.extended || slots.extension?.()));
4351
+ const isExtended = vue.shallowRef(props.extended === null ? !!slots.extension?.() : props.extended);
4280
4352
  const contentHeight = vue.computed(() => parseInt(Number(props.height) + (props.density === 'prominent' ? Number(props.height) : 0) - (props.density === 'comfortable' ? 8 : 0) - (props.density === 'compact' ? 16 : 0), 10));
4281
4353
  const extensionHeight = vue.computed(() => isExtended.value ? parseInt(Number(props.extensionHeight) + (props.density === 'prominent' ? Number(props.extensionHeight) : 0) - (props.density === 'comfortable' ? 4 : 0) - (props.density === 'compact' ? 8 : 0), 10) : 0);
4282
4354
  provideDefaults({
@@ -4288,7 +4360,7 @@
4288
4360
  const hasTitle = !!(props.title || slots.title);
4289
4361
  const hasImage = !!(slots.image || props.image);
4290
4362
  const extension = slots.extension?.();
4291
- isExtended.value = !!(props.extended || extension);
4363
+ isExtended.value = props.extended === null ? !!extension : props.extended;
4292
4364
  return vue.createVNode(props.tag, {
4293
4365
  "class": vue.normalizeClass(['v-toolbar', {
4294
4366
  'v-toolbar--absolute': props.absolute,
@@ -4671,9 +4743,15 @@
4671
4743
  };
4672
4744
  }
4673
4745
 
4746
+ // Types
4747
+
4674
4748
  const makeVBtnGroupProps = propsFactory({
4675
4749
  baseColor: String,
4676
4750
  divided: Boolean,
4751
+ direction: {
4752
+ type: String,
4753
+ default: 'horizontal'
4754
+ },
4677
4755
  ...makeBorderProps(),
4678
4756
  ...makeComponentProps(),
4679
4757
  ...makeDensityProps(),
@@ -4707,7 +4785,7 @@
4707
4785
  } = useRounded(props);
4708
4786
  provideDefaults({
4709
4787
  VBtn: {
4710
- height: 'auto',
4788
+ height: vue.toRef(() => props.direction === 'horizontal' ? 'auto' : null),
4711
4789
  baseColor: vue.toRef(() => props.baseColor),
4712
4790
  color: vue.toRef(() => props.color),
4713
4791
  density: vue.toRef(() => props.density),
@@ -4717,7 +4795,7 @@
4717
4795
  });
4718
4796
  useRender(() => {
4719
4797
  return vue.createVNode(props.tag, {
4720
- "class": vue.normalizeClass(['v-btn-group', {
4798
+ "class": vue.normalizeClass(['v-btn-group', `v-btn-group--${props.direction}`, {
4721
4799
  'v-btn-group--divided': props.divided
4722
4800
  }, themeClasses.value, borderClasses.value, densityClasses.value, elevationClasses.value, roundedClasses.value, props.class]),
4723
4801
  "style": vue.normalizeStyle(props.style)
@@ -5840,8 +5918,8 @@
5840
5918
  window.clearTimeout(element._ripple.showTimer);
5841
5919
  }
5842
5920
  let keyboardRipple = false;
5843
- function keyboardRippleShow(e) {
5844
- if (!keyboardRipple && (e.keyCode === keyCodes.enter || e.keyCode === keyCodes.space)) {
5921
+ function keyboardRippleShow(e, keys) {
5922
+ if (!keyboardRipple && keys.includes(e.keyCode)) {
5845
5923
  keyboardRipple = true;
5846
5924
  rippleShow(e);
5847
5925
  }
@@ -5869,9 +5947,12 @@
5869
5947
  el._ripple.enabled = enabled;
5870
5948
  el._ripple.centered = modifiers.center;
5871
5949
  el._ripple.circle = modifiers.circle;
5872
- if (isObject(value) && value.class) {
5873
- el._ripple.class = value.class;
5950
+ const bindingValue = isObject(value) ? value : {};
5951
+ if (bindingValue.class) {
5952
+ el._ripple.class = bindingValue.class;
5874
5953
  }
5954
+ const allowedKeys = bindingValue.keys ?? [keyCodes.enter, keyCodes.space];
5955
+ el._ripple.keyDownHandler = e => keyboardRippleShow(e, allowedKeys);
5875
5956
  if (enabled && !wasEnabled) {
5876
5957
  if (modifiers.stop) {
5877
5958
  el.addEventListener('touchstart', rippleStop, {
@@ -5893,7 +5974,7 @@
5893
5974
  el.addEventListener('mousedown', rippleShow);
5894
5975
  el.addEventListener('mouseup', rippleHide);
5895
5976
  el.addEventListener('mouseleave', rippleHide);
5896
- el.addEventListener('keydown', keyboardRippleShow);
5977
+ el.addEventListener('keydown', e => keyboardRippleShow(e, allowedKeys));
5897
5978
  el.addEventListener('keyup', keyboardRippleHide);
5898
5979
  el.addEventListener('blur', focusRippleHide);
5899
5980
 
@@ -5913,7 +5994,9 @@
5913
5994
  el.removeEventListener('touchcancel', rippleHide);
5914
5995
  el.removeEventListener('mouseup', rippleHide);
5915
5996
  el.removeEventListener('mouseleave', rippleHide);
5916
- el.removeEventListener('keydown', keyboardRippleShow);
5997
+ if (el._ripple?.keyDownHandler) {
5998
+ el.removeEventListener('keydown', el._ripple.keyDownHandler);
5999
+ }
5917
6000
  el.removeEventListener('keyup', keyboardRippleHide);
5918
6001
  el.removeEventListener('dragstart', rippleHide);
5919
6002
  el.removeEventListener('blur', focusRippleHide);
@@ -5922,8 +6005,8 @@
5922
6005
  updateRipple(el, binding, false);
5923
6006
  }
5924
6007
  function unmounted$4(el) {
5925
- delete el._ripple;
5926
6008
  removeListeners(el);
6009
+ delete el._ripple;
5927
6010
  }
5928
6011
  function updated$1(el, binding) {
5929
6012
  if (binding.value === binding.oldValue) {
@@ -6196,6 +6279,31 @@
6196
6279
  // Utilities
6197
6280
  const VAlertTitle = createSimpleFunctional('v-alert-title');
6198
6281
 
6282
+ // Utilities
6283
+
6284
+ // Types
6285
+
6286
+ // Types
6287
+
6288
+ // Composables
6289
+ const makeIconSizeProps = propsFactory({
6290
+ iconSize: [Number, String],
6291
+ iconSizes: {
6292
+ type: Array,
6293
+ default: () => [['x-small', 10], ['small', 16], ['default', 24], ['large', 28], ['x-large', 32]]
6294
+ }
6295
+ }, 'iconSize');
6296
+ function useIconSizes(props, fallback) {
6297
+ const iconSize = vue.computed(() => {
6298
+ const iconSizeMap = new Map(props.iconSizes);
6299
+ const _iconSize = props.iconSize ?? fallback() ?? 'default';
6300
+ return iconSizeMap.has(_iconSize) ? iconSizeMap.get(_iconSize) : _iconSize;
6301
+ });
6302
+ return {
6303
+ iconSize
6304
+ };
6305
+ }
6306
+
6199
6307
  // Types
6200
6308
 
6201
6309
  const allowedTypes = ['success', 'info', 'warning', 'error'];
@@ -6235,6 +6343,7 @@
6235
6343
  ...makeDensityProps(),
6236
6344
  ...makeDimensionProps(),
6237
6345
  ...makeElevationProps(),
6346
+ ...makeIconSizeProps(),
6238
6347
  ...makeLocationProps(),
6239
6348
  ...makePositionProps(),
6240
6349
  ...makeRoundedProps(),
@@ -6262,6 +6371,9 @@
6262
6371
  if (!props.type) return props.icon;
6263
6372
  return props.icon ?? `$${props.type}`;
6264
6373
  });
6374
+ const {
6375
+ iconSize
6376
+ } = useIconSizes(props, () => props.prominent ? 44 : 28);
6265
6377
  const {
6266
6378
  themeClasses
6267
6379
  } = provideTheme(props);
@@ -6309,6 +6421,11 @@
6309
6421
  const hasPrepend = !!(slots.prepend || icon.value);
6310
6422
  const hasTitle = !!(slots.title || props.title);
6311
6423
  const hasClose = !!(slots.close || props.closable);
6424
+ const iconProps = {
6425
+ density: props.density,
6426
+ icon: icon.value,
6427
+ size: iconSize.value
6428
+ };
6312
6429
  return isActive.value && vue.createVNode(props.tag, {
6313
6430
  "class": vue.normalizeClass(['v-alert', props.border && {
6314
6431
  'v-alert--border': !!props.border,
@@ -6326,19 +6443,14 @@
6326
6443
  }, null), hasPrepend && vue.createElementVNode("div", {
6327
6444
  "key": "prepend",
6328
6445
  "class": "v-alert__prepend"
6329
- }, [!slots.prepend ? vue.createVNode(VIcon, {
6330
- "key": "prepend-icon",
6331
- "density": props.density,
6332
- "icon": icon.value,
6333
- "size": props.prominent ? 44 : 28
6334
- }, null) : vue.createVNode(VDefaultsProvider, {
6446
+ }, [!slots.prepend ? vue.createVNode(VIcon, vue.mergeProps({
6447
+ "key": "prepend-icon"
6448
+ }, iconProps), null) : vue.createVNode(VDefaultsProvider, {
6335
6449
  "key": "prepend-defaults",
6336
6450
  "disabled": !icon.value,
6337
6451
  "defaults": {
6338
6452
  VIcon: {
6339
- density: props.density,
6340
- icon: icon.value,
6341
- size: props.prominent ? 44 : 28
6453
+ ...iconProps
6342
6454
  }
6343
6455
  }
6344
6456
  }, slots.prepend)]), vue.createElementVNode("div", {
@@ -7863,6 +7975,7 @@
7863
7975
  const VSlideGroupSymbol = Symbol.for('vuetify:v-slide-group');
7864
7976
  const makeVSlideGroupProps = propsFactory({
7865
7977
  centerActive: Boolean,
7978
+ contentClass: null,
7866
7979
  direction: {
7867
7980
  type: String,
7868
7981
  default: 'horizontal'
@@ -8175,7 +8288,7 @@
8175
8288
  })]), vue.createElementVNode("div", {
8176
8289
  "key": "container",
8177
8290
  "ref": containerRef,
8178
- "class": "v-slide-group__container",
8291
+ "class": vue.normalizeClass(['v-slide-group__container', props.contentClass]),
8179
8292
  "onScroll": onScroll
8180
8293
  }, [vue.createElementVNode("div", {
8181
8294
  "ref": contentRef,
@@ -8538,16 +8651,85 @@
8538
8651
  }
8539
8652
  });
8540
8653
 
8654
+ const makeVDividerProps = propsFactory({
8655
+ color: String,
8656
+ inset: Boolean,
8657
+ length: [Number, String],
8658
+ opacity: [Number, String],
8659
+ thickness: [Number, String],
8660
+ vertical: Boolean,
8661
+ ...makeComponentProps(),
8662
+ ...makeThemeProps()
8663
+ }, 'VDivider');
8664
+ const VDivider = genericComponent()({
8665
+ name: 'VDivider',
8666
+ props: makeVDividerProps(),
8667
+ setup(props, _ref) {
8668
+ let {
8669
+ attrs,
8670
+ slots
8671
+ } = _ref;
8672
+ const {
8673
+ themeClasses
8674
+ } = provideTheme(props);
8675
+ const {
8676
+ textColorClasses,
8677
+ textColorStyles
8678
+ } = useTextColor(() => props.color);
8679
+ const dividerStyles = vue.computed(() => {
8680
+ const styles = {};
8681
+ if (props.length) {
8682
+ styles[props.vertical ? 'height' : 'width'] = convertToUnit(props.length);
8683
+ }
8684
+ if (props.thickness) {
8685
+ styles[props.vertical ? 'borderRightWidth' : 'borderTopWidth'] = convertToUnit(props.thickness);
8686
+ }
8687
+ return styles;
8688
+ });
8689
+ useRender(() => {
8690
+ const divider = vue.createElementVNode("hr", {
8691
+ "class": vue.normalizeClass([{
8692
+ 'v-divider': true,
8693
+ 'v-divider--inset': props.inset,
8694
+ 'v-divider--vertical': props.vertical
8695
+ }, themeClasses.value, textColorClasses.value, props.class]),
8696
+ "style": vue.normalizeStyle([dividerStyles.value, textColorStyles.value, {
8697
+ '--v-border-opacity': props.opacity
8698
+ }, props.style]),
8699
+ "aria-orientation": !attrs.role || attrs.role === 'separator' ? props.vertical ? 'vertical' : 'horizontal' : undefined,
8700
+ "role": `${attrs.role || 'separator'}`
8701
+ }, null);
8702
+ if (!slots.default) return divider;
8703
+ return vue.createElementVNode("div", {
8704
+ "class": vue.normalizeClass(['v-divider__wrapper', {
8705
+ 'v-divider__wrapper--vertical': props.vertical,
8706
+ 'v-divider__wrapper--inset': props.inset
8707
+ }])
8708
+ }, [divider, vue.createElementVNode("div", {
8709
+ "class": "v-divider__content"
8710
+ }, [slots.default()]), divider]);
8711
+ });
8712
+ return {};
8713
+ }
8714
+ });
8715
+
8541
8716
  // Utilities
8542
8717
 
8543
8718
  // List
8544
8719
  const ListKey = Symbol.for('vuetify:list');
8545
8720
  function createList() {
8721
+ let {
8722
+ filterable
8723
+ } = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {
8724
+ filterable: false
8725
+ };
8546
8726
  const parent = vue.inject(ListKey, {
8727
+ filterable: false,
8547
8728
  hasPrepend: vue.shallowRef(false),
8548
8729
  updateHasPrepend: () => null
8549
8730
  });
8550
8731
  const data = {
8732
+ filterable: parent.filterable || filterable,
8551
8733
  hasPrepend: vue.shallowRef(false),
8552
8734
  updateHasPrepend: value => {
8553
8735
  if (value) data.hasPrepend.value = value;
@@ -9499,6 +9681,9 @@
9499
9681
  roundedClasses
9500
9682
  } = useRounded(roundedProps);
9501
9683
  const lineClasses = vue.toRef(() => props.lines ? `v-list-item--${props.lines}-line` : undefined);
9684
+ const rippleOptions = vue.toRef(() => props.ripple !== undefined && !!props.ripple && list?.filterable ? {
9685
+ keys: [keyCodes.enter]
9686
+ } : props.ripple);
9502
9687
  const slotProps = vue.computed(() => ({
9503
9688
  isActive: isActive.value,
9504
9689
  select,
@@ -9523,8 +9708,9 @@
9523
9708
  function onKeyDown(e) {
9524
9709
  const target = e.target;
9525
9710
  if (['INPUT', 'TEXTAREA'].includes(target.tagName)) return;
9526
- if (e.key === 'Enter' || e.key === ' ') {
9711
+ if (e.key === 'Enter' || e.key === ' ' && !list?.filterable) {
9527
9712
  e.preventDefault();
9713
+ e.stopPropagation();
9528
9714
  e.target.dispatchEvent(new MouseEvent('click', e));
9529
9715
  }
9530
9716
  }
@@ -9634,7 +9820,7 @@
9634
9820
  }), vue.createElementVNode("div", {
9635
9821
  "class": "v-list-item__spacer"
9636
9822
  }, null)])]
9637
- }), [[Ripple, isClickable.value && props.ripple]]);
9823
+ }), [[Ripple, isClickable.value && rippleOptions.value]]);
9638
9824
  });
9639
9825
  return {
9640
9826
  activate,
@@ -9689,68 +9875,6 @@
9689
9875
  }
9690
9876
  });
9691
9877
 
9692
- const makeVDividerProps = propsFactory({
9693
- color: String,
9694
- inset: Boolean,
9695
- length: [Number, String],
9696
- opacity: [Number, String],
9697
- thickness: [Number, String],
9698
- vertical: Boolean,
9699
- ...makeComponentProps(),
9700
- ...makeThemeProps()
9701
- }, 'VDivider');
9702
- const VDivider = genericComponent()({
9703
- name: 'VDivider',
9704
- props: makeVDividerProps(),
9705
- setup(props, _ref) {
9706
- let {
9707
- attrs,
9708
- slots
9709
- } = _ref;
9710
- const {
9711
- themeClasses
9712
- } = provideTheme(props);
9713
- const {
9714
- textColorClasses,
9715
- textColorStyles
9716
- } = useTextColor(() => props.color);
9717
- const dividerStyles = vue.computed(() => {
9718
- const styles = {};
9719
- if (props.length) {
9720
- styles[props.vertical ? 'height' : 'width'] = convertToUnit(props.length);
9721
- }
9722
- if (props.thickness) {
9723
- styles[props.vertical ? 'borderRightWidth' : 'borderTopWidth'] = convertToUnit(props.thickness);
9724
- }
9725
- return styles;
9726
- });
9727
- useRender(() => {
9728
- const divider = vue.createElementVNode("hr", {
9729
- "class": vue.normalizeClass([{
9730
- 'v-divider': true,
9731
- 'v-divider--inset': props.inset,
9732
- 'v-divider--vertical': props.vertical
9733
- }, themeClasses.value, textColorClasses.value, props.class]),
9734
- "style": vue.normalizeStyle([dividerStyles.value, textColorStyles.value, {
9735
- '--v-border-opacity': props.opacity
9736
- }, props.style]),
9737
- "aria-orientation": !attrs.role || attrs.role === 'separator' ? props.vertical ? 'vertical' : 'horizontal' : undefined,
9738
- "role": `${attrs.role || 'separator'}`
9739
- }, null);
9740
- if (!slots.default) return divider;
9741
- return vue.createElementVNode("div", {
9742
- "class": vue.normalizeClass(['v-divider__wrapper', {
9743
- 'v-divider__wrapper--vertical': props.vertical,
9744
- 'v-divider__wrapper--inset': props.inset
9745
- }])
9746
- }, [divider, vue.createElementVNode("div", {
9747
- "class": "v-divider__content"
9748
- }, [slots.default()]), divider]);
9749
- });
9750
- return {};
9751
- }
9752
- });
9753
-
9754
9878
  // Types
9755
9879
 
9756
9880
  const makeVListChildrenProps = propsFactory({
@@ -10019,6 +10143,7 @@
10019
10143
  activeClass: String,
10020
10144
  bgColor: String,
10021
10145
  disabled: Boolean,
10146
+ filterable: Boolean,
10022
10147
  expandIcon: IconValue,
10023
10148
  collapseIcon: IconValue,
10024
10149
  lines: {
@@ -10102,7 +10227,9 @@
10102
10227
  const activeColor = vue.toRef(() => props.activeColor);
10103
10228
  const baseColor = vue.toRef(() => props.baseColor);
10104
10229
  const color = vue.toRef(() => props.color);
10105
- createList();
10230
+ createList({
10231
+ filterable: props.filterable
10232
+ });
10106
10233
  provideDefaults({
10107
10234
  VListGroup: {
10108
10235
  activeColor,
@@ -12679,7 +12806,12 @@
12679
12806
  }
12680
12807
  function calculateOffset(index) {
12681
12808
  index = clamp(index, 0, items.value.length - 1);
12682
- return offsets[index] || 0;
12809
+ const whole = Math.floor(index);
12810
+ const fraction = index % 1;
12811
+ const next = whole + 1;
12812
+ const wholeOffset = offsets[whole] || 0;
12813
+ const nextOffset = offsets[next] || wholeOffset;
12814
+ return wholeOffset + (nextOffset - wholeOffset) * fraction;
12683
12815
  }
12684
12816
  function calculateIndex(scrollTop) {
12685
12817
  return binaryClosest(offsets, scrollTop);
@@ -13033,6 +13165,7 @@
13033
13165
  },
13034
13166
  openOnClear: Boolean,
13035
13167
  itemColor: String,
13168
+ noAutoScroll: Boolean,
13036
13169
  ...makeItemsProps({
13037
13170
  itemChildren: false
13038
13171
  })
@@ -13247,7 +13380,7 @@
13247
13380
  vue.watch(menu, () => {
13248
13381
  if (!props.hideSelected && menu.value && model.value.length) {
13249
13382
  const index = displayItems.value.findIndex(item => model.value.some(s => (props.valueComparator || deepEqual)(s.value, item.value)));
13250
- IN_BROWSER && window.requestAnimationFrame(() => {
13383
+ IN_BROWSER && !props.noAutoScroll && window.requestAnimationFrame(() => {
13251
13384
  index >= 0 && vVirtualScrollRef.value?.scrollToIndex(index);
13252
13385
  });
13253
13386
  }
@@ -13340,6 +13473,22 @@
13340
13473
  key: item.value,
13341
13474
  onClick: () => select(item, null)
13342
13475
  });
13476
+ if (item.raw.type === 'divider') {
13477
+ return slots.divider?.({
13478
+ props: item.raw,
13479
+ index
13480
+ }) ?? vue.createVNode(VDivider, vue.mergeProps(item.props, {
13481
+ "key": `divider-${index}`
13482
+ }), null);
13483
+ }
13484
+ if (item.raw.type === 'subheader') {
13485
+ return slots.subheader?.({
13486
+ props: item.raw,
13487
+ index
13488
+ }) ?? vue.createVNode(VListSubheader, vue.mergeProps(item.props, {
13489
+ "key": `subheader-${index}`
13490
+ }), null);
13491
+ }
13343
13492
  return slots.item?.({
13344
13493
  item,
13345
13494
  index,
@@ -13500,6 +13649,9 @@
13500
13649
  let match = -1;
13501
13650
  if ((query || customFiltersLength > 0) && !options?.noFilter) {
13502
13651
  if (typeof item === 'object') {
13652
+ if (['divider', 'subheader'].includes(item.raw?.type)) {
13653
+ continue;
13654
+ }
13503
13655
  const filterKeys = keys || Object.keys(transformed);
13504
13656
  for (const key of filterKeys) {
13505
13657
  const value = getPropertyFromItem(transformed, key);
@@ -13702,7 +13854,7 @@
13702
13854
  menu.value = !menu.value;
13703
13855
  }
13704
13856
  function onListKeydown(e) {
13705
- if (e.key !== ' ' && checkPrintable(e)) {
13857
+ if (checkPrintable(e) || e.key === 'Backspace') {
13706
13858
  vTextFieldRef.value?.focus();
13707
13859
  }
13708
13860
  }
@@ -13907,6 +14059,7 @@
13907
14059
  }, props.menuProps), {
13908
14060
  default: () => [hasList && vue.createVNode(VList, vue.mergeProps({
13909
14061
  "ref": listRef,
14062
+ "filterable": true,
13910
14063
  "selected": selectedValues.value,
13911
14064
  "selectStrategy": props.multiple ? 'independent' : 'single-independent',
13912
14065
  "onMousedown": e => e.preventDefault(),
@@ -13938,6 +14091,22 @@
13938
14091
  active: highlightFirst.value && index === 0 ? true : undefined,
13939
14092
  onClick: () => select(item, null)
13940
14093
  });
14094
+ if (item.raw.type === 'divider') {
14095
+ return slots.divider?.({
14096
+ props: item.raw,
14097
+ index
14098
+ }) ?? vue.createVNode(VDivider, vue.mergeProps(item.props, {
14099
+ "key": `divider-${index}`
14100
+ }), null);
14101
+ }
14102
+ if (item.raw.type === 'subheader') {
14103
+ return slots.subheader?.({
14104
+ props: item.raw,
14105
+ index
14106
+ }) ?? vue.createVNode(VListSubheader, vue.mergeProps(item.props, {
14107
+ "key": `subheader-${index}`
14108
+ }), null);
14109
+ }
13941
14110
  return slots.item?.({
13942
14111
  item,
13943
14112
  index,
@@ -14082,7 +14251,8 @@
14082
14251
  ...makeThemeProps(),
14083
14252
  ...makeTransitionProps({
14084
14253
  transition: 'scale-rotate-transition'
14085
- })
14254
+ }),
14255
+ ...makeDimensionProps()
14086
14256
  }, 'VBadge');
14087
14257
  const VBadge = genericComponent()({
14088
14258
  name: 'VBadge',
@@ -14112,6 +14282,9 @@
14112
14282
  const base = props.floating ? props.dot ? 2 : 4 : props.dot ? 8 : 12;
14113
14283
  return base + (['top', 'bottom'].includes(side) ? Number(props.offsetY ?? 0) : ['left', 'right'].includes(side) ? Number(props.offsetX ?? 0) : 0);
14114
14284
  });
14285
+ const {
14286
+ dimensionStyles
14287
+ } = useDimension(props);
14115
14288
  useRender(() => {
14116
14289
  const value = Number(props.content);
14117
14290
  const content = !props.max || isNaN(value) ? props.content : value <= Number(props.max) ? value : `${props.max}+`;
@@ -14133,7 +14306,7 @@
14133
14306
  }, {
14134
14307
  default: () => [vue.withDirectives(vue.createElementVNode("span", vue.mergeProps({
14135
14308
  "class": ['v-badge__badge', themeClasses.value, backgroundColorClasses.value, roundedClasses.value, textColorClasses.value],
14136
- "style": [backgroundColorStyles.value, textColorStyles.value, props.inline ? {} : locationStyles.value],
14309
+ "style": [backgroundColorStyles.value, textColorStyles.value, dimensionStyles.value, props.inline ? {} : locationStyles.value],
14137
14310
  "aria-atomic": "true",
14138
14311
  "aria-label": t(props.label, value),
14139
14312
  "aria-live": "polite",
@@ -17542,13 +17715,13 @@
17542
17715
  return null;
17543
17716
  }
17544
17717
  const sundayJanuarySecond2000 = new Date(2000, 0, 2);
17545
- function getWeekdays(locale, firstDayOfWeek) {
17718
+ function getWeekdays(locale, firstDayOfWeek, weekdayFormat) {
17546
17719
  const daysFromSunday = firstDayOfWeek ?? weekInfo(locale)?.firstDay ?? 0;
17547
17720
  return createRange(7).map(i => {
17548
17721
  const weekday = new Date(sundayJanuarySecond2000);
17549
17722
  weekday.setDate(sundayJanuarySecond2000.getDate() + daysFromSunday + i);
17550
17723
  return new Intl.DateTimeFormat(locale, {
17551
- weekday: 'narrow'
17724
+ weekday: weekdayFormat ?? 'narrow'
17552
17725
  }).format(weekday);
17553
17726
  });
17554
17727
  }
@@ -18012,9 +18185,9 @@
18012
18185
  getDiff(date, comparing, unit) {
18013
18186
  return getDiff(date, comparing, unit);
18014
18187
  }
18015
- getWeekdays(firstDayOfWeek) {
18188
+ getWeekdays(firstDayOfWeek, weekdayFormat) {
18016
18189
  const firstDay = firstDayOfWeek !== undefined ? Number(firstDayOfWeek) : undefined;
18017
- return getWeekdays(this.locale, firstDay);
18190
+ return getWeekdays(this.locale, firstDay, weekdayFormat);
18018
18191
  }
18019
18192
  getYear(date) {
18020
18193
  return getYear(date);
@@ -18369,6 +18542,7 @@
18369
18542
  _search.value = val ?? '';
18370
18543
  if (!props.multiple && !hasSelectionSlot.value) {
18371
18544
  model.value = [transformItem$3(props, val)];
18545
+ vue.nextTick(() => vVirtualScrollRef.value?.scrollToIndex(0));
18372
18546
  }
18373
18547
  if (val && props.multiple && props.delimiters?.length) {
18374
18548
  const values = val.split(new RegExp(`(?:${props.delimiters.join('|')})+`));
@@ -18449,7 +18623,7 @@
18449
18623
  menu.value = !menu.value;
18450
18624
  }
18451
18625
  function onListKeydown(e) {
18452
- if (e.key !== ' ' && checkPrintable(e)) {
18626
+ if (checkPrintable(e) || e.key === 'Backspace') {
18453
18627
  vTextFieldRef.value?.focus();
18454
18628
  }
18455
18629
  }
@@ -18654,6 +18828,7 @@
18654
18828
  }, props.menuProps), {
18655
18829
  default: () => [hasList && vue.createVNode(VList, vue.mergeProps({
18656
18830
  "ref": listRef,
18831
+ "filterable": true,
18657
18832
  "selected": selectedValues.value,
18658
18833
  "selectStrategy": props.multiple ? 'independent' : 'single-independent',
18659
18834
  "onMousedown": e => e.preventDefault(),
@@ -18685,6 +18860,22 @@
18685
18860
  active: highlightFirst.value && index === 0 ? true : undefined,
18686
18861
  onClick: () => select(item, null)
18687
18862
  });
18863
+ if (item.raw.type === 'divider') {
18864
+ return slots.divider?.({
18865
+ props: item.raw,
18866
+ index
18867
+ }) ?? vue.createVNode(VDivider, vue.mergeProps(item.props, {
18868
+ "key": `divider-${index}`
18869
+ }), null);
18870
+ }
18871
+ if (item.raw.type === 'subheader') {
18872
+ return slots.subheader?.({
18873
+ props: item.raw,
18874
+ index
18875
+ }) ?? vue.createVNode(VListSubheader, vue.mergeProps(item.props, {
18876
+ "key": `subheader-${index}`
18877
+ }), null);
18878
+ }
18688
18879
  return slots.item?.({
18689
18880
  item,
18690
18881
  index,
@@ -20567,6 +20758,7 @@
20567
20758
  color: String,
20568
20759
  disableSort: Boolean,
20569
20760
  fixedHeader: Boolean,
20761
+ lastFixed: Boolean,
20570
20762
  multiSort: Boolean,
20571
20763
  sortAscIcon: {
20572
20764
  type: IconValue,
@@ -20613,10 +20805,11 @@
20613
20805
  loaderClasses
20614
20806
  } = useLoader(props);
20615
20807
  function getFixedStyles(column, y) {
20616
- if (!(props.sticky || props.fixedHeader) && !column.fixed) return undefined;
20808
+ if (!(props.sticky || props.fixedHeader) && !(column.fixed || column.lastFixed)) return undefined;
20617
20809
  return {
20618
20810
  position: 'sticky',
20619
- left: column.fixed ? convertToUnit(column.fixedOffset) : undefined,
20811
+ left: column.fixed || column.lastFixed ? convertToUnit(column.fixedOffset) : undefined,
20812
+ right: column.lastFixed ? convertToUnit(column.fixedOffset ?? 0) : undefined,
20620
20813
  top: props.sticky || props.fixedHeader ? `calc(var(--v-table-header-height) * ${y})` : undefined
20621
20814
  };
20622
20815
  }
@@ -21132,11 +21325,18 @@
21132
21325
  }
21133
21326
  });
21134
21327
 
21328
+ // Types
21329
+
21135
21330
  const makeVTableProps = propsFactory({
21136
21331
  fixedHeader: Boolean,
21137
21332
  fixedFooter: Boolean,
21138
21333
  height: [Number, String],
21139
21334
  hover: Boolean,
21335
+ striped: {
21336
+ type: String,
21337
+ default: null,
21338
+ validator: v => ['even', 'odd'].includes(v)
21339
+ },
21140
21340
  ...makeComponentProps(),
21141
21341
  ...makeDensityProps(),
21142
21342
  ...makeTagProps(),
@@ -21163,7 +21363,9 @@
21163
21363
  'v-table--fixed-footer': props.fixedFooter,
21164
21364
  'v-table--has-top': !!slots.top,
21165
21365
  'v-table--has-bottom': !!slots.bottom,
21166
- 'v-table--hover': props.hover
21366
+ 'v-table--hover': props.hover,
21367
+ 'v-table--striped-even': props.striped === 'even',
21368
+ 'v-table--striped-odd': props.striped === 'odd'
21167
21369
  }, themeClasses.value, densityClasses.value, props.class]),
21168
21370
  "style": vue.normalizeStyle(props.style)
21169
21371
  }, {
@@ -22338,7 +22540,8 @@
22338
22540
  firstDayOfWeek: {
22339
22541
  type: [Number, String],
22340
22542
  default: undefined
22341
- }
22543
+ },
22544
+ weekdayFormat: String
22342
22545
  }, 'calendar');
22343
22546
  function useCalendar(props) {
22344
22547
  const adapter = useDate();
@@ -22579,7 +22782,7 @@
22579
22782
  "ref": daysRef,
22580
22783
  "key": daysInMonth.value[0].date?.toString(),
22581
22784
  "class": "v-date-picker-month__days"
22582
- }, [!props.hideWeekdays && adapter.getWeekdays(props.firstDayOfWeek).map(weekDay => vue.createElementVNode("div", {
22785
+ }, [!props.hideWeekdays && adapter.getWeekdays(props.firstDayOfWeek, props.weekdayFormat).map(weekDay => vue.createElementVNode("div", {
22583
22786
  "class": vue.normalizeClass(['v-date-picker-month__day', 'v-date-picker-month__weekday'])
22584
22787
  }, [weekDay])), daysInMonth.value.map((item, i) => {
22585
22788
  const slotProps = {
@@ -24194,6 +24397,9 @@
24194
24397
  startStatus.value = status;
24195
24398
  } else if (side === 'end') {
24196
24399
  endStatus.value = status;
24400
+ } else if (side === 'both') {
24401
+ startStatus.value = status;
24402
+ endStatus.value = status;
24197
24403
  }
24198
24404
  }
24199
24405
  function getStatus(side) {
@@ -24305,6 +24511,32 @@
24305
24511
  }, [renderSide('end', endStatus.value)])]
24306
24512
  });
24307
24513
  });
24514
+ function reset(side) {
24515
+ const effectiveSide = side ?? props.side;
24516
+ setStatus(effectiveSide, 'ok');
24517
+ vue.nextTick(() => {
24518
+ setScrollAmount(getScrollSize() - previousScrollSize + getScrollAmount());
24519
+ if (props.mode !== 'manual') {
24520
+ vue.nextTick(() => {
24521
+ window.requestAnimationFrame(() => {
24522
+ window.requestAnimationFrame(() => {
24523
+ window.requestAnimationFrame(() => {
24524
+ if (effectiveSide === 'both') {
24525
+ intersecting('start');
24526
+ intersecting('end');
24527
+ } else {
24528
+ intersecting(effectiveSide);
24529
+ }
24530
+ });
24531
+ });
24532
+ });
24533
+ });
24534
+ }
24535
+ });
24536
+ }
24537
+ return {
24538
+ reset
24539
+ };
24308
24540
  }
24309
24541
  });
24310
24542
 
@@ -25223,6 +25455,10 @@
25223
25455
  type: Number,
25224
25456
  default: 0
25225
25457
  },
25458
+ minFractionDigits: {
25459
+ type: Number,
25460
+ default: null
25461
+ },
25226
25462
  ...omit(makeVTextFieldProps(), ['modelValue', 'validationValue'])
25227
25463
  }, 'VNumberInput');
25228
25464
  const VNumberInput = genericComponent()({
@@ -25250,9 +25486,19 @@
25250
25486
  const isFocused = vue.shallowRef(props.focused);
25251
25487
  function correctPrecision(val) {
25252
25488
  let precision = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : props.precision;
25253
- const fixed = precision == null ? String(val) : val.toFixed(precision);
25254
- return isFocused.value ? Number(fixed).toString() // trim zeros
25255
- : fixed;
25489
+ if (precision == null) {
25490
+ return String(val);
25491
+ }
25492
+ let fixed = val.toFixed(precision);
25493
+ if (isFocused.value) {
25494
+ return Number(fixed).toString(); // trim zeros
25495
+ }
25496
+ if ((props.minFractionDigits ?? precision) < precision) {
25497
+ const trimLimit = precision - props.minFractionDigits;
25498
+ const [baseDigits, fractionDigits] = fixed.split('.');
25499
+ fixed = [baseDigits, fractionDigits.replace(new RegExp(`0{1,${trimLimit}}$`), '')].filter(Boolean).join('.');
25500
+ }
25501
+ return fixed;
25256
25502
  }
25257
25503
  const model = useProxiedModel(props, 'modelValue', null, val => val ?? null, val => val == null ? val ?? null : clamp(Number(val), props.min, props.max));
25258
25504
  const _inputText = vue.shallowRef(null);
@@ -25307,6 +25553,7 @@
25307
25553
  }
25308
25554
  };
25309
25555
  vue.watch(() => props.precision, () => formatInputValue());
25556
+ vue.watch(() => props.minFractionDigits, () => formatInputValue());
25310
25557
  vue.onMounted(() => {
25311
25558
  clampModel();
25312
25559
  });
@@ -25421,7 +25668,7 @@
25421
25668
  inputText.value = null;
25422
25669
  return;
25423
25670
  }
25424
- inputText.value = props.precision == null ? String(model.value) : model.value.toFixed(props.precision);
25671
+ inputText.value = correctPrecision(model.value);
25425
25672
  }
25426
25673
  function trimDecimalZeros() {
25427
25674
  if (controlsDisabled.value) return;
@@ -25681,9 +25928,10 @@
25681
25928
  e.preventDefault();
25682
25929
  e.stopPropagation();
25683
25930
  const clipboardText = e?.clipboardData?.getData('Text').trim().slice(0, length.value) ?? '';
25931
+ const finalIndex = clipboardText.length - 1 === -1 ? index : clipboardText.length - 1;
25684
25932
  if (isValidNumber(clipboardText)) return;
25685
25933
  model.value = clipboardText.split('');
25686
- inputRef.value?.[index].blur();
25934
+ inputRef.value?.[finalIndex].focus();
25687
25935
  }
25688
25936
  function reset() {
25689
25937
  model.value = [];
@@ -29468,7 +29716,7 @@
29468
29716
  };
29469
29717
  });
29470
29718
  }
29471
- const version$1 = "3.8.8-master.2025-06-10";
29719
+ const version$1 = "3.8.9-dev.2025-06-12";
29472
29720
  createVuetify$1.version = version$1;
29473
29721
 
29474
29722
  // Vue's inject() can only be used in setup
@@ -29493,7 +29741,7 @@
29493
29741
  ...options
29494
29742
  });
29495
29743
  };
29496
- const version = "3.8.8-master.2025-06-10";
29744
+ const version = "3.8.9-dev.2025-06-12";
29497
29745
  createVuetify.version = version;
29498
29746
 
29499
29747
  exports.blueprints = index;