@vuetify/v0 0.2.1 → 1.0.0-alpha.1
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.
- package/README.md +5 -1
- package/dist/{adapter-CCIeOzqr.mjs → adapter-CDpOQ8sn.mjs} +29 -20
- package/dist/{adapter-CcHB7rs3.d.mts → adapter-DoziXEzS.d.mts} +1 -1
- package/dist/{adapter-Drq1v5wV.mjs → adapter-DtgIrQsG.mjs} +5 -2
- package/dist/{adapter-BZjmDNJF.d.mts → adapter-J7ude3gO.d.mts} +2 -2
- package/dist/adapters-CFjrKxA2.mjs +5 -0
- package/dist/adapters-CiCexgsk.mjs +4 -0
- package/dist/{adapters-Cd8NDs18.mjs → adapters-Da2twiUn.mjs} +1 -1
- package/dist/adapters-DegUcfkd.mjs +2 -0
- package/dist/browser/index.js +10113 -8547
- package/dist/components/index.d.mts +3 -3
- package/dist/components/index.mjs +2 -2
- package/dist/{components-C142GPl_.mjs → components-CaPQCjo5.mjs} +1356 -386
- package/dist/composables/index.d.mts +11 -11
- package/dist/composables/index.mjs +24 -24
- package/dist/constants/index.mjs +2 -2
- package/dist/{createDataTable-DKE5QsMe.mjs → createDataTable-B4UflKnT.mjs} +100 -30
- package/dist/{createGroup-CzRZ9COh.mjs → createGroup-BC2nfttd.mjs} +24 -9
- package/dist/{createPagination-Tp4C4He8.mjs → createPagination-qvJkcTUY.mjs} +11 -7
- package/dist/{createSelection-Dsb3I0zm.mjs → createSelection-BA9guLah.mjs} +28 -21
- package/dist/{createSingle-C7IGUjP6.mjs → createSingle-BHxHLZeg.mjs} +13 -17
- package/dist/{createTokens-CHTawmud.mjs → createTokens-oJAeh262.mjs} +27 -15
- package/dist/{createTrinity-vvXk0ARD.mjs → createTrinity-BTCs1pYx.mjs} +34 -31
- package/dist/data-table/adapters/client/index.d.mts +1 -1
- package/dist/data-table/adapters/client/index.mjs +1 -1
- package/dist/data-table/adapters/index.d.mts +4 -4
- package/dist/data-table/adapters/index.mjs +5 -5
- package/dist/data-table/adapters/server/index.d.mts +1 -1
- package/dist/data-table/adapters/server/index.mjs +1 -1
- package/dist/data-table/adapters/virtual/index.d.mts +1 -1
- package/dist/data-table/adapters/virtual/index.mjs +1 -1
- package/dist/data-table/index.d.mts +6 -6
- package/dist/data-table/index.mjs +6 -6
- package/dist/date/index.mjs +1 -1
- package/dist/features/adapters/posthog/index.mjs +1 -1
- package/dist/features/index.d.mts +1 -1
- package/dist/features/index.mjs +1 -1
- package/dist/{globals-BrRJkuSY.mjs → globals-Berkg6mP.mjs} +1 -1
- package/dist/{htmlElements-DcYtv0hg.mjs → htmlElements-CIePKaTX.mjs} +1 -1
- package/dist/{index-76fQGkkO.d.mts → index-D4odwkZg.d.mts} +8 -11
- package/dist/{index-B_XLHftL.d.mts → index-DFvLSoto.d.mts} +296 -258
- package/dist/{index-DoGxDgdN.d.mts → index-DVPq3_Fz.d.mts} +55 -4
- package/dist/{index-BFuSOgUi.d.mts → index-Gk3x_7zD.d.mts} +1570 -437
- package/dist/{index-BUsrN1vL.d.mts → index-TtSSvHY6.d.mts} +1 -1
- package/dist/index.d.mts +12 -12
- package/dist/index.mjs +27 -27
- package/dist/json/attributes.json +276 -0
- package/dist/json/importMap.json +60 -0
- package/dist/json/tags.json +136 -2
- package/dist/json/web-types.json +1183 -344
- package/dist/locale/adapters/index.d.mts +2 -2
- package/dist/locale/adapters/index.mjs +2 -2
- package/dist/locale/adapters/v0/index.d.mts +1 -1
- package/dist/locale/adapters/v0/index.mjs +1 -1
- package/dist/locale/adapters/vue-i18n/index.d.mts +1 -1
- package/dist/locale/index.d.mts +3 -3
- package/dist/locale/index.mjs +2 -2
- package/dist/logger/adapters/index.mjs +2 -2
- package/dist/logger/adapters/v0/index.mjs +1 -1
- package/dist/logger/index.d.mts +1 -1
- package/dist/logger/index.mjs +2 -2
- package/dist/notifications/index.d.mts +1 -1
- package/dist/notifications/index.mjs +1 -1
- package/dist/palettes/ant/index.d.mts +1 -1
- package/dist/palettes/index.d.mts +2 -2
- package/dist/palettes/material/index.d.mts +1 -1
- package/dist/palettes/md1/index.d.mts +1 -1
- package/dist/palettes/md2/index.d.mts +1 -1
- package/dist/palettes/radix/index.d.mts +1 -1
- package/dist/palettes/tailwind/index.d.mts +1 -1
- package/dist/permissions/adapters/index.d.mts +1 -1
- package/dist/permissions/adapters/v0/index.d.mts +1 -1
- package/dist/permissions/index.d.mts +1 -1
- package/dist/permissions/index.mjs +1 -1
- package/dist/{posthog-Ccm8FQfD.mjs → posthog-CPvNHMUb.mjs} +1 -1
- package/dist/rules/index.d.mts +1 -1
- package/dist/rules/index.mjs +1 -1
- package/dist/{server-CIftA0pK.mjs → server-B6OtHgBT.mjs} +1 -1
- package/dist/{server-DNUTnISs.d.mts → server-ZiHJ4tfq.d.mts} +1 -1
- package/dist/storage/index.d.mts +1 -1
- package/dist/storage/index.mjs +1 -1
- package/dist/theme/adapters/index.d.mts +1 -1
- package/dist/theme/adapters/index.mjs +4 -4
- package/dist/theme/adapters/unhead/index.d.mts +1 -1
- package/dist/theme/adapters/unhead/index.mjs +1 -1
- package/dist/theme/adapters/v0/index.d.mts +1 -1
- package/dist/theme/adapters/v0/index.mjs +1 -1
- package/dist/theme/index.d.mts +1 -1
- package/dist/theme/index.mjs +3 -3
- package/dist/{toArray-doLQVI56.mjs → toArray-BA_JxFPv.mjs} +9 -0
- package/dist/{unhead--58lO3Z-.mjs → unhead-D2YqAcmF.mjs} +2 -2
- package/dist/{useClickOutside-BjO3Nty9.mjs → useClickOutside-B9a6Jext.mjs} +572 -160
- package/dist/{useFeatures-D9bGOvh4.mjs → useFeatures-wgMwaQ5W.mjs} +14 -5
- package/dist/{useLocale-BRQTt3Ka.mjs → useLocale-qMmVnAwS.mjs} +14 -5
- package/dist/{useLogger-Daz-Zr0z.mjs → useLogger-DFIRqm-N.mjs} +33 -16
- package/dist/{usePermissions-Yp3guoLH.mjs → usePermissions-tZhkBJmq.mjs} +11 -3
- package/dist/{useRules-BFPH7q8w.mjs → useRules-D3UXEtu7.mjs} +10 -2
- package/dist/{useTheme-zRa0Nh_g.mjs → useTheme-BeD__R8t.mjs} +14 -5
- package/dist/utilities/index.mjs +5 -5
- package/dist/{v0-CcV0VwYd.mjs → v0-6XptGYVx.mjs} +2 -2
- package/dist/{v0-DOq_Ia5H.mjs → v0-BG7RhKBv.mjs} +2 -2
- package/dist/{v0-Bno8FQ_F.mjs → v0-CNitYI9N.mjs} +1 -1
- package/dist/{v0-BpgPZ1qB.d.mts → v0-CWXUkMY0.d.mts} +1 -1
- package/dist/{v0-BAG8p0si.d.mts → v0-Dzw5OwNo.d.mts} +1 -1
- package/dist/{v0-D-AEQbvj.mjs → v0-I2mHxD9T.mjs} +1 -1
- package/dist/{virtual-BaQWQ9ji.d.mts → virtual-BCOfxnRS.d.mts} +1 -1
- package/dist/{virtual-D1HwNBLS.mjs → virtual-To-dSw2_.mjs} +2 -2
- package/package.json +10 -7
- package/SKILL.md +0 -95
- package/dist/adapters-BbNfjyvY.mjs +0 -5
- package/dist/adapters-BzRMo72Y.mjs +0 -4
- package/dist/adapters-_DyP1X4U.mjs +0 -2
- /package/dist/{index-c55Utzva.d.mts → index-DvuJXuAN.d.mts} +0 -0
|
@@ -1,22 +1,22 @@
|
|
|
1
|
-
import { a as SUPPORTS_OBSERVER, i as SUPPORTS_MUTATION_OBSERVER, n as SUPPORTS_INTERSECTION_OBSERVER, r as SUPPORTS_MATCH_MEDIA, t as IN_BROWSER } from "./globals-
|
|
1
|
+
import { a as SUPPORTS_OBSERVER, i as SUPPORTS_MUTATION_OBSERVER, n as SUPPORTS_INTERSECTION_OBSERVER, r as SUPPORTS_MATCH_MEDIA, t as IN_BROWSER } from "./globals-Berkg6mP.mjs";
|
|
2
2
|
import { clamp, instanceExists, isArray, isElement, isFunction, isNull, isNullOrUndefined, isNumber, isObject, isString, isUndefined, mergeDeep, range, resolveIds, resolveIndexes, useId as useId$1 } from "./utilities/index.mjs";
|
|
3
|
-
import { i as useContext,
|
|
4
|
-
import { a as createPlugin, i as useLogger, o as createPluginContext } from "./useLogger-
|
|
5
|
-
import { a as createRegistry } from "./createTokens-
|
|
6
|
-
import { i as createModel, t as createSelection } from "./createSelection-
|
|
7
|
-
import { t as createSingle } from "./createSingle-
|
|
8
|
-
import {
|
|
9
|
-
import {
|
|
10
|
-
import {
|
|
11
|
-
import {
|
|
12
|
-
import "./createPagination-
|
|
13
|
-
import "./createDataTable-
|
|
14
|
-
import { a as useRules, o as isStandardSchema } from "./useRules-
|
|
15
|
-
import "./useFeatures-
|
|
16
|
-
import "./usePermissions-
|
|
3
|
+
import { i as useContext, t as createTrinity } from "./createTrinity-BTCs1pYx.mjs";
|
|
4
|
+
import { a as createPlugin, i as useLogger, o as createPluginContext } from "./useLogger-DFIRqm-N.mjs";
|
|
5
|
+
import { a as createRegistry } from "./createTokens-oJAeh262.mjs";
|
|
6
|
+
import { i as createModel, t as createSelection } from "./createSelection-BA9guLah.mjs";
|
|
7
|
+
import { t as createSingle } from "./createSingle-BHxHLZeg.mjs";
|
|
8
|
+
import { a as useLocale } from "./useLocale-qMmVnAwS.mjs";
|
|
9
|
+
import { t as toArray } from "./toArray-BA_JxFPv.mjs";
|
|
10
|
+
import { n as createFilter } from "./adapter-CDpOQ8sn.mjs";
|
|
11
|
+
import { t as createGroup } from "./createGroup-BC2nfttd.mjs";
|
|
12
|
+
import "./createPagination-qvJkcTUY.mjs";
|
|
13
|
+
import "./createDataTable-B4UflKnT.mjs";
|
|
14
|
+
import { a as useRules, o as isStandardSchema } from "./useRules-D3UXEtu7.mjs";
|
|
15
|
+
import "./useFeatures-wgMwaQ5W.mjs";
|
|
16
|
+
import "./usePermissions-tZhkBJmq.mjs";
|
|
17
17
|
import { t as MemoryAdapter } from "./memory-XCMtkld1.mjs";
|
|
18
|
-
import "./useTheme-
|
|
19
|
-
import { computed, effectScope, isRef, nextTick, onMounted, onScopeDispose, reactive, readonly, ref, shallowReactive, shallowReadonly, shallowRef, toRef, toValue, unref, watch, watchEffect } from "vue";
|
|
18
|
+
import "./useTheme-BeD__R8t.mjs";
|
|
19
|
+
import { computed, effectScope, hasInjectionContext, isRef, nextTick, onMounted, onScopeDispose, reactive, readonly, ref, shallowReactive, shallowReadonly, shallowRef, toRef, toValue, unref, watch, watchEffect } from "vue";
|
|
20
20
|
//#region src/composables/createBreadcrumbs/index.ts
|
|
21
21
|
/**
|
|
22
22
|
* @module createBreadcrumbs
|
|
@@ -33,6 +33,16 @@ import { computed, effectScope, isRef, nextTick, onMounted, onScopeDispose, reac
|
|
|
33
33
|
* - Trinity pattern for dependency injection
|
|
34
34
|
*
|
|
35
35
|
* Inheritance chain: createRegistry → createSelection → createSingle → createBreadcrumbs
|
|
36
|
+
*
|
|
37
|
+
* @example
|
|
38
|
+
* ```ts
|
|
39
|
+
* import { createBreadcrumbs } from '@vuetify/v0'
|
|
40
|
+
*
|
|
41
|
+
* const crumbs = createBreadcrumbs()
|
|
42
|
+
* crumbs.register({ text: 'Home' })
|
|
43
|
+
* crumbs.register({ text: 'Docs' })
|
|
44
|
+
* console.log(crumbs.depth.value) // 2
|
|
45
|
+
* ```
|
|
36
46
|
*/
|
|
37
47
|
/**
|
|
38
48
|
* Creates a breadcrumbs navigation model.
|
|
@@ -63,6 +73,7 @@ function createBreadcrumbs(options = {}) {
|
|
|
63
73
|
const single = createSingle({
|
|
64
74
|
...options,
|
|
65
75
|
reactive: true,
|
|
76
|
+
events: true,
|
|
66
77
|
enroll: true
|
|
67
78
|
});
|
|
68
79
|
const depth = toRef(() => single.size);
|
|
@@ -129,12 +140,7 @@ function createBreadcrumbs(options = {}) {
|
|
|
129
140
|
*/
|
|
130
141
|
function createBreadcrumbsContext(_options = {}) {
|
|
131
142
|
const { namespace = "v0:breadcrumbs", ...options } = _options;
|
|
132
|
-
|
|
133
|
-
const context = createBreadcrumbs(options);
|
|
134
|
-
function provideBreadcrumbsContext(_context = context, app) {
|
|
135
|
-
return _provideBreadcrumbsContext(_context, app);
|
|
136
|
-
}
|
|
137
|
-
return createTrinity(useBreadcrumbsContext, provideBreadcrumbsContext, context);
|
|
143
|
+
return createTrinity(namespace, createBreadcrumbs(options));
|
|
138
144
|
}
|
|
139
145
|
/**
|
|
140
146
|
* Returns the current breadcrumbs instance from context.
|
|
@@ -178,6 +184,14 @@ function useBreadcrumbs(namespace = "v0:breadcrumbs") {
|
|
|
178
184
|
* - One-shot (default) or repeating mode
|
|
179
185
|
* - Automatic cleanup on scope disposal
|
|
180
186
|
* - SSR-safe
|
|
187
|
+
*
|
|
188
|
+
* @example
|
|
189
|
+
* ```ts
|
|
190
|
+
* import { useTimer } from '@vuetify/v0'
|
|
191
|
+
*
|
|
192
|
+
* const timer = useTimer(() => console.log('fired'), { duration: 5000 })
|
|
193
|
+
* timer.start()
|
|
194
|
+
* ```
|
|
181
195
|
*/
|
|
182
196
|
/**
|
|
183
197
|
* Creates a reactive timer with pause/resume support.
|
|
@@ -311,6 +325,15 @@ function useTimer(handler, options = {}) {
|
|
|
311
325
|
*
|
|
312
326
|
* Perfect for building select, combobox, tooltip, and menu components
|
|
313
327
|
* without wrapping the Popover compound component.
|
|
328
|
+
*
|
|
329
|
+
* @example
|
|
330
|
+
* ```ts
|
|
331
|
+
* import { usePopover } from '@vuetify/v0'
|
|
332
|
+
*
|
|
333
|
+
* const popover = usePopover()
|
|
334
|
+
* popover.open()
|
|
335
|
+
* popover.toggle()
|
|
336
|
+
* ```
|
|
314
337
|
*/
|
|
315
338
|
function usePopover(options = {}) {
|
|
316
339
|
const { id: _id, positionArea = "bottom", positionTry = "most-width bottom", showDelay = 0, hideDelay = 0 } = options;
|
|
@@ -392,6 +415,15 @@ function usePopover(options = {}) {
|
|
|
392
415
|
* useRovingFocus and useVirtualFocus.
|
|
393
416
|
*
|
|
394
417
|
* Not exported from the package barrel — consumed only by sibling composables.
|
|
418
|
+
*
|
|
419
|
+
* @example
|
|
420
|
+
* ```ts
|
|
421
|
+
* import { createFocusTraversal } from '#v0/composables/createFocusTraversal'
|
|
422
|
+
*
|
|
423
|
+
* const items = () => [{ id: 'a' }, { id: 'b' }, { id: 'c' }]
|
|
424
|
+
* const traversal = createFocusTraversal(items, id => console.log(id))
|
|
425
|
+
* traversal.next()
|
|
426
|
+
* ```
|
|
395
427
|
*/
|
|
396
428
|
function mod(length, index) {
|
|
397
429
|
return (index % length + length) % length;
|
|
@@ -574,6 +606,15 @@ function createFocusTraversal(items, activate, options = {}) {
|
|
|
574
606
|
*
|
|
575
607
|
* Perfect for comboboxes, autocompletes, listboxes, and other widgets
|
|
576
608
|
* where DOM focus must remain on the control element.
|
|
609
|
+
*
|
|
610
|
+
* @example
|
|
611
|
+
* ```ts
|
|
612
|
+
* import { useVirtualFocus } from '@vuetify/v0'
|
|
613
|
+
*
|
|
614
|
+
* const items = () => [{ id: 'a' }, { id: 'b' }, { id: 'c' }]
|
|
615
|
+
* const cursor = useVirtualFocus(items)
|
|
616
|
+
* cursor.next()
|
|
617
|
+
* ```
|
|
577
618
|
*/
|
|
578
619
|
function useVirtualFocus(items, options) {
|
|
579
620
|
const { control, target, orientation, circular, columns, onHighlight } = options;
|
|
@@ -616,6 +657,9 @@ function useVirtualFocus(items, options) {
|
|
|
616
657
|
}
|
|
617
658
|
const listener = target ?? control;
|
|
618
659
|
if (listener) useEventListener(listener, "keydown", traversal.onKeydown);
|
|
660
|
+
onScopeDispose(() => {
|
|
661
|
+
clear();
|
|
662
|
+
});
|
|
619
663
|
return {
|
|
620
664
|
highlightedId: traversal.activeId,
|
|
621
665
|
highlight,
|
|
@@ -709,6 +753,16 @@ var ServerAdapter = class {
|
|
|
709
753
|
* - Strict mode: reverts query to selected value on close if no match
|
|
710
754
|
* - Popover-based dropdown positioning
|
|
711
755
|
* - Context DI via createComboboxContext / useCombobox
|
|
756
|
+
*
|
|
757
|
+
* @example
|
|
758
|
+
* ```ts
|
|
759
|
+
* import { createCombobox } from '@vuetify/v0'
|
|
760
|
+
*
|
|
761
|
+
* const combobox = createCombobox({ strict: true })
|
|
762
|
+
* combobox.selection.register({ value: 'Apple' })
|
|
763
|
+
* combobox.selection.register({ value: 'Banana' })
|
|
764
|
+
* combobox.open()
|
|
765
|
+
* ```
|
|
712
766
|
*/
|
|
713
767
|
/**
|
|
714
768
|
* Creates a combobox context that orchestrates selection, popover, virtual
|
|
@@ -778,7 +832,7 @@ function createCombobox(options = {}) {
|
|
|
778
832
|
const isOpen = popover.isOpen;
|
|
779
833
|
const cursor = useVirtualFocus(() => selection.values().filter((ticket) => filtered.value.has(ticket.id) && !toValue(ticket.disabled)).map((ticket) => ({
|
|
780
834
|
id: ticket.id,
|
|
781
|
-
el: () => document.querySelector(`#${CSS.escape(`${id}-option-${ticket.id}`)}`),
|
|
835
|
+
el: () => IN_BROWSER ? document.querySelector(`#${CSS.escape(`${id}-option-${ticket.id}`)}`) : null,
|
|
782
836
|
disabled: ticket.disabled
|
|
783
837
|
})), {
|
|
784
838
|
control: inputEl,
|
|
@@ -879,12 +933,7 @@ function createCombobox(options = {}) {
|
|
|
879
933
|
*/
|
|
880
934
|
function createComboboxContext(options = {}) {
|
|
881
935
|
const { namespace = "v0:combobox", ...rest } = options;
|
|
882
|
-
|
|
883
|
-
const context = createCombobox(rest);
|
|
884
|
-
function provideCombobox(_context = context, app) {
|
|
885
|
-
return _provideCombobox(_context, app);
|
|
886
|
-
}
|
|
887
|
-
return createTrinity(useCombobox, provideCombobox, context);
|
|
936
|
+
return createTrinity(namespace, createCombobox(rest));
|
|
888
937
|
}
|
|
889
938
|
/**
|
|
890
939
|
* Injects the current combobox context from a parent provider.
|
|
@@ -924,6 +973,15 @@ function useCombobox(namespace = "v0:combobox") {
|
|
|
924
973
|
*
|
|
925
974
|
* Per-field validation logic lives in createValidation.
|
|
926
975
|
* createForm is the mothership — it coordinates, not creates.
|
|
976
|
+
*
|
|
977
|
+
* @example
|
|
978
|
+
* ```ts
|
|
979
|
+
* import { createForm } from '@vuetify/v0'
|
|
980
|
+
*
|
|
981
|
+
* const form = createForm()
|
|
982
|
+
* const isValid = await form.validate()
|
|
983
|
+
* if (isValid) form.submit()
|
|
984
|
+
* ```
|
|
927
985
|
*/
|
|
928
986
|
/**
|
|
929
987
|
* Creates a new form instance.
|
|
@@ -1023,12 +1081,7 @@ function createForm(options = {}) {
|
|
|
1023
1081
|
*/
|
|
1024
1082
|
function createFormContext(_options = {}) {
|
|
1025
1083
|
const { namespace = "v0:form", ...options } = _options;
|
|
1026
|
-
|
|
1027
|
-
const context = createForm(options);
|
|
1028
|
-
function provideFormContext(_context = context, app) {
|
|
1029
|
-
return _provideFormContext(_context, app);
|
|
1030
|
-
}
|
|
1031
|
-
return createTrinity(useFormContext, provideFormContext, context);
|
|
1084
|
+
return createTrinity(namespace, createForm(options));
|
|
1032
1085
|
}
|
|
1033
1086
|
/**
|
|
1034
1087
|
* Returns the current form instance.
|
|
@@ -1048,6 +1101,7 @@ function createFormContext(_options = {}) {
|
|
|
1048
1101
|
* ```
|
|
1049
1102
|
*/
|
|
1050
1103
|
function useForm(namespace = "v0:form") {
|
|
1104
|
+
if (!hasInjectionContext()) return void 0;
|
|
1051
1105
|
try {
|
|
1052
1106
|
return useContext(namespace);
|
|
1053
1107
|
} catch {
|
|
@@ -1073,8 +1127,18 @@ function useForm(namespace = "v0:form") {
|
|
|
1073
1127
|
* - Tri-state isValid (null/true/false)
|
|
1074
1128
|
*
|
|
1075
1129
|
* Uses useRules() to resolve alias strings via shared context.
|
|
1130
|
+
*
|
|
1131
|
+
* @example
|
|
1132
|
+
* ```ts
|
|
1133
|
+
* import { createValidation } from '@vuetify/v0'
|
|
1134
|
+
*
|
|
1135
|
+
* const validation = createValidation({
|
|
1136
|
+
* rules: [v => !!v || 'Required'],
|
|
1137
|
+
* })
|
|
1138
|
+
* await validation.validate('hello')
|
|
1139
|
+
* ```
|
|
1076
1140
|
*/
|
|
1077
|
-
const UNSET = Symbol("unset");
|
|
1141
|
+
const UNSET = /* @__PURE__ */ Symbol("unset");
|
|
1078
1142
|
/**
|
|
1079
1143
|
* Creates a per-input validation instance.
|
|
1080
1144
|
*
|
|
@@ -1146,6 +1210,13 @@ function createValidation(_options = {}) {
|
|
|
1146
1210
|
isValid.value = errorMessages.length === 0;
|
|
1147
1211
|
}
|
|
1148
1212
|
return errorMessages.length === 0;
|
|
1213
|
+
} catch (error) {
|
|
1214
|
+
if (gen !== generation) return isValid.value ?? false;
|
|
1215
|
+
if (!silent) {
|
|
1216
|
+
errors.value = [error instanceof Error ? error.message : "Validation error"];
|
|
1217
|
+
isValid.value = false;
|
|
1218
|
+
}
|
|
1219
|
+
return false;
|
|
1149
1220
|
} finally {
|
|
1150
1221
|
if (gen === generation && !silent) isValidating.value = false;
|
|
1151
1222
|
}
|
|
@@ -1191,6 +1262,16 @@ function createValidation(_options = {}) {
|
|
|
1191
1262
|
*
|
|
1192
1263
|
* No event handling — composables never bind DOM events. Components call
|
|
1193
1264
|
* validate() and write isFocused/isTouched when they choose.
|
|
1265
|
+
*
|
|
1266
|
+
* @example
|
|
1267
|
+
* ```ts
|
|
1268
|
+
* import { shallowRef } from 'vue'
|
|
1269
|
+
* import { createInput } from '@vuetify/v0'
|
|
1270
|
+
*
|
|
1271
|
+
* const value = shallowRef('')
|
|
1272
|
+
* const input = createInput({ value, label: 'Name', rules: ['required'] })
|
|
1273
|
+
* await input.validate()
|
|
1274
|
+
* ```
|
|
1194
1275
|
*/
|
|
1195
1276
|
function createInput(options) {
|
|
1196
1277
|
const { value, id = /* @__PURE__ */ useId$1(), label, name, form, required, disabled = false, readonly: _readonly = false, rules = [], error = false, errorMessages, dirty: dirtyFn, equals = (a, b) => a === b } = options;
|
|
@@ -1268,48 +1349,6 @@ function createInput(options) {
|
|
|
1268
1349
|
};
|
|
1269
1350
|
}
|
|
1270
1351
|
//#endregion
|
|
1271
|
-
//#region src/composables/createNested/strategies.ts
|
|
1272
|
-
/**
|
|
1273
|
-
* Multiple open strategy: allows multiple nodes to be open simultaneously.
|
|
1274
|
-
*
|
|
1275
|
-
* @remarks
|
|
1276
|
-
* Perfect for tree views, file explorers, and nested menus where users expect
|
|
1277
|
-
* to keep multiple sections expanded at once.
|
|
1278
|
-
*
|
|
1279
|
-
* @example
|
|
1280
|
-
* ```ts
|
|
1281
|
-
* const tree = createNested({ openStrategy: multipleOpenStrategy })
|
|
1282
|
-
* tree.open('node-1')
|
|
1283
|
-
* tree.open('node-2')
|
|
1284
|
-
* // Both nodes are now open
|
|
1285
|
-
* ```
|
|
1286
|
-
*/
|
|
1287
|
-
const multipleOpenStrategy = {
|
|
1288
|
-
onOpen: void 0,
|
|
1289
|
-
onClose: void 0
|
|
1290
|
-
};
|
|
1291
|
-
/**
|
|
1292
|
-
* Single open strategy: only one node can be open at a time (accordion behavior).
|
|
1293
|
-
*
|
|
1294
|
-
* @remarks
|
|
1295
|
-
* Perfect for accordions, single-select navigation, and contexts where only
|
|
1296
|
-
* one section should be visible at a time.
|
|
1297
|
-
*
|
|
1298
|
-
* @example
|
|
1299
|
-
* ```ts
|
|
1300
|
-
* const tree = createNested({ openStrategy: singleOpenStrategy })
|
|
1301
|
-
* tree.open('node-1') // node-1 opens
|
|
1302
|
-
* tree.open('node-2') // node-1 closes, node-2 opens
|
|
1303
|
-
* ```
|
|
1304
|
-
*/
|
|
1305
|
-
const singleOpenStrategy = {
|
|
1306
|
-
onOpen: (id, context) => {
|
|
1307
|
-
const toClose = [...context.openedIds].filter((openedId) => openedId !== id);
|
|
1308
|
-
for (const openedId of toClose) context.openedIds.delete(openedId);
|
|
1309
|
-
},
|
|
1310
|
-
onClose: void 0
|
|
1311
|
-
};
|
|
1312
|
-
//#endregion
|
|
1313
1352
|
//#region src/composables/createNested/index.ts
|
|
1314
1353
|
/**
|
|
1315
1354
|
* @module createNested
|
|
@@ -1323,17 +1362,20 @@ const singleOpenStrategy = {
|
|
|
1323
1362
|
* - Tree traversal utilities (getPath, getDescendants, etc.)
|
|
1324
1363
|
* - Cascade selection propagation through nested registers
|
|
1325
1364
|
* - `rootIds` tracking for top-level item detection
|
|
1326
|
-
* - Pluggable open strategies
|
|
1327
1365
|
*
|
|
1328
1366
|
* Inheritance chain: createSelection → createGroup → createNested
|
|
1367
|
+
*
|
|
1368
|
+
* @example
|
|
1369
|
+
* ```ts
|
|
1370
|
+
* import { createNested } from '@vuetify/v0'
|
|
1371
|
+
*
|
|
1372
|
+
* const tree = createNested()
|
|
1373
|
+
* const root = tree.register({ value: 'root' })
|
|
1374
|
+
* tree.register({ value: 'child', parentId: root.id })
|
|
1375
|
+
* tree.open(root.id)
|
|
1376
|
+
* ```
|
|
1329
1377
|
*/
|
|
1330
1378
|
/**
|
|
1331
|
-
* Resolves open mode to an OpenStrategy.
|
|
1332
|
-
*/
|
|
1333
|
-
function resolveOpenStrategy(open = "multiple") {
|
|
1334
|
-
return open === "single" ? singleOpenStrategy : multipleOpenStrategy;
|
|
1335
|
-
}
|
|
1336
|
-
/**
|
|
1337
1379
|
* Creates a new nested tree instance with hierarchical management.
|
|
1338
1380
|
*
|
|
1339
1381
|
* Extends `createGroup` to support parent-child relationships, tree traversal,
|
|
@@ -1372,10 +1414,9 @@ function resolveOpenStrategy(open = "multiple") {
|
|
|
1372
1414
|
* ```
|
|
1373
1415
|
*/
|
|
1374
1416
|
function createNested(_options = {}) {
|
|
1375
|
-
const { open: openMode = "multiple", openAll = false, reveal: revealOnOpen = false, selection: selectionMode = "cascade", active: activeMode = "single",
|
|
1417
|
+
const { open: openMode = "multiple", openAll = false, reveal: revealOnOpen = false, selection: selectionMode = "cascade", active: activeMode = "single", ...options } = _options;
|
|
1376
1418
|
const mandatoryOption = _options.mandatory ?? false;
|
|
1377
1419
|
const multipleOption = _options.multiple ?? true;
|
|
1378
|
-
const resolvedOpenStrategy = openStrategy ?? resolveOpenStrategy(openMode);
|
|
1379
1420
|
const group = createGroup(options);
|
|
1380
1421
|
const logger = useLogger();
|
|
1381
1422
|
const children = shallowReactive(/* @__PURE__ */ new Map());
|
|
@@ -1407,7 +1448,9 @@ function createNested(_options = {}) {
|
|
|
1407
1448
|
const item = group.get(id);
|
|
1408
1449
|
if (!item || toValue(item.disabled)) continue;
|
|
1409
1450
|
openedIds.add(id);
|
|
1410
|
-
|
|
1451
|
+
if (openMode === "single") {
|
|
1452
|
+
for (const openedId of openedIds) if (openedId !== id) openedIds.delete(openedId);
|
|
1453
|
+
}
|
|
1411
1454
|
if (revealOnOpen) {
|
|
1412
1455
|
let parentId = parents.get(id);
|
|
1413
1456
|
while (!/* @__PURE__ */ isUndefined(parentId)) {
|
|
@@ -1424,7 +1467,6 @@ function createNested(_options = {}) {
|
|
|
1424
1467
|
const item = group.get(id);
|
|
1425
1468
|
if (!item || toValue(item.disabled)) continue;
|
|
1426
1469
|
openedIds.delete(id);
|
|
1427
|
-
resolvedOpenStrategy.onClose?.(id, context);
|
|
1428
1470
|
}
|
|
1429
1471
|
}
|
|
1430
1472
|
function flip(ids) {
|
|
@@ -1508,7 +1550,13 @@ function createNested(_options = {}) {
|
|
|
1508
1550
|
function getPath(id) {
|
|
1509
1551
|
const path = [];
|
|
1510
1552
|
let currentId = id;
|
|
1553
|
+
const visited = /* @__PURE__ */ new Set();
|
|
1511
1554
|
while (!/* @__PURE__ */ isUndefined(currentId)) {
|
|
1555
|
+
if (visited.has(currentId)) {
|
|
1556
|
+
logger.warn(`Circular parent reference detected at "${currentId}".`);
|
|
1557
|
+
break;
|
|
1558
|
+
}
|
|
1559
|
+
visited.add(currentId);
|
|
1512
1560
|
path.unshift(currentId);
|
|
1513
1561
|
currentId = parents.get(currentId);
|
|
1514
1562
|
}
|
|
@@ -1867,7 +1915,7 @@ function createNested(_options = {}) {
|
|
|
1867
1915
|
rootIds.clear();
|
|
1868
1916
|
group.reset();
|
|
1869
1917
|
}
|
|
1870
|
-
|
|
1918
|
+
return {
|
|
1871
1919
|
...group,
|
|
1872
1920
|
children,
|
|
1873
1921
|
parents,
|
|
@@ -1903,7 +1951,6 @@ function createNested(_options = {}) {
|
|
|
1903
1951
|
deactivateAll,
|
|
1904
1952
|
toFlat,
|
|
1905
1953
|
multiple: toValue(multipleOption),
|
|
1906
|
-
openStrategy: resolvedOpenStrategy,
|
|
1907
1954
|
select,
|
|
1908
1955
|
unselect,
|
|
1909
1956
|
toggle,
|
|
@@ -1920,7 +1967,6 @@ function createNested(_options = {}) {
|
|
|
1920
1967
|
return group.size;
|
|
1921
1968
|
}
|
|
1922
1969
|
};
|
|
1923
|
-
return context;
|
|
1924
1970
|
}
|
|
1925
1971
|
/**
|
|
1926
1972
|
* Creates a new nested context with provide/inject pattern.
|
|
@@ -1942,12 +1988,7 @@ function createNested(_options = {}) {
|
|
|
1942
1988
|
*/
|
|
1943
1989
|
function createNestedContext(_options = {}) {
|
|
1944
1990
|
const { namespace = "v0:nested", ...options } = _options;
|
|
1945
|
-
|
|
1946
|
-
const context = createNested(options);
|
|
1947
|
-
function provideNestedContext(_context = context, app) {
|
|
1948
|
-
return _provideNestedContext(_context, app);
|
|
1949
|
-
}
|
|
1950
|
-
return createTrinity(useNestedContext, provideNestedContext, context);
|
|
1991
|
+
return createTrinity(namespace, createNested(options));
|
|
1951
1992
|
}
|
|
1952
1993
|
/**
|
|
1953
1994
|
* Returns the current nested instance from context.
|
|
@@ -1973,6 +2014,15 @@ function useNested(namespace = "v0:nested") {
|
|
|
1973
2014
|
*
|
|
1974
2015
|
* Used by createSlider, createNumberField, and other numeric composables.
|
|
1975
2016
|
* Handles floating-point precision correction internally.
|
|
2017
|
+
*
|
|
2018
|
+
* @example
|
|
2019
|
+
* ```ts
|
|
2020
|
+
* import { createNumeric } from '@vuetify/v0'
|
|
2021
|
+
*
|
|
2022
|
+
* const numeric = createNumeric({ min: 0, max: 10, step: 1 })
|
|
2023
|
+
* console.log(numeric.snap(3.7)) // 4
|
|
2024
|
+
* console.log(numeric.toPercent(5)) // 0.5
|
|
2025
|
+
* ```
|
|
1976
2026
|
*/
|
|
1977
2027
|
function decimalPlaces(n) {
|
|
1978
2028
|
const s = String(n);
|
|
@@ -1984,6 +2034,7 @@ function createNumeric(options = {}) {
|
|
|
1984
2034
|
const extent = max - min;
|
|
1985
2035
|
const decimals = Math.max(decimalPlaces(step), Number.isFinite(min) ? decimalPlaces(min) : 0);
|
|
1986
2036
|
function snap(value) {
|
|
2037
|
+
if (!Number.isFinite(value)) return min;
|
|
1987
2038
|
if (step <= 0 || !Number.isFinite(min)) return /* @__PURE__ */ clamp(value, min, max);
|
|
1988
2039
|
const result = min + Math.round((/* @__PURE__ */ clamp(value, min, max) - min) / step) * step;
|
|
1989
2040
|
return /* @__PURE__ */ clamp(decimals > 0 ? +result.toFixed(decimals) : result, min, max);
|
|
@@ -2046,6 +2097,15 @@ function createNumeric(options = {}) {
|
|
|
2046
2097
|
* @remarks
|
|
2047
2098
|
* Orchestrator composable that composes createInput + createNumeric + Intl.NumberFormat.
|
|
2048
2099
|
* Manages a numeric value with formatting, parsing, stepping, and field state.
|
|
2100
|
+
*
|
|
2101
|
+
* @example
|
|
2102
|
+
* ```ts
|
|
2103
|
+
* import { createNumberField } from '@vuetify/v0'
|
|
2104
|
+
*
|
|
2105
|
+
* const field = createNumberField({ min: 0, max: 100, step: 5 })
|
|
2106
|
+
* field.increment()
|
|
2107
|
+
* console.log(field.value.value) // 5
|
|
2108
|
+
* ```
|
|
2049
2109
|
*/
|
|
2050
2110
|
function createNumberField(options = {}) {
|
|
2051
2111
|
const { value = ref(null), locale = "en-US", format: formatOptions, clamp: shouldClamp = true, disabled = false, readonly: _readonly = false, min, max, step, leap, wrap, id, label, name, rules, error, errorMessages } = options;
|
|
@@ -2170,6 +2230,16 @@ function createNumberField(options = {}) {
|
|
|
2170
2230
|
* - Perfect for hydration-safe rendering
|
|
2171
2231
|
*
|
|
2172
2232
|
* Essential for composables that need to behave differently during SSR vs client-side.
|
|
2233
|
+
*
|
|
2234
|
+
* @example
|
|
2235
|
+
* ```ts
|
|
2236
|
+
* import { useHydration } from '@vuetify/v0'
|
|
2237
|
+
*
|
|
2238
|
+
* const { isHydrated } = useHydration()
|
|
2239
|
+
* if (isHydrated.value) {
|
|
2240
|
+
* // safe for client-only logic
|
|
2241
|
+
* }
|
|
2242
|
+
* ```
|
|
2173
2243
|
*/
|
|
2174
2244
|
/**
|
|
2175
2245
|
* Creates a new hydration instance.
|
|
@@ -2258,6 +2328,15 @@ const [createHydrationContext, createHydrationPlugin, useHydration] = createPlug
|
|
|
2258
2328
|
* Accepts refs, getters, raw DOM elements, or Vue component instances
|
|
2259
2329
|
* and normalizes them to a plain Element. Uses structural typing to
|
|
2260
2330
|
* avoid cross-version Vue Ref incompatibilities.
|
|
2331
|
+
*
|
|
2332
|
+
* @example
|
|
2333
|
+
* ```ts
|
|
2334
|
+
* import { shallowRef } from 'vue'
|
|
2335
|
+
* import { toElement } from '@vuetify/v0'
|
|
2336
|
+
*
|
|
2337
|
+
* const el = shallowRef<HTMLElement | null>(null)
|
|
2338
|
+
* const resolved = toElement(el) // HTMLElement | undefined
|
|
2339
|
+
* ```
|
|
2261
2340
|
*/
|
|
2262
2341
|
/**
|
|
2263
2342
|
* Resolves a {@link MaybeElementRef} to a DOM Element or undefined.
|
|
@@ -2305,6 +2384,19 @@ function toElement(target) {
|
|
|
2305
2384
|
* - `undefined` — not yet created
|
|
2306
2385
|
* - `null` — permanently stopped (`stop()` was called; `setup()` is a no-op)
|
|
2307
2386
|
* - instance — active observer
|
|
2387
|
+
*
|
|
2388
|
+
* @example
|
|
2389
|
+
* ```ts
|
|
2390
|
+
* import { createObserver } from '#v0/composables/createObserver'
|
|
2391
|
+
*
|
|
2392
|
+
* const observer = createObserver(target, entries => {
|
|
2393
|
+
* console.log(entries)
|
|
2394
|
+
* }, {
|
|
2395
|
+
* supports: true,
|
|
2396
|
+
* create: cb => new ResizeObserver(cb),
|
|
2397
|
+
* observe: (o, el) => o.observe(el),
|
|
2398
|
+
* })
|
|
2399
|
+
* ```
|
|
2308
2400
|
*/
|
|
2309
2401
|
function createObserver(target, userCallback, config) {
|
|
2310
2402
|
const { isHydrated } = useHydration();
|
|
@@ -2397,6 +2489,17 @@ function createObserver(target, userCallback, config) {
|
|
|
2397
2489
|
* - Box model options (content-box/border-box)
|
|
2398
2490
|
*
|
|
2399
2491
|
* Perfect for responsive components and size-based rendering.
|
|
2492
|
+
*
|
|
2493
|
+
* @example
|
|
2494
|
+
* ```ts
|
|
2495
|
+
* import { useTemplateRef } from 'vue'
|
|
2496
|
+
* import { useResizeObserver } from '@vuetify/v0'
|
|
2497
|
+
*
|
|
2498
|
+
* const target = useTemplateRef('target')
|
|
2499
|
+
* useResizeObserver(target, entries => {
|
|
2500
|
+
* console.log(entries[0].contentRect.width)
|
|
2501
|
+
* })
|
|
2502
|
+
* ```
|
|
2400
2503
|
*/
|
|
2401
2504
|
/**
|
|
2402
2505
|
* A composable that uses the Resize Observer API to detect when an element's
|
|
@@ -2508,8 +2611,8 @@ function useElementSize(target) {
|
|
|
2508
2611
|
_pause();
|
|
2509
2612
|
}
|
|
2510
2613
|
return {
|
|
2511
|
-
width,
|
|
2512
|
-
height,
|
|
2614
|
+
width: shallowReadonly(width),
|
|
2615
|
+
height: shallowReadonly(height),
|
|
2513
2616
|
isActive,
|
|
2514
2617
|
isPaused: shallowReadonly(isPaused),
|
|
2515
2618
|
pause,
|
|
@@ -2537,6 +2640,16 @@ function useElementSize(target) {
|
|
|
2537
2640
|
*
|
|
2538
2641
|
* Use variable mode (default) for items with different widths like Breadcrumbs.
|
|
2539
2642
|
* Use uniform mode (itemWidth option) for same-width items like Pagination buttons.
|
|
2643
|
+
*
|
|
2644
|
+
* @example
|
|
2645
|
+
* ```ts
|
|
2646
|
+
* import { useTemplateRef } from 'vue'
|
|
2647
|
+
* import { createOverflow } from '@vuetify/v0'
|
|
2648
|
+
*
|
|
2649
|
+
* const el = useTemplateRef('container')
|
|
2650
|
+
* const overflow = createOverflow({ container: el })
|
|
2651
|
+
* console.log(overflow.capacity.value) // number of items that fit
|
|
2652
|
+
* ```
|
|
2540
2653
|
*/
|
|
2541
2654
|
/**
|
|
2542
2655
|
* Creates a new overflow context for computing how many items fit in a container.
|
|
@@ -2625,7 +2738,7 @@ function createOverflow(options = {}) {
|
|
|
2625
2738
|
if (available <= 0) return 0;
|
|
2626
2739
|
const g = toValue(gap);
|
|
2627
2740
|
const uniformWidth = toValue(itemWidth) ?? 0;
|
|
2628
|
-
if (
|
|
2741
|
+
if (!/* @__PURE__ */ isUndefined(itemWidth) && uniformWidth <= 0) return Infinity;
|
|
2629
2742
|
if (uniformWidth > 0) {
|
|
2630
2743
|
const subsequent = uniformWidth + g;
|
|
2631
2744
|
if (available < uniformWidth) return 0;
|
|
@@ -2676,12 +2789,7 @@ function createOverflow(options = {}) {
|
|
|
2676
2789
|
*/
|
|
2677
2790
|
function createOverflowContext(_options = {}) {
|
|
2678
2791
|
const { namespace = "v0:overflow", ...options } = _options;
|
|
2679
|
-
|
|
2680
|
-
const context = createOverflow(options);
|
|
2681
|
-
function provideOverflowContext(_context = context, app) {
|
|
2682
|
-
return _provideOverflowContext(_context, app);
|
|
2683
|
-
}
|
|
2684
|
-
return createTrinity(useOverflowContext, provideOverflowContext, context);
|
|
2792
|
+
return createTrinity(namespace, createOverflow(options));
|
|
2685
2793
|
}
|
|
2686
2794
|
/**
|
|
2687
2795
|
* Returns the current overflow context from dependency injection.
|
|
@@ -2725,6 +2833,15 @@ function useOverflow(namespace = "v0:overflow") {
|
|
|
2725
2833
|
* All segments stay selected (multiple: true, enroll: true) so
|
|
2726
2834
|
* selectedValues always reflects the full set of segment values.
|
|
2727
2835
|
* Compatible with useProxyModel for v-model bridging.
|
|
2836
|
+
*
|
|
2837
|
+
* @example
|
|
2838
|
+
* ```ts
|
|
2839
|
+
* import { createProgress } from '@vuetify/v0'
|
|
2840
|
+
*
|
|
2841
|
+
* const progress = createProgress({ min: 0, max: 100, value: 25 })
|
|
2842
|
+
* progress.register({ value: 50 })
|
|
2843
|
+
* console.log(progress.percent.value)
|
|
2844
|
+
* ```
|
|
2728
2845
|
*/
|
|
2729
2846
|
/**
|
|
2730
2847
|
* Creates a progress instance with model-based segment tracking.
|
|
@@ -2818,12 +2935,7 @@ function createProgress(options = {}) {
|
|
|
2818
2935
|
*/
|
|
2819
2936
|
function createProgressContext(_options = {}) {
|
|
2820
2937
|
const { namespace = "v0:progress", ...options } = _options;
|
|
2821
|
-
|
|
2822
|
-
const context = createProgress(options);
|
|
2823
|
-
function provide(_context = context, app) {
|
|
2824
|
-
return _provide(_context, app);
|
|
2825
|
-
}
|
|
2826
|
-
return createTrinity(use, provide, context);
|
|
2938
|
+
return createTrinity(namespace, createProgress(options));
|
|
2827
2939
|
}
|
|
2828
2940
|
/**
|
|
2829
2941
|
* Returns the current progress instance from context.
|
|
@@ -2852,6 +2964,15 @@ function useProgress(namespace = "v0:progress") {
|
|
|
2852
2964
|
* Built on top of createRegistry, the queue automatically manages timeouts for tickets,
|
|
2853
2965
|
* ensuring only the first ticket in the queue is active at any time. When a ticket
|
|
2854
2966
|
* expires or is removed, the next ticket in the queue automatically becomes active.
|
|
2967
|
+
*
|
|
2968
|
+
* @example
|
|
2969
|
+
* ```ts
|
|
2970
|
+
* import { createQueue } from '@vuetify/v0'
|
|
2971
|
+
*
|
|
2972
|
+
* const queue = createQueue()
|
|
2973
|
+
* queue.register({ value: 'Notification 1', timeout: 3000 })
|
|
2974
|
+
* queue.register({ value: 'Notification 2', timeout: 3000 })
|
|
2975
|
+
* ```
|
|
2855
2976
|
*/
|
|
2856
2977
|
/**
|
|
2857
2978
|
* Creates a new queue instance
|
|
@@ -3002,12 +3123,7 @@ function createQueue(_options = {}) {
|
|
|
3002
3123
|
*/
|
|
3003
3124
|
function createQueueContext(_options = {}) {
|
|
3004
3125
|
const { namespace = "v0:queue", ...options } = _options;
|
|
3005
|
-
|
|
3006
|
-
const context = createQueue(options);
|
|
3007
|
-
function provideQueueContext(_context = context, app) {
|
|
3008
|
-
return _provideQueueContext(_context, app);
|
|
3009
|
-
}
|
|
3010
|
-
return createTrinity(useQueueContext, provideQueueContext, context);
|
|
3126
|
+
return createTrinity(namespace, createQueue(options));
|
|
3011
3127
|
}
|
|
3012
3128
|
/**
|
|
3013
3129
|
* Returns the current queue instance.
|
|
@@ -3050,6 +3166,15 @@ function useQueue(namespace = "v0:queue") {
|
|
|
3050
3166
|
* Unlike registry-based composables, rating tracks a single number
|
|
3051
3167
|
* within a range with computed item states, making it efficient
|
|
3052
3168
|
* for any star/icon rating use case.
|
|
3169
|
+
*
|
|
3170
|
+
* @example
|
|
3171
|
+
* ```ts
|
|
3172
|
+
* import { createRating } from '@vuetify/v0'
|
|
3173
|
+
*
|
|
3174
|
+
* const rating = createRating({ size: 5, value: 3 })
|
|
3175
|
+
* rating.select(4)
|
|
3176
|
+
* console.log(rating.value.value) // 4
|
|
3177
|
+
* ```
|
|
3053
3178
|
*/
|
|
3054
3179
|
/**
|
|
3055
3180
|
* Creates a rating instance.
|
|
@@ -3147,12 +3272,7 @@ function createRating(_options = {}) {
|
|
|
3147
3272
|
*/
|
|
3148
3273
|
function createRatingContext(_options = {}) {
|
|
3149
3274
|
const { namespace = "v0:rating", ...options } = _options;
|
|
3150
|
-
|
|
3151
|
-
const context = createRating(options);
|
|
3152
|
-
function provideRatingContext(_context = context, app) {
|
|
3153
|
-
return _provideRatingContext(_context, app);
|
|
3154
|
-
}
|
|
3155
|
-
return createTrinity(useRatingContext, provideRatingContext, context);
|
|
3275
|
+
return createTrinity(namespace, createRating(options));
|
|
3156
3276
|
}
|
|
3157
3277
|
/**
|
|
3158
3278
|
* Returns the current rating instance from context.
|
|
@@ -3198,6 +3318,16 @@ function useRating(namespace = "v0:rating") {
|
|
|
3198
3318
|
* Designed for single-thumb, range, and multi-thumb sliders.
|
|
3199
3319
|
* Also reusable for color picker tracks, media scrubbers,
|
|
3200
3320
|
* gradient editors, and other 1D value-on-track controls.
|
|
3321
|
+
*
|
|
3322
|
+
* @example
|
|
3323
|
+
* ```ts
|
|
3324
|
+
* import { shallowRef } from 'vue'
|
|
3325
|
+
* import { createSlider } from '@vuetify/v0'
|
|
3326
|
+
*
|
|
3327
|
+
* const slider = createSlider({ min: 0, max: 100, step: 5 })
|
|
3328
|
+
* slider.register({ value: shallowRef(25) })
|
|
3329
|
+
* slider.set(0, 60)
|
|
3330
|
+
* ```
|
|
3201
3331
|
*/
|
|
3202
3332
|
/**
|
|
3203
3333
|
* Creates slider state with value math, step snapping, and multi-thumb support.
|
|
@@ -3385,6 +3515,16 @@ function createSlider(options = {}) {
|
|
|
3385
3515
|
* - Perfect for wizards, carousels, pagination, onboarding flows
|
|
3386
3516
|
*
|
|
3387
3517
|
* Inheritance chain: createRegistry → createSelection → createSingle → createStep
|
|
3518
|
+
*
|
|
3519
|
+
* @example
|
|
3520
|
+
* ```ts
|
|
3521
|
+
* import { createStep } from '@vuetify/v0'
|
|
3522
|
+
*
|
|
3523
|
+
* const wizard = createStep({ circular: false })
|
|
3524
|
+
* wizard.register({ value: 'step-1' })
|
|
3525
|
+
* wizard.register({ value: 'step-2' })
|
|
3526
|
+
* wizard.next()
|
|
3527
|
+
* ```
|
|
3388
3528
|
*/
|
|
3389
3529
|
/**
|
|
3390
3530
|
* Creates a new step instance with navigation through items.
|
|
@@ -3533,12 +3673,7 @@ function createStep(_options = {}) {
|
|
|
3533
3673
|
*/
|
|
3534
3674
|
function createStepContext(_options = {}) {
|
|
3535
3675
|
const { namespace = "v0:step", ...options } = _options;
|
|
3536
|
-
|
|
3537
|
-
const context = createStep(options);
|
|
3538
|
-
function provideStepContext(_context = context, app) {
|
|
3539
|
-
return _provideStepContext(_context, app);
|
|
3540
|
-
}
|
|
3541
|
-
return createTrinity(useStepContext, provideStepContext, context);
|
|
3676
|
+
return createTrinity(namespace, createStep(options));
|
|
3542
3677
|
}
|
|
3543
3678
|
/**
|
|
3544
3679
|
* Returns the current step instance.
|
|
@@ -3588,6 +3723,16 @@ function useStep(namespace = "v0:step") {
|
|
|
3588
3723
|
* - Perfect for command pattern, history tracking
|
|
3589
3724
|
*
|
|
3590
3725
|
* Extends createRegistry with temporal navigation capabilities.
|
|
3726
|
+
*
|
|
3727
|
+
* @example
|
|
3728
|
+
* ```ts
|
|
3729
|
+
* import { createTimeline } from '@vuetify/v0'
|
|
3730
|
+
*
|
|
3731
|
+
* const timeline = createTimeline({ size: 5 })
|
|
3732
|
+
* timeline.register({ value: 'action-1' })
|
|
3733
|
+
* timeline.register({ value: 'action-2' })
|
|
3734
|
+
* timeline.undo()
|
|
3735
|
+
* ```
|
|
3591
3736
|
*/
|
|
3592
3737
|
/**
|
|
3593
3738
|
* Creates a new timeline instance.
|
|
@@ -3699,12 +3844,7 @@ function createTimeline(_options = {}) {
|
|
|
3699
3844
|
*/
|
|
3700
3845
|
function createTimelineContext(_options = {}) {
|
|
3701
3846
|
const { namespace = "v0:timeline", ...options } = _options;
|
|
3702
|
-
|
|
3703
|
-
const context = createTimeline(options);
|
|
3704
|
-
function provideTimelineContext(_context = context, app) {
|
|
3705
|
-
return _provideTimelineContext(_context, app);
|
|
3706
|
-
}
|
|
3707
|
-
return createTrinity(useTimelineContext, provideTimelineContext, context);
|
|
3847
|
+
return createTrinity(namespace, createTimeline(options));
|
|
3708
3848
|
}
|
|
3709
3849
|
/**
|
|
3710
3850
|
* Returns the current timeline instance.
|
|
@@ -3748,6 +3888,16 @@ function useTimeline(namespace = "v0:timeline") {
|
|
|
3748
3888
|
* - Configurable overscan (extra items rendered for smooth scrolling)
|
|
3749
3889
|
*
|
|
3750
3890
|
* Perfect for large data sets, chat apps, and infinite scroll implementations.
|
|
3891
|
+
*
|
|
3892
|
+
* @example
|
|
3893
|
+
* ```ts
|
|
3894
|
+
* import { shallowRef } from 'vue'
|
|
3895
|
+
* import { createVirtual } from '@vuetify/v0'
|
|
3896
|
+
*
|
|
3897
|
+
* const items = shallowRef(Array.from({ length: 10000 }, (_, i) => ({ id: i })))
|
|
3898
|
+
* const virtual = createVirtual(items, { itemHeight: 40 })
|
|
3899
|
+
* console.log(virtual.items.value)
|
|
3900
|
+
* ```
|
|
3751
3901
|
*/
|
|
3752
3902
|
/**
|
|
3753
3903
|
* Virtual scrolling composable for efficiently rendering large lists
|
|
@@ -4040,12 +4190,7 @@ function createVirtual(items, _options = {}) {
|
|
|
4040
4190
|
*/
|
|
4041
4191
|
function createVirtualContext(items, _options = {}) {
|
|
4042
4192
|
const { namespace = "v0:virtual", ...options } = _options;
|
|
4043
|
-
|
|
4044
|
-
const context = createVirtual(items, options);
|
|
4045
|
-
function provideVirtualContext(_context = context, app) {
|
|
4046
|
-
return _provideVirtualContext(_context, app);
|
|
4047
|
-
}
|
|
4048
|
-
return createTrinity(useVirtualContext, provideVirtualContext, context);
|
|
4193
|
+
return createTrinity(namespace, createVirtual(items, options));
|
|
4049
4194
|
}
|
|
4050
4195
|
/**
|
|
4051
4196
|
* Returns the current virtual context from dependency injection.
|
|
@@ -4095,6 +4240,16 @@ function useVirtual(namespace = "v0:virtual") {
|
|
|
4095
4240
|
* - Type preservation
|
|
4096
4241
|
*
|
|
4097
4242
|
* Perfect for creating reactive versions of plain objects while automatically unwrapping refs.
|
|
4243
|
+
*
|
|
4244
|
+
* @example
|
|
4245
|
+
* ```ts
|
|
4246
|
+
* import { shallowRef } from 'vue'
|
|
4247
|
+
* import { toReactive } from '@vuetify/v0'
|
|
4248
|
+
*
|
|
4249
|
+
* const source = { name: shallowRef('Alice'), age: 30 }
|
|
4250
|
+
* const reactive = toReactive(source)
|
|
4251
|
+
* console.log(reactive.name) // 'Alice' (auto-unwrapped)
|
|
4252
|
+
* ```
|
|
4098
4253
|
*/
|
|
4099
4254
|
function createMapProxy(refObject) {
|
|
4100
4255
|
let mapProxy;
|
|
@@ -4252,6 +4407,14 @@ function toReactive(objectRef) {
|
|
|
4252
4407
|
* - Custom breakpoint configuration
|
|
4253
4408
|
*
|
|
4254
4409
|
* Perfect for responsive layouts and conditional rendering based on screen size.
|
|
4410
|
+
*
|
|
4411
|
+
* @example
|
|
4412
|
+
* ```ts
|
|
4413
|
+
* import { useBreakpoints } from '@vuetify/v0'
|
|
4414
|
+
*
|
|
4415
|
+
* const { current, isMobile, smAndUp } = useBreakpoints()
|
|
4416
|
+
* console.log(current.value) // 'md'
|
|
4417
|
+
* ```
|
|
4255
4418
|
*/
|
|
4256
4419
|
/**
|
|
4257
4420
|
* Creates default breakpoint configuration.
|
|
@@ -4590,12 +4753,7 @@ function createDate(options) {
|
|
|
4590
4753
|
*/
|
|
4591
4754
|
function createDateContext(options) {
|
|
4592
4755
|
const { namespace = "v0:date", ...dateOptions } = options;
|
|
4593
|
-
|
|
4594
|
-
const context = createDate(dateOptions);
|
|
4595
|
-
function provideDateContext(_context = context, app) {
|
|
4596
|
-
return _provideDateContext(_context, app);
|
|
4597
|
-
}
|
|
4598
|
-
return createTrinity(useDateContext, provideDateContext, context);
|
|
4756
|
+
return createTrinity(namespace, createDate(dateOptions));
|
|
4599
4757
|
}
|
|
4600
4758
|
/**
|
|
4601
4759
|
* Creates a new date plugin.
|
|
@@ -4703,7 +4861,7 @@ function normalizeKey(key) {
|
|
|
4703
4861
|
}
|
|
4704
4862
|
//#endregion
|
|
4705
4863
|
//#region src/composables/useHotkey/parsing.ts
|
|
4706
|
-
const logger = useLogger();
|
|
4864
|
+
const logger = /* @__PURE__ */ useLogger();
|
|
4707
4865
|
const MODIFIERS = [
|
|
4708
4866
|
"ctrl",
|
|
4709
4867
|
"shift",
|
|
@@ -4879,6 +5037,14 @@ function splitKeySequence(str) {
|
|
|
4879
5037
|
* - SSR-safe (no-op when not in browser)
|
|
4880
5038
|
*
|
|
4881
5039
|
* Builds on useEventListener for lifecycle-managed keyboard events.
|
|
5040
|
+
*
|
|
5041
|
+
* @example
|
|
5042
|
+
* ```ts
|
|
5043
|
+
* import { useHotkey } from '@vuetify/v0'
|
|
5044
|
+
*
|
|
5045
|
+
* useHotkey('ctrl+k', () => console.log('opened palette'))
|
|
5046
|
+
* useHotkey('g-h', () => console.log('go home'))
|
|
5047
|
+
* ```
|
|
4882
5048
|
*/
|
|
4883
5049
|
const isMac = IN_BROWSER && /mac|iphone|ipad|ipod/i.test(navigator?.userAgent ?? "");
|
|
4884
5050
|
/**
|
|
@@ -4922,6 +5088,7 @@ function useHotkey(keys, callback, options = {}, _platform) {
|
|
|
4922
5088
|
let isSequence = false;
|
|
4923
5089
|
let groupIndex = 0;
|
|
4924
5090
|
function isInputFocused() {
|
|
5091
|
+
if (!IN_BROWSER) return false;
|
|
4925
5092
|
if (toValue(inputs)) return false;
|
|
4926
5093
|
const activeElement = document.activeElement;
|
|
4927
5094
|
if (!activeElement) return false;
|
|
@@ -5050,6 +5217,115 @@ function matchesKeyGroup(e, group, platformIsMac) {
|
|
|
5050
5217
|
return modifiersMatch && e.key.toLowerCase() === actualKey.toLowerCase();
|
|
5051
5218
|
}
|
|
5052
5219
|
//#endregion
|
|
5220
|
+
//#region src/composables/useImage/index.ts
|
|
5221
|
+
/**
|
|
5222
|
+
* @module useImage
|
|
5223
|
+
*
|
|
5224
|
+
* @see https://0.vuetifyjs.com/composables/system/use-image
|
|
5225
|
+
*
|
|
5226
|
+
* @remarks
|
|
5227
|
+
* Image loading state machine with deferred loading support.
|
|
5228
|
+
*
|
|
5229
|
+
* Key features:
|
|
5230
|
+
* - State machine: idle → loading → loaded | error
|
|
5231
|
+
* - Reactive `eager` gate withholds the source until ready
|
|
5232
|
+
* - Automatic reset when `src` changes
|
|
5233
|
+
* - Manual `retry()` to re-attempt after error
|
|
5234
|
+
* - Bind-ready handlers and gated source
|
|
5235
|
+
* - SSR-safe
|
|
5236
|
+
*
|
|
5237
|
+
* Perfect for image components, lightboxes, lazy-loaded galleries,
|
|
5238
|
+
* and any UI that needs to react to image load state.
|
|
5239
|
+
*
|
|
5240
|
+
* @example
|
|
5241
|
+
* ```ts
|
|
5242
|
+
* import { useImage } from '@vuetify/v0'
|
|
5243
|
+
*
|
|
5244
|
+
* const { status, source, onLoad, onError } = useImage({
|
|
5245
|
+
* src: 'https://example.com/img.png',
|
|
5246
|
+
* })
|
|
5247
|
+
* ```
|
|
5248
|
+
*/
|
|
5249
|
+
/**
|
|
5250
|
+
* Tracks image loading state as a reactive state machine.
|
|
5251
|
+
*
|
|
5252
|
+
* @param options Configuration options
|
|
5253
|
+
* @returns Image context with state refs and event handlers
|
|
5254
|
+
*
|
|
5255
|
+
* @see https://0.vuetifyjs.com/composables/system/use-image
|
|
5256
|
+
*
|
|
5257
|
+
* @example
|
|
5258
|
+
* ```ts
|
|
5259
|
+
* import { toRef } from 'vue'
|
|
5260
|
+
* import { useImage } from '@vuetify/v0'
|
|
5261
|
+
*
|
|
5262
|
+
* const props = defineProps<{ src: string }>()
|
|
5263
|
+
*
|
|
5264
|
+
* const { source, isLoaded, onLoad, onError, retry } = useImage({
|
|
5265
|
+
* src: toRef(() => props.src),
|
|
5266
|
+
* })
|
|
5267
|
+
* ```
|
|
5268
|
+
*
|
|
5269
|
+
* @example
|
|
5270
|
+
* Composed with `useIntersectionObserver` for lazy loading:
|
|
5271
|
+
* ```ts
|
|
5272
|
+
* const target = shallowRef<HTMLElement>()
|
|
5273
|
+
* const { isIntersecting } = useIntersectionObserver(target, () => {}, {
|
|
5274
|
+
* once: true,
|
|
5275
|
+
* rootMargin: '200px',
|
|
5276
|
+
* })
|
|
5277
|
+
*
|
|
5278
|
+
* const { source, onLoad, onError } = useImage({
|
|
5279
|
+
* src: toRef(() => props.src),
|
|
5280
|
+
* eager: isIntersecting,
|
|
5281
|
+
* })
|
|
5282
|
+
* ```
|
|
5283
|
+
*/
|
|
5284
|
+
function useImage(options) {
|
|
5285
|
+
const { src, eager = true } = options;
|
|
5286
|
+
const status = shallowRef(toValue(eager) ? "loading" : "idle");
|
|
5287
|
+
const isIdle = toRef(() => status.value === "idle");
|
|
5288
|
+
const isLoading = toRef(() => status.value === "loading");
|
|
5289
|
+
const isLoaded = toRef(() => status.value === "loaded");
|
|
5290
|
+
const isError = toRef(() => status.value === "error");
|
|
5291
|
+
const source = toRef(() => status.value === "idle" ? void 0 : toValue(src));
|
|
5292
|
+
function onLoad() {
|
|
5293
|
+
status.value = "loaded";
|
|
5294
|
+
}
|
|
5295
|
+
function onError() {
|
|
5296
|
+
status.value = "error";
|
|
5297
|
+
}
|
|
5298
|
+
function retry() {
|
|
5299
|
+
const resumeAs = toValue(eager) ? "loading" : "idle";
|
|
5300
|
+
status.value = "idle";
|
|
5301
|
+
nextTick(() => {
|
|
5302
|
+
status.value = resumeAs;
|
|
5303
|
+
});
|
|
5304
|
+
}
|
|
5305
|
+
const stopEager = watch(() => toValue(eager), (value) => {
|
|
5306
|
+
if (value && status.value === "idle") status.value = "loading";
|
|
5307
|
+
else if (!value && status.value !== "loaded" && status.value !== "error") status.value = "idle";
|
|
5308
|
+
});
|
|
5309
|
+
const stopSrc = watch(() => toValue(src), () => {
|
|
5310
|
+
status.value = toValue(eager) ? "loading" : "idle";
|
|
5311
|
+
});
|
|
5312
|
+
onScopeDispose(() => {
|
|
5313
|
+
stopEager();
|
|
5314
|
+
stopSrc();
|
|
5315
|
+
}, true);
|
|
5316
|
+
return {
|
|
5317
|
+
status: shallowReadonly(status),
|
|
5318
|
+
isIdle,
|
|
5319
|
+
isLoading,
|
|
5320
|
+
isLoaded,
|
|
5321
|
+
isError,
|
|
5322
|
+
source,
|
|
5323
|
+
onLoad,
|
|
5324
|
+
onError,
|
|
5325
|
+
retry
|
|
5326
|
+
};
|
|
5327
|
+
}
|
|
5328
|
+
//#endregion
|
|
5053
5329
|
//#region src/composables/useIntersectionObserver/index.ts
|
|
5054
5330
|
/**
|
|
5055
5331
|
* @module useIntersectionObserver
|
|
@@ -5070,6 +5346,17 @@ function matchesKeyGroup(e, group, platformIsMac) {
|
|
|
5070
5346
|
* - Immediate callback option
|
|
5071
5347
|
*
|
|
5072
5348
|
* Perfect for lazy loading, infinite scroll, and visibility detection.
|
|
5349
|
+
*
|
|
5350
|
+
* @example
|
|
5351
|
+
* ```ts
|
|
5352
|
+
* import { useTemplateRef } from 'vue'
|
|
5353
|
+
* import { useIntersectionObserver } from '@vuetify/v0'
|
|
5354
|
+
*
|
|
5355
|
+
* const target = useTemplateRef('target')
|
|
5356
|
+
* useIntersectionObserver(target, entries => {
|
|
5357
|
+
* console.log(entries[0].isIntersecting)
|
|
5358
|
+
* })
|
|
5359
|
+
* ```
|
|
5073
5360
|
*/
|
|
5074
5361
|
/**
|
|
5075
5362
|
* A composable that uses the Intersection Observer API to detect when an element
|
|
@@ -5230,6 +5517,15 @@ function useElementIntersection(target, options = {}) {
|
|
|
5230
5517
|
*
|
|
5231
5518
|
* Perfect for dialogs, menus, tooltips, and any component with
|
|
5232
5519
|
* conditionally rendered content.
|
|
5520
|
+
*
|
|
5521
|
+
* @example
|
|
5522
|
+
* ```ts
|
|
5523
|
+
* import { shallowRef } from 'vue'
|
|
5524
|
+
* import { useLazy } from '@vuetify/v0'
|
|
5525
|
+
*
|
|
5526
|
+
* const isOpen = shallowRef(false)
|
|
5527
|
+
* const { hasContent, onAfterLeave } = useLazy(isOpen)
|
|
5528
|
+
* ```
|
|
5233
5529
|
*/
|
|
5234
5530
|
/**
|
|
5235
5531
|
* Deferred content rendering for performance optimization.
|
|
@@ -5320,6 +5616,14 @@ function useLazy(active, options = {}) {
|
|
|
5320
5616
|
* - Supports both static and dynamic queries
|
|
5321
5617
|
*
|
|
5322
5618
|
* Perfect for responsive conditionals beyond breakpoint detection.
|
|
5619
|
+
*
|
|
5620
|
+
* @example
|
|
5621
|
+
* ```ts
|
|
5622
|
+
* import { useMediaQuery } from '@vuetify/v0'
|
|
5623
|
+
*
|
|
5624
|
+
* const { matches } = useMediaQuery('(prefers-color-scheme: dark)')
|
|
5625
|
+
* console.log(matches.value) // true/false
|
|
5626
|
+
* ```
|
|
5323
5627
|
*/
|
|
5324
5628
|
/**
|
|
5325
5629
|
* Reactive media query matching.
|
|
@@ -5440,6 +5744,17 @@ function usePrefersContrast() {
|
|
|
5440
5744
|
* - Configurable observation options (childList, attributes, characterData, etc.)
|
|
5441
5745
|
*
|
|
5442
5746
|
* Perfect for detecting DOM changes and responding to mutations.
|
|
5747
|
+
*
|
|
5748
|
+
* @example
|
|
5749
|
+
* ```ts
|
|
5750
|
+
* import { useTemplateRef } from 'vue'
|
|
5751
|
+
* import { useMutationObserver } from '@vuetify/v0'
|
|
5752
|
+
*
|
|
5753
|
+
* const target = useTemplateRef('target')
|
|
5754
|
+
* useMutationObserver(target, records => {
|
|
5755
|
+
* console.log(records)
|
|
5756
|
+
* }, { childList: true })
|
|
5757
|
+
* ```
|
|
5443
5758
|
*/
|
|
5444
5759
|
/**
|
|
5445
5760
|
* A composable that uses the Mutation Observer API to detect changes in the DOM.
|
|
@@ -5551,6 +5866,14 @@ function useMutationObserver(target, callback, options = {}) {
|
|
|
5551
5866
|
* - Toast queue with pause/resume and auto-dismiss
|
|
5552
5867
|
* - Adapter integration via event system
|
|
5553
5868
|
* - Plugin installation via createNotificationsPlugin
|
|
5869
|
+
*
|
|
5870
|
+
* @example
|
|
5871
|
+
* ```ts
|
|
5872
|
+
* import { useNotifications } from '@vuetify/v0'
|
|
5873
|
+
*
|
|
5874
|
+
* const notifications = useNotifications()
|
|
5875
|
+
* notifications.send({ subject: 'Saved', severity: 'success' })
|
|
5876
|
+
* ```
|
|
5554
5877
|
*/
|
|
5555
5878
|
function createNotifications(options = {}) {
|
|
5556
5879
|
const { timeout = 3e3, ...registryOptions } = options;
|
|
@@ -6072,6 +6395,15 @@ const [createNotificationsContext, createNotificationsPlugin, useNotifications]
|
|
|
6072
6395
|
* - Re-entry during leave: cancels exit, stays mounted
|
|
6073
6396
|
* - Immediate mode: auto-unmounts if done() not called (fast path)
|
|
6074
6397
|
* - SSR-safe: starts unmounted
|
|
6398
|
+
*
|
|
6399
|
+
* @example
|
|
6400
|
+
* ```ts
|
|
6401
|
+
* import { shallowRef } from 'vue'
|
|
6402
|
+
* import { usePresence } from '@vuetify/v0'
|
|
6403
|
+
*
|
|
6404
|
+
* const isOpen = shallowRef(false)
|
|
6405
|
+
* const { isMounted, state, done } = usePresence({ present: isOpen })
|
|
6406
|
+
* ```
|
|
6075
6407
|
*/
|
|
6076
6408
|
/**
|
|
6077
6409
|
* Animation-agnostic mount lifecycle management.
|
|
@@ -6183,6 +6515,16 @@ function usePresence(options) {
|
|
|
6183
6515
|
* - Works with any ModelContext (Selection, Slider, etc.)
|
|
6184
6516
|
*
|
|
6185
6517
|
* Bridges the gap between model composables and Vue's v-model.
|
|
6518
|
+
*
|
|
6519
|
+
* @example
|
|
6520
|
+
* ```ts
|
|
6521
|
+
* import { shallowRef } from 'vue'
|
|
6522
|
+
* import { createSelection, useProxyModel } from '@vuetify/v0'
|
|
6523
|
+
*
|
|
6524
|
+
* const selection = createSelection({ events: true })
|
|
6525
|
+
* const model = shallowRef<string[]>([])
|
|
6526
|
+
* useProxyModel(selection, model, { multiple: true })
|
|
6527
|
+
* ```
|
|
6186
6528
|
*/
|
|
6187
6529
|
/**
|
|
6188
6530
|
* Syncs a ref with a model context bidirectionally.
|
|
@@ -6287,6 +6629,16 @@ function useProxyModel(context, model, options) {
|
|
|
6287
6629
|
* - Callable function with cancel method
|
|
6288
6630
|
*
|
|
6289
6631
|
* Perfect for throttling updates to the next animation frame.
|
|
6632
|
+
*
|
|
6633
|
+
* @example
|
|
6634
|
+
* ```ts
|
|
6635
|
+
* import { useRaf } from '@vuetify/v0'
|
|
6636
|
+
*
|
|
6637
|
+
* const update = useRaf(timestamp => {
|
|
6638
|
+
* // runs on next animation frame
|
|
6639
|
+
* })
|
|
6640
|
+
* update()
|
|
6641
|
+
* ```
|
|
6290
6642
|
*/
|
|
6291
6643
|
/**
|
|
6292
6644
|
* Scope-disposed safe requestAnimationFrame.
|
|
@@ -6355,6 +6707,15 @@ function useRaf(callback) {
|
|
|
6355
6707
|
* - Auto-attaches keydown listener when target is provided
|
|
6356
6708
|
*
|
|
6357
6709
|
* Perfect for toolbars, menus, tree items, grids, and other composite widgets.
|
|
6710
|
+
*
|
|
6711
|
+
* @example
|
|
6712
|
+
* ```ts
|
|
6713
|
+
* import { useRovingFocus } from '@vuetify/v0'
|
|
6714
|
+
*
|
|
6715
|
+
* const items = () => [{ id: 'a' }, { id: 'b' }, { id: 'c' }]
|
|
6716
|
+
* const focus = useRovingFocus(items, { orientation: 'horizontal' })
|
|
6717
|
+
* focus.next()
|
|
6718
|
+
* ```
|
|
6358
6719
|
*/
|
|
6359
6720
|
function useRovingFocus(items, options = {}) {
|
|
6360
6721
|
const { orientation, circular, columns, onFocus, target } = options;
|
|
@@ -6432,6 +6793,14 @@ var Vuetify0RtlAdapter = class {
|
|
|
6432
6793
|
* - Subtree overrides via context provision
|
|
6433
6794
|
*
|
|
6434
6795
|
* Independent from useLocale — Vuetify connects them via adapter.
|
|
6796
|
+
*
|
|
6797
|
+
* @example
|
|
6798
|
+
* ```ts
|
|
6799
|
+
* import { useRtl } from '@vuetify/v0'
|
|
6800
|
+
*
|
|
6801
|
+
* const { isRtl, toggle } = useRtl()
|
|
6802
|
+
* toggle() // flip direction
|
|
6803
|
+
* ```
|
|
6435
6804
|
*/
|
|
6436
6805
|
/**
|
|
6437
6806
|
* Creates a new RTL direction instance.
|
|
@@ -6483,6 +6852,15 @@ const [createRtlContext, createRtlPlugin, useRtl] = createPluginContext("v0:rtl"
|
|
|
6483
6852
|
* - Auto-cleanup when registered within component setup
|
|
6484
6853
|
*
|
|
6485
6854
|
* Built on createSelection for consistent ticket-based management.
|
|
6855
|
+
*
|
|
6856
|
+
* @example
|
|
6857
|
+
* ```ts
|
|
6858
|
+
* import { useStack } from '@vuetify/v0'
|
|
6859
|
+
*
|
|
6860
|
+
* const stack = useStack()
|
|
6861
|
+
* const ticket = stack.register({ onDismiss: () => console.log('dismissed') })
|
|
6862
|
+
* ticket.select()
|
|
6863
|
+
* ```
|
|
6486
6864
|
*/
|
|
6487
6865
|
/**
|
|
6488
6866
|
* Creates a new stack instance for managing overlay z-indexes.
|
|
@@ -6600,12 +6978,7 @@ function createStack(_options = {}) {
|
|
|
6600
6978
|
*/
|
|
6601
6979
|
function createStackContext(_options = {}) {
|
|
6602
6980
|
const { namespace = "v0:stack", ...options } = _options;
|
|
6603
|
-
|
|
6604
|
-
const context = createStack(options);
|
|
6605
|
-
function provideStackContext(_context = context, app) {
|
|
6606
|
-
return _provideStackContext(_context, app);
|
|
6607
|
-
}
|
|
6608
|
-
return createTrinity(useStackContext, provideStackContext, context);
|
|
6981
|
+
return createTrinity(namespace, createStack(options));
|
|
6609
6982
|
}
|
|
6610
6983
|
/**
|
|
6611
6984
|
* Creates a Vue plugin to provide stack context at app level.
|
|
@@ -6712,6 +7085,15 @@ function useStack(namespace = "v0:stack") {
|
|
|
6712
7085
|
* - Automatic cleanup on remove/clear
|
|
6713
7086
|
*
|
|
6714
7087
|
* Uses adapter pattern to abstract storage implementation details.
|
|
7088
|
+
*
|
|
7089
|
+
* @example
|
|
7090
|
+
* ```ts
|
|
7091
|
+
* import { useStorage } from '@vuetify/v0'
|
|
7092
|
+
*
|
|
7093
|
+
* const storage = useStorage()
|
|
7094
|
+
* const theme = storage.get('theme', 'light')
|
|
7095
|
+
* theme.value = 'dark' // persists automatically
|
|
7096
|
+
* ```
|
|
6715
7097
|
*/
|
|
6716
7098
|
/**
|
|
6717
7099
|
* Creates a new storage instance.
|
|
@@ -6753,7 +7135,7 @@ function createStorage(options = {}) {
|
|
|
6753
7135
|
if (/* @__PURE__ */ isNullOrUndefined(raw)) return void 0;
|
|
6754
7136
|
try {
|
|
6755
7137
|
const parsed = serializer.read(raw);
|
|
6756
|
-
if (ttl && /* @__PURE__ */ isObject(parsed) && "
|
|
7138
|
+
if (ttl && /* @__PURE__ */ isObject(parsed) && "__v0" in parsed && "__v" in parsed) {
|
|
6757
7139
|
const envelope = parsed;
|
|
6758
7140
|
if (Date.now() - envelope.__t > ttl) {
|
|
6759
7141
|
adapter?.removeItem(prefixedKey);
|
|
@@ -6769,7 +7151,7 @@ function createStorage(options = {}) {
|
|
|
6769
7151
|
}
|
|
6770
7152
|
function writeStored(prefixedKey, value) {
|
|
6771
7153
|
const wrapped = ttl ? {
|
|
6772
|
-
|
|
7154
|
+
__v0: 1,
|
|
6773
7155
|
__v: value,
|
|
6774
7156
|
__t: Date.now()
|
|
6775
7157
|
} : value;
|
|
@@ -6859,6 +7241,17 @@ const [createStorageContext, createStoragePlugin, useStorage] = createPluginCont
|
|
|
6859
7241
|
*
|
|
6860
7242
|
* Perfect for conditional side effects, feature flags, and performance optimization
|
|
6861
7243
|
* by only running reactive effects when needed.
|
|
7244
|
+
*
|
|
7245
|
+
* @example
|
|
7246
|
+
* ```ts
|
|
7247
|
+
* import { shallowRef } from 'vue'
|
|
7248
|
+
* import { useToggleScope } from '@vuetify/v0'
|
|
7249
|
+
*
|
|
7250
|
+
* const isEnabled = shallowRef(false)
|
|
7251
|
+
* const { isActive } = useToggleScope(isEnabled, () => {
|
|
7252
|
+
* // effects run while isEnabled is true
|
|
7253
|
+
* })
|
|
7254
|
+
* ```
|
|
6862
7255
|
*/
|
|
6863
7256
|
/**
|
|
6864
7257
|
* Conditionally manages an effect scope based on a reactive boolean source.
|
|
@@ -6954,6 +7347,15 @@ function useToggleScope(source, fn) {
|
|
|
6954
7347
|
* - Multiple overloads for type safety
|
|
6955
7348
|
*
|
|
6956
7349
|
* Perfect for safely managing event listeners in Vue components.
|
|
7350
|
+
*
|
|
7351
|
+
* @example
|
|
7352
|
+
* ```ts
|
|
7353
|
+
* import { useEventListener } from '@vuetify/v0'
|
|
7354
|
+
*
|
|
7355
|
+
* useEventListener(window, 'resize', () => {
|
|
7356
|
+
* console.log('window resized')
|
|
7357
|
+
* })
|
|
7358
|
+
* ```
|
|
6957
7359
|
*/
|
|
6958
7360
|
/**
|
|
6959
7361
|
* Attaches an event listener to a target.
|
|
@@ -7050,6 +7452,15 @@ function useDocumentEventListener(event, listener, options) {
|
|
|
7050
7452
|
* Accessibility: This composable handles pointer interactions only. For accessible
|
|
7051
7453
|
* components (dialogs, popovers, menus), pair with `useHotkey` for Escape key
|
|
7052
7454
|
* dismissal per WCAG/APG requirements.
|
|
7455
|
+
*
|
|
7456
|
+
* @example
|
|
7457
|
+
* ```ts
|
|
7458
|
+
* import { useTemplateRef } from 'vue'
|
|
7459
|
+
* import { useClickOutside } from '@vuetify/v0'
|
|
7460
|
+
*
|
|
7461
|
+
* const target = useTemplateRef('popover')
|
|
7462
|
+
* useClickOutside(target, () => console.log('clicked outside'))
|
|
7463
|
+
* ```
|
|
7053
7464
|
*/
|
|
7054
7465
|
/**
|
|
7055
7466
|
* Detects clicks outside of the specified element(s).
|
|
@@ -7237,6 +7648,7 @@ function useClickOutside(target, handler, options = {}) {
|
|
|
7237
7648
|
* Handle window blur - detect focus moving to iframe.
|
|
7238
7649
|
*/
|
|
7239
7650
|
function onBlur(event) {
|
|
7651
|
+
if (!IN_BROWSER) return;
|
|
7240
7652
|
if (isPaused.value) return;
|
|
7241
7653
|
if (event.defaultPrevented) return;
|
|
7242
7654
|
if (document.activeElement instanceof HTMLIFrameElement) {
|
|
@@ -7287,4 +7699,4 @@ function useClickOutside(target, handler, options = {}) {
|
|
|
7287
7699
|
};
|
|
7288
7700
|
}
|
|
7289
7701
|
//#endregion
|
|
7290
|
-
export {
|
|
7702
|
+
export { createStep as $, usePrefersContrast as A, createForm as At, createDatePlugin as B, useTimer as Bt, usePresence as C, createNumberField as Ct, useNotifications as D, useNested as Dt, createNotificationsPlugin as E, createNestedContext as Et, useIntersectionObserver as F, useCombobox as Ft, useBreakpoints as G, createBreakpoints as H, createBreadcrumbsContext as Ht, useImage as I, ServerAdapter as It, createVirtualContext as J, toReactive as K, useHotkey as L, ClientAdapter as Lt, usePrefersReducedMotion as M, useForm as Mt, useLazy as N, createCombobox as Nt, useMutationObserver as O, createInput as Ot, useElementIntersection as P, createComboboxContext as Pt, useTimeline as Q, createDate as R, useVirtualFocus as Rt, useProxyModel as S, useHydration as St, createNotificationsContext as T, createNested as Tt, createBreakpointsContext as U, useBreadcrumbs as Ut, useDate as V, createBreadcrumbs as Vt, createBreakpointsPlugin as W, createTimeline as X, useVirtual as Y, createTimelineContext as Z, createRtlPlugin as _, toElement as _t, useToggleScope as a, useRating as at, useRovingFocus as b, createHydrationContext as bt, createStoragePlugin as c, useQueue as ct, createStackContext as d, useProgress as dt, createStepContext as et, createStackPlugin as f, createOverflow as ft, createRtlFallback as g, useResizeObserver as gt, createRtlContext as h, useElementSize as ht, useWindowEventListener as i, createRatingContext as it, usePrefersDark as j, createFormContext as jt, useMediaQuery as k, createValidation as kt, useStorage as l, createProgress as lt, createRtl as m, useOverflow as mt, useDocumentEventListener as n, createSlider as nt, createStorage as o, createQueue as ot, useStack as p, createOverflowContext as pt, createVirtual as q, useEventListener as r, createRating as rt, createStorageContext as s, createQueueContext as st, useClickOutside as t, useStep as tt, createStack as u, createProgressContext as ut, useRtl as v, createFallbackHydration as vt, createNotifications as w, createNumeric as wt, useRaf as x, createHydrationPlugin as xt, Vuetify0RtlAdapter as y, createHydration as yt, createDateContext as z, usePopover as zt };
|