import { $ as createTextVNode, C as vShow, Cn as withDirectives, Dt as mergeProps, Ft as onMounted, Kn as ref, M as Fragment, Ot as nextTick, Qn as toRef, U as computed, V as cloneVNode, Vn as onScopeDispose, W as createBaseVNode, Yn as shallowRef, _n as watchEffect, ar as normalizeClass, cn as useId, cr as toDisplayString, er as toValue, et as createVNode, gn as watch, nr as unref, sr as normalizeStyle } from "./vue.runtime.esm-bundler-BvoXUmaf.js"; import { $ as PREFERS_REDUCED_MOTION, B as matchesSelector, H as omit, O as focusableChildren, Q as IN_BROWSER, S as ensureValidVNode, Z as wrapInArray, _ as convertToUnit, a as provideDefaults, d as EventProp, f as callEvent, g as clamp, j as getPropertyFromItem, l as propsFactory, m as checkPrintable, n as genericComponent, p as camelizeProps, s as getCurrentInstance, w as filterInputAttrs, y as debounce } from "./defineComponent-DB6xIcDy.js"; import { t as Box } from "./box-BNWMOtF7.js"; import { a as VSlideYTransition, c as nullifyTransforms, n as VExpandXTransition, o as VDialogTransition, s as animate } from "./transitions-DCQ3sjjZ.js"; import { t as makeComponentProps } from "./component-DdiwBe6i.js"; import { t as deepEqual } from "./deepEqual-DDqmGqyF.js"; import { i as standardEasing } from "./easing-DfcvkbkS.js"; import { t as getScrollParent } from "./getScrollParent-DuXs8SPu.js"; import { t as useRender } from "./useRender-fVtVsZgv.js"; import { a as makeItemsProps, c as VListItem, i as VList, o as useItems, s as VListSubheader } from "./VList-DkWOjB0M.js"; import { r as useTextColor, t as useBackgroundColor } from "./color-B6vuQruj.js"; import { i as provideTheme, r as makeThemeProps } from "./theme-Cx5kFg0-.js"; import { t as VDivider } from "./VDivider-BJiijT0J.js"; import { n as IconValue } from "./icons-k2ZLE_i8.js"; import { n as useToggleScope, t as useProxiedModel } from "./proxiedModel-DSlSIQ0y.js"; import { i as useRtl, r as useLocale } from "./locale-DDGMqzqb.js"; import { a as useDisplay } from "./display-DKaCj-_K.js"; import { t as useResizeObserver } from "./resizeObserver-C12jWpYk.js"; import { t as makeTagProps } from "./tag-C_KkCPzB.js"; import { t as VDefaultsProvider } from "./VDefaultsProvider-C09t4-My.js"; import { n as useDimension, t as makeDimensionProps } from "./dimensions-BDdmuRdK.js"; import { n as Intersect } from "./VImg-DaEUT7gG.js"; import { n as useRounded, t as makeRoundedProps } from "./rounded-BuPGKRa9.js"; import { n as makeTransitionProps, t as MaybeTransition } from "./transition-DqoZ8fA1.js"; import { n as useBorder, t as makeBorderProps } from "./border-jCmRyoxP.js"; import { n as useElevation, t as makeElevationProps } from "./elevation-B0TH2wU6.js"; import { n as useDensity, t as makeDensityProps } from "./density-CpKZ5PhP.js"; import { n as makeVariantProps, r as useVariant, t as genOverlays } from "./variant-CqXtG9Ih.js"; import { i as useGroupItem, n as makeGroupProps, r as useGroup, t as makeGroupItemProps } from "./group-Cm2viEWK.js"; import { n as makeSizeProps, r as useSize, t as VIcon } from "./VIcon-1CJH_3Uo.js"; import { n as makeLoaderProps, r as useLoader, t as LoaderSlot } from "./loader-CV4sMFhE.js"; import { r as useLink, t as makeRouterProps } from "./router-D_jP4Uwb.js"; import { t as Ripple } from "./ripple-Z40rPDte.js"; import { t as VAvatar } from "./VAvatar-CA-KqvIX.js"; import { t as forwardRefs } from "./forwardRefs-CW3d8km7.js"; import { t as VMenu } from "./VMenu-DCQFp-2Y.js"; import { a as useFocus, c as makeVSelectionControlProps, i as makeFocusProps, l as VLabel, n as makeVInputProps, o as useInputIcon, r as useForm, s as VSelectionControl, t as VInput } from "./VInput-BxI8SL-_.js"; import { n as VSlideGroupSymbol, r as makeVSlideGroupProps, t as VSlideGroup } from "./VSlideGroup-TpMGTwfd.js"; import { t as VSheet } from "./VSheet-CLHX3uIJ.js"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VSelect/VSelect.css"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VChip/VChip.css"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VChipGroup/VChipGroup.css"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VTextField/VTextField.css"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VCounter/VCounter.css"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VField/VField.css"; import "/Users/thackmaster/Development/routie2/frontend/node_modules/vuetify/lib/components/VVirtualScroll/VVirtualScroll.css"; //#region node_modules/vuetify/lib/components/VCheckbox/VCheckboxBtn.js var makeVCheckboxBtnProps = propsFactory({ indeterminate: Boolean, indeterminateIcon: { type: IconValue, default: "$checkboxIndeterminate" }, ...makeVSelectionControlProps({ falseIcon: "$checkboxOff", trueIcon: "$checkboxOn" }) }, "VCheckboxBtn"); var VCheckboxBtn = genericComponent()({ name: "VCheckboxBtn", props: makeVCheckboxBtnProps(), emits: { "update:modelValue": (value) => true, "update:indeterminate": (value) => true }, setup(props, { slots }) { const indeterminate = useProxiedModel(props, "indeterminate"); const model = useProxiedModel(props, "modelValue"); function onChange(v) { if (indeterminate.value) indeterminate.value = false; } const falseIcon = toRef(() => { return indeterminate.value ? props.indeterminateIcon : props.falseIcon; }); const trueIcon = toRef(() => { return indeterminate.value ? props.indeterminateIcon : props.trueIcon; }); useRender(() => { return createVNode(VSelectionControl, mergeProps(omit(VSelectionControl.filterProps(props), ["modelValue"]), { "modelValue": model.value, "onUpdate:modelValue": [($event) => model.value = $event, onChange], "class": ["v-checkbox-btn", props.class], "style": props.style, "type": "checkbox", "falseIcon": falseIcon.value, "trueIcon": trueIcon.value, "aria-checked": indeterminate.value ? "mixed" : void 0 }), slots); }); return {}; } }); //#endregion //#region node_modules/vuetify/lib/components/VChipGroup/VChipGroup.js var VChipGroupSymbol = Symbol.for("vuetify:v-chip-group"); var makeVChipGroupProps = propsFactory({ baseColor: String, column: Boolean, filter: Boolean, valueComparator: { type: Function, default: deepEqual }, ...makeVSlideGroupProps({ scrollToActive: false }), ...makeComponentProps(), ...makeGroupProps({ selectedClass: "v-chip--selected" }), ...makeTagProps(), ...makeThemeProps(), ...makeVariantProps({ variant: "tonal" }) }, "VChipGroup"); genericComponent()({ name: "VChipGroup", props: makeVChipGroupProps(), emits: { "update:modelValue": (value) => true }, setup(props, { slots }) { const { themeClasses } = provideTheme(props); const { isSelected, select, next, prev, selected } = useGroup(props, VChipGroupSymbol); provideDefaults({ VChip: { baseColor: toRef(() => props.baseColor), color: toRef(() => props.color), disabled: toRef(() => props.disabled), filter: toRef(() => props.filter), variant: toRef(() => props.variant) } }); useRender(() => { return createVNode(VSlideGroup, mergeProps(VSlideGroup.filterProps(props), { "class": [ "v-chip-group", { "v-chip-group--column": props.column }, themeClasses.value, props.class ], "style": props.style }), { default: () => [slots.default?.({ isSelected, select, next, prev, selected: selected.value })] }); }); return {}; } }); //#endregion //#region node_modules/vuetify/lib/components/VChip/VChip.js var makeVChipProps = propsFactory({ activeClass: String, appendAvatar: String, appendIcon: IconValue, baseColor: String, closable: Boolean, closeIcon: { type: IconValue, default: "$delete" }, closeLabel: { type: String, default: "$vuetify.close" }, draggable: Boolean, filter: Boolean, filterIcon: { type: IconValue, default: "$complete" }, label: Boolean, link: { type: Boolean, default: void 0 }, pill: Boolean, prependAvatar: String, prependIcon: IconValue, ripple: { type: [Boolean, Object], default: true }, text: { type: [ String, Number, Boolean ], default: void 0 }, modelValue: { type: Boolean, default: true }, onClick: EventProp(), onClickOnce: EventProp(), ...makeBorderProps(), ...makeComponentProps(), ...makeDensityProps(), ...makeElevationProps(), ...makeGroupItemProps(), ...makeRoundedProps(), ...makeRouterProps(), ...makeSizeProps(), ...makeTagProps({ tag: "span" }), ...makeThemeProps(), ...makeVariantProps({ variant: "tonal" }) }, "VChip"); var VChip = genericComponent()({ name: "VChip", directives: { vRipple: Ripple }, props: makeVChipProps(), emits: { "click:close": (e) => true, "update:modelValue": (value) => true, "group:selected": (val) => true, click: (e) => true }, setup(props, { attrs, emit, slots }) { const { t } = useLocale(); const { borderClasses } = useBorder(props); const { densityClasses } = useDensity(props); const { elevationClasses } = useElevation(props); const { roundedClasses } = useRounded(props); const { sizeClasses } = useSize(props); const { themeClasses } = provideTheme(props); const isActive = useProxiedModel(props, "modelValue"); const group = useGroupItem(props, VChipGroupSymbol, false); const slideGroup = useGroupItem(props, VSlideGroupSymbol, false); const link = useLink(props, attrs); const isLink = toRef(() => props.link !== false && link.isLink.value); const isClickable = computed(() => !props.disabled && props.link !== false && (!!group || props.link || link.isClickable.value)); const closeProps = toRef(() => ({ "aria-label": t(props.closeLabel), disabled: props.disabled, onClick(e) { e.preventDefault(); e.stopPropagation(); isActive.value = false; emit("click:close", e); } })); watch(isActive, (val) => { if (val) { group?.register(); slideGroup?.register(); } else { group?.unregister(); slideGroup?.unregister(); } }); const { colorClasses, colorStyles, variantClasses } = useVariant(() => { return { color: !group || group.isSelected.value ? props.color ?? props.baseColor : props.baseColor, variant: props.variant }; }); function onClick(e) { emit("click", e); if (!isClickable.value) return; link.navigate.value?.(e); group?.toggle(); } function onKeyDown(e) { if (e.key === "Enter" || e.key === " ") { e.preventDefault(); onClick(e); } } return () => { const Tag = link.isLink.value ? "a" : props.tag; const hasAppendMedia = !!(props.appendIcon || props.appendAvatar); const hasAppend = !!(hasAppendMedia || slots.append); const hasClose = !!(slots.close || props.closable); const hasFilter = !!(slots.filter || props.filter) && group; const hasPrependMedia = !!(props.prependIcon || props.prependAvatar); const hasPrepend = !!(hasPrependMedia || slots.prepend); return isActive.value && withDirectives(createVNode(Tag, mergeProps(link.linkProps, { "class": [ "v-chip", { "v-chip--disabled": props.disabled, "v-chip--label": props.label, "v-chip--link": isClickable.value, "v-chip--filter": hasFilter, "v-chip--pill": props.pill, [`${props.activeClass}`]: props.activeClass && link.isActive?.value }, themeClasses.value, borderClasses.value, colorClasses.value, densityClasses.value, elevationClasses.value, roundedClasses.value, sizeClasses.value, variantClasses.value, group?.selectedClass.value, props.class ], "style": [colorStyles.value, props.style], "disabled": props.disabled || void 0, "draggable": props.draggable, "tabindex": isClickable.value ? 0 : void 0, "onClick": onClick, "onKeydown": isClickable.value && !isLink.value && onKeyDown }), { default: () => [ genOverlays(isClickable.value, "v-chip"), hasFilter && createVNode(VExpandXTransition, { "key": "filter" }, { default: () => [withDirectives(createBaseVNode("div", { "class": "v-chip__filter" }, [!slots.filter ? createVNode(VIcon, { "key": "filter-icon", "icon": props.filterIcon }, null) : createVNode(VDefaultsProvider, { "key": "filter-defaults", "disabled": !props.filterIcon, "defaults": { VIcon: { icon: props.filterIcon } } }, slots.filter)]), [[vShow, group.isSelected.value]])] }), hasPrepend && createBaseVNode("div", { "key": "prepend", "class": "v-chip__prepend" }, [!slots.prepend ? createBaseVNode(Fragment, null, [props.prependIcon && createVNode(VIcon, { "key": "prepend-icon", "icon": props.prependIcon, "start": true }, null), props.prependAvatar && createVNode(VAvatar, { "key": "prepend-avatar", "image": props.prependAvatar, "start": true }, null)]) : createVNode(VDefaultsProvider, { "key": "prepend-defaults", "disabled": !hasPrependMedia, "defaults": { VAvatar: { image: props.prependAvatar, start: true }, VIcon: { icon: props.prependIcon, start: true } } }, slots.prepend)]), createBaseVNode("div", { "class": "v-chip__content", "data-no-activator": "" }, [slots.default?.({ isSelected: group?.isSelected.value, selectedClass: group?.selectedClass.value, select: group?.select, toggle: group?.toggle, value: group?.value.value, disabled: props.disabled }) ?? toDisplayString(props.text)]), hasAppend && createBaseVNode("div", { "key": "append", "class": "v-chip__append" }, [!slots.append ? createBaseVNode(Fragment, null, [props.appendIcon && createVNode(VIcon, { "key": "append-icon", "end": true, "icon": props.appendIcon }, null), props.appendAvatar && createVNode(VAvatar, { "key": "append-avatar", "end": true, "image": props.appendAvatar }, null)]) : createVNode(VDefaultsProvider, { "key": "append-defaults", "disabled": !hasAppendMedia, "defaults": { VAvatar: { end: true, image: props.appendAvatar }, VIcon: { end: true, icon: props.appendIcon } } }, slots.append)]), hasClose && createBaseVNode("button", mergeProps({ "key": "close", "class": "v-chip__close", "type": "button", "data-testid": "close-chip" }, closeProps.value), [!slots.close ? createVNode(VIcon, { "key": "close-icon", "icon": props.closeIcon, "size": "x-small" }, null) : createVNode(VDefaultsProvider, { "key": "close-defaults", "defaults": { VIcon: { icon: props.closeIcon, size: "x-small" } } }, slots.close)]) ] }), [[ Ripple, isClickable.value && props.ripple, null ]]); }; } }); //#endregion //#region node_modules/vuetify/lib/components/VCounter/VCounter.js var makeVCounterProps = propsFactory({ active: Boolean, disabled: Boolean, max: [Number, String], value: { type: [Number, String], default: 0 }, ...makeComponentProps(), ...makeTransitionProps({ transition: { component: VSlideYTransition } }) }, "VCounter"); var VCounter = genericComponent()({ name: "VCounter", functional: true, props: makeVCounterProps(), setup(props, { slots }) { const counter = toRef(() => { return props.max ? `${props.value} / ${props.max}` : String(props.value); }); useRender(() => createVNode(MaybeTransition, { "transition": props.transition }, { default: () => [withDirectives(createBaseVNode("div", { "class": normalizeClass([ "v-counter", { "text-error": props.max && !props.disabled && parseFloat(props.value) > parseFloat(props.max) }, props.class ]), "style": normalizeStyle(props.style) }, [slots.default ? slots.default({ counter: counter.value, max: props.max, value: props.value }) : counter.value]), [[vShow, props.active]])] })); return {}; } }); //#endregion //#region node_modules/vuetify/lib/components/VField/VFieldLabel.js var makeVFieldLabelProps = propsFactory({ floating: Boolean, ...makeComponentProps() }, "VFieldLabel"); var VFieldLabel = genericComponent()({ name: "VFieldLabel", props: makeVFieldLabelProps(), setup(props, { slots }) { useRender(() => createVNode(VLabel, { "class": normalizeClass([ "v-field-label", { "v-field-label--floating": props.floating }, props.class ]), "style": normalizeStyle(props.style) }, slots)); return {}; } }); //#endregion //#region node_modules/vuetify/lib/components/VField/VField.js var allowedVariants = [ "underlined", "outlined", "filled", "solo", "solo-inverted", "solo-filled", "plain" ]; var makeVFieldProps = propsFactory({ appendInnerIcon: IconValue, bgColor: String, clearable: Boolean, clearIcon: { type: IconValue, default: "$clear" }, active: Boolean, centerAffix: { type: Boolean, default: void 0 }, color: String, baseColor: String, dirty: Boolean, disabled: { type: Boolean, default: null }, glow: Boolean, error: Boolean, flat: Boolean, iconColor: [Boolean, String], label: String, persistentClear: Boolean, prependInnerIcon: IconValue, reverse: Boolean, singleLine: Boolean, variant: { type: String, default: "filled", validator: (v) => allowedVariants.includes(v) }, "onClick:clear": EventProp(), "onClick:appendInner": EventProp(), "onClick:prependInner": EventProp(), ...makeComponentProps(), ...makeLoaderProps(), ...makeRoundedProps(), ...makeThemeProps() }, "VField"); var VField = genericComponent()({ name: "VField", inheritAttrs: false, props: { id: String, details: Boolean, labelId: String, ...makeFocusProps(), ...makeVFieldProps() }, emits: { "update:focused": (focused) => true, "update:modelValue": (value) => true }, setup(props, { attrs, emit, slots }) { const { themeClasses } = provideTheme(props); const { loaderClasses } = useLoader(props); const { focusClasses, isFocused, focus, blur } = useFocus(props); const { InputIcon } = useInputIcon(props); const { roundedClasses } = useRounded(props); const { rtlClasses } = useRtl(); const isActive = toRef(() => props.dirty || props.active); const hasLabel = toRef(() => !!(props.label || slots.label)); const hasFloatingLabel = toRef(() => !props.singleLine && hasLabel.value); const uid = useId(); const id = computed(() => props.id || `input-${uid}`); const messagesId = toRef(() => !props.details ? void 0 : `${id.value}-messages`); const labelRef = ref(); const floatingLabelRef = ref(); const controlRef = ref(); const isPlainOrUnderlined = computed(() => ["plain", "underlined"].includes(props.variant)); const color = computed(() => { return props.error || props.disabled ? void 0 : isActive.value && isFocused.value ? props.color : props.baseColor; }); const iconColor = computed(() => { if (props.iconColor === true || !props.iconColor && props.glow && isFocused.value) return color.value; if (!props.iconColor || props.glow && !isFocused.value) return void 0; return props.iconColor; }); const { backgroundColorClasses, backgroundColorStyles } = useBackgroundColor(() => props.bgColor); const { textColorClasses, textColorStyles } = useTextColor(color); watch(isActive, (val) => { if (hasFloatingLabel.value && !PREFERS_REDUCED_MOTION()) { const el = labelRef.value.$el; const targetEl = floatingLabelRef.value.$el; requestAnimationFrame(() => { const rect = nullifyTransforms(el); const targetRect = new Box(targetEl); const x = targetRect.x - rect.x; const y = targetRect.y - rect.y - (rect.height / 2 - targetRect.height / 2); const targetWidth = targetRect.width / .75; const width = Math.abs(targetWidth - rect.width) > 1 ? { maxWidth: convertToUnit(targetWidth) } : void 0; const style = getComputedStyle(el); const targetStyle = getComputedStyle(targetEl); const duration = parseFloat(style.transitionDuration) * 1e3 || 150; const scale = parseFloat(targetStyle.getPropertyValue("--v-field-label-scale")); const color = targetStyle.getPropertyValue("color"); el.style.visibility = "visible"; targetEl.style.visibility = "hidden"; animate(el, { transform: `translate(${x}px, ${y}px) scale(${scale})`, color, ...width }, { duration, easing: standardEasing, direction: val ? "normal" : "reverse" }).finished.then(() => { el.style.removeProperty("visibility"); targetEl.style.removeProperty("visibility"); }); }); } }, { flush: "post" }); const slotProps = computed(() => ({ isActive, isFocused, controlRef, iconColor, blur, focus })); const floatingLabelProps = toRef(() => { const ariaHidden = !isActive.value; return { "aria-hidden": ariaHidden, for: ariaHidden ? void 0 : id.value }; }); const mainLabelProps = toRef(() => { const ariaHidden = hasFloatingLabel.value && isActive.value; return { "aria-hidden": ariaHidden, for: ariaHidden ? void 0 : id.value }; }); function onClick(e) { if (e.target !== document.activeElement) e.preventDefault(); } useRender(() => { const isOutlined = props.variant === "outlined"; const hasPrepend = !!(slots["prepend-inner"] || props.prependInnerIcon); const hasClear = !!(props.clearable || slots.clear) && !props.disabled; const hasAppend = !!(slots["append-inner"] || props.appendInnerIcon || hasClear); const label = () => slots.label ? slots.label({ ...slotProps.value, label: props.label, props: { for: id.value } }) : props.label; return createBaseVNode("div", mergeProps({ "class": [ "v-field", { "v-field--active": isActive.value, "v-field--appended": hasAppend, "v-field--center-affix": props.centerAffix ?? !isPlainOrUnderlined.value, "v-field--disabled": props.disabled, "v-field--dirty": props.dirty, "v-field--error": props.error, "v-field--glow": props.glow, "v-field--flat": props.flat, "v-field--has-background": !!props.bgColor, "v-field--persistent-clear": props.persistentClear, "v-field--prepended": hasPrepend, "v-field--reverse": props.reverse, "v-field--single-line": props.singleLine, "v-field--no-label": !label(), [`v-field--variant-${props.variant}`]: true }, themeClasses.value, backgroundColorClasses.value, focusClasses.value, loaderClasses.value, roundedClasses.value, rtlClasses.value, props.class ], "style": [backgroundColorStyles.value, props.style], "onClick": onClick }, attrs), [ createBaseVNode("div", { "class": "v-field__overlay" }, null), createVNode(LoaderSlot, { "name": "v-field", "active": !!props.loading, "color": props.error ? "error" : typeof props.loading === "string" ? props.loading : props.color }, { default: slots.loader }), hasPrepend && createBaseVNode("div", { "key": "prepend", "class": "v-field__prepend-inner" }, [slots["prepend-inner"] ? slots["prepend-inner"](slotProps.value) : props.prependInnerIcon && createVNode(InputIcon, { "key": "prepend-icon", "name": "prependInner", "color": iconColor.value }, null)]), createBaseVNode("div", { "class": "v-field__field", "data-no-activator": "" }, [ [ "filled", "solo", "solo-inverted", "solo-filled" ].includes(props.variant) && hasFloatingLabel.value && createVNode(VFieldLabel, mergeProps({ "key": "floating-label", "ref": floatingLabelRef, "class": [textColorClasses.value], "floating": true }, floatingLabelProps.value, { "style": textColorStyles.value }), { default: () => [label()] }), hasLabel.value && createVNode(VFieldLabel, mergeProps({ "key": "label", "ref": labelRef, "id": props.labelId }, mainLabelProps.value), { default: () => [label()] }), slots.default?.({ ...slotProps.value, props: { id: id.value, class: "v-field__input", "aria-describedby": messagesId.value }, focus, blur }) ?? createBaseVNode("div", { "id": id.value, "class": "v-field__input", "aria-describedby": messagesId.value }, null) ]), hasClear && createVNode(VExpandXTransition, { "key": "clear" }, { default: () => [withDirectives(createBaseVNode("div", { "class": "v-field__clearable", "onMousedown": (e) => { e.preventDefault(); e.stopPropagation(); } }, [createVNode(VDefaultsProvider, { "defaults": { VIcon: { icon: props.clearIcon } } }, { default: () => [slots.clear ? slots.clear({ ...slotProps.value, props: { onFocus: focus, onBlur: blur, onClick: props["onClick:clear"], tabindex: -1 } }) : createVNode(InputIcon, { "name": "clear", "onFocus": focus, "onBlur": blur, "tabindex": -1 }, null)] })]), [[vShow, props.dirty]])] }), hasAppend && createBaseVNode("div", { "key": "append", "class": "v-field__append-inner" }, [slots["append-inner"] ? slots["append-inner"](slotProps.value) : props.appendInnerIcon && createVNode(InputIcon, { "key": "append-icon", "name": "appendInner", "color": iconColor.value }, null)]), createBaseVNode("div", { "class": normalizeClass(["v-field__outline", textColorClasses.value]), "style": normalizeStyle(textColorStyles.value) }, [isOutlined && createBaseVNode(Fragment, null, [ createBaseVNode("div", { "class": "v-field__outline__start" }, null), hasFloatingLabel.value && createBaseVNode("div", { "class": "v-field__outline__notch" }, [createVNode(VFieldLabel, mergeProps({ "ref": floatingLabelRef, "floating": true }, floatingLabelProps.value), { default: () => [label()] })]), createBaseVNode("div", { "class": "v-field__outline__end" }, null) ]), isPlainOrUnderlined.value && hasFloatingLabel.value && createVNode(VFieldLabel, mergeProps({ "ref": floatingLabelRef, "floating": true }, floatingLabelProps.value), { default: () => [label()] })]) ]); }); return { controlRef, fieldIconColor: iconColor }; } }); //#endregion //#region node_modules/vuetify/lib/composables/autocomplete.js var makeAutocompleteProps = propsFactory({ autocomplete: String }, "autocomplete"); function useAutocomplete(props) { const uniqueId = useId(); const reloadTrigger = shallowRef(0); const isSuppressing = toRef(() => props.autocomplete === "suppress"); const fieldName = toRef(() => { if (!props.name) return void 0; return isSuppressing.value ? `${props.name}-${uniqueId}-${reloadTrigger.value}` : props.name; }); return { isSuppressing, fieldAutocomplete: toRef(() => { return isSuppressing.value ? "off" : props.autocomplete; }), fieldName, update: () => reloadTrigger.value = (/* @__PURE__ */ new Date()).getTime() }; } //#endregion //#region node_modules/vuetify/lib/composables/autofocus.js function useAutofocus(props) { function onIntersect(isIntersecting, entries) { if (!props.autofocus || !isIntersecting) return; const el = entries[0].target; (el.matches("input,textarea") ? el : el.querySelector("input,textarea"))?.focus(); } return { onIntersect }; } //#endregion //#region node_modules/vuetify/lib/components/VTextField/VTextField.js var activeTypes = [ "color", "file", "time", "date", "datetime-local", "week", "month" ]; var makeVTextFieldProps = propsFactory({ autofocus: Boolean, counter: [ Boolean, Number, String ], counterValue: [Number, Function], prefix: String, placeholder: String, persistentPlaceholder: Boolean, persistentCounter: Boolean, suffix: String, role: String, type: { type: String, default: "text" }, modelModifiers: Object, ...makeAutocompleteProps(), ...omit(makeVInputProps(), ["direction"]), ...makeVFieldProps() }, "VTextField"); var VTextField = genericComponent()({ name: "VTextField", directives: { vIntersect: Intersect }, inheritAttrs: false, props: makeVTextFieldProps(), emits: { "click:control": (e) => true, "mousedown:control": (e) => true, "update:focused": (focused) => true, "update:modelValue": (val) => true }, setup(props, { attrs, emit, slots }) { const model = useProxiedModel(props, "modelValue", void 0, (v) => { if (Object.is(v, -0)) return "-0"; return v; }); const { isFocused, focus, blur } = useFocus(props); const { onIntersect } = useAutofocus(props); const counterValue = computed(() => { return typeof props.counterValue === "function" ? props.counterValue(model.value) : typeof props.counterValue === "number" ? props.counterValue : (model.value ?? "").toString().length; }); const max = computed(() => { if (attrs.maxlength) return attrs.maxlength; if (!props.counter || typeof props.counter !== "number" && typeof props.counter !== "string") return void 0; return props.counter; }); const isPlainOrUnderlined = computed(() => ["plain", "underlined"].includes(props.variant)); const vInputRef = ref(); const vFieldRef = ref(); const inputRef = ref(); const autocomplete = useAutocomplete(props); const isActive = computed(() => activeTypes.includes(props.type) || props.persistentPlaceholder || isFocused.value || props.active); function onFocus() { if (autocomplete.isSuppressing.value) autocomplete.update(); if (!isFocused.value) focus(); nextTick(() => { if (inputRef.value !== document.activeElement) inputRef.value?.focus(); }); } function onControlMousedown(e) { emit("mousedown:control", e); if (e.target === inputRef.value) return; onFocus(); e.preventDefault(); } function onControlClick(e) { emit("click:control", e); } function onClear(e, reset) { e.stopPropagation(); onFocus(); nextTick(() => { reset(); callEvent(props["onClick:clear"], e); }); } function onInput(e) { const el = e.target; if (!(props.modelModifiers?.trim && [ "text", "search", "password", "tel", "url" ].includes(props.type))) { model.value = el.value; return; } const value = el.value; const start = el.selectionStart; const end = el.selectionEnd; model.value = value; nextTick(() => { let offset = 0; if (value.trimStart().length === el.value.length) offset = value.length - el.value.length; if (start != null) el.selectionStart = start - offset; if (end != null) el.selectionEnd = end - offset; }); } useRender(() => { const hasCounter = !!(slots.counter || props.counter !== false && props.counter != null); const hasDetails = !!(hasCounter || slots.details); const [rootAttrs, inputAttrs] = filterInputAttrs(attrs); const { modelValue: _, ...inputProps } = VInput.filterProps(props); const fieldProps = VField.filterProps(props); return createVNode(VInput, mergeProps({ "ref": vInputRef, "modelValue": model.value, "onUpdate:modelValue": ($event) => model.value = $event, "class": [ "v-text-field", { "v-text-field--prefixed": props.prefix, "v-text-field--suffixed": props.suffix, "v-input--plain-underlined": isPlainOrUnderlined.value }, props.class ], "style": props.style }, rootAttrs, inputProps, { "centerAffix": !isPlainOrUnderlined.value, "focused": isFocused.value, "indentDetails": props.indentDetails ?? !isPlainOrUnderlined.value }), { ...slots, default: ({ id, isDisabled, isDirty, isReadonly, isValid, hasDetails, reset }) => createVNode(VField, mergeProps({ "ref": vFieldRef, "onMousedown": onControlMousedown, "onClick": onControlClick, "onClick:clear": (e) => onClear(e, reset), "role": props.role }, omit(fieldProps, ["onClick:clear"]), { "id": id.value, "labelId": `${id.value}-label`, "active": isActive.value || isDirty.value, "dirty": isDirty.value || props.dirty, "disabled": isDisabled.value, "focused": isFocused.value, "details": hasDetails.value, "error": isValid.value === false }), { ...slots, default: ({ props: { class: fieldClass, ...slotProps }, controlRef }) => { const inputNode = createBaseVNode("input", mergeProps({ "ref": (val) => inputRef.value = controlRef.value = val, "value": model.value, "onInput": onInput, "autofocus": props.autofocus, "readonly": isReadonly.value, "disabled": isDisabled.value, "name": autocomplete.fieldName.value, "autocomplete": autocomplete.fieldAutocomplete.value, "placeholder": props.placeholder, "size": 1, "role": props.role, "type": props.type, "onFocus": focus, "onBlur": blur, "aria-labelledby": `${id.value}-label` }, slotProps, inputAttrs), null); return createBaseVNode(Fragment, null, [ props.prefix && createBaseVNode("span", { "class": "v-text-field__prefix" }, [createBaseVNode("span", { "class": "v-text-field__prefix__text" }, [props.prefix])]), withDirectives(slots.default ? createBaseVNode("div", { "class": normalizeClass(fieldClass), "data-no-activator": "" }, [slots.default({ id }), inputNode]) : cloneVNode(inputNode, { class: fieldClass }), [[ Intersect, onIntersect, null, { once: true } ]]), props.suffix && createBaseVNode("span", { "class": "v-text-field__suffix" }, [createBaseVNode("span", { "class": "v-text-field__suffix__text" }, [props.suffix])]) ]); } }), details: hasDetails ? (slotProps) => createBaseVNode(Fragment, null, [slots.details?.(slotProps), hasCounter && createBaseVNode(Fragment, null, [createBaseVNode("span", null, null), createVNode(VCounter, { "active": props.persistentCounter || isFocused.value, "value": counterValue.value, "max": max.value, "disabled": props.disabled }, slots.counter)])]) : void 0 }); }); return forwardRefs({}, vInputRef, vFieldRef, inputRef); } }); //#endregion //#region node_modules/vuetify/lib/components/VVirtualScroll/VVirtualScrollItem.js var makeVVirtualScrollItemProps = propsFactory({ renderless: Boolean, ...makeComponentProps() }, "VVirtualScrollItem"); var VVirtualScrollItem = genericComponent()({ name: "VVirtualScrollItem", inheritAttrs: false, props: makeVVirtualScrollItemProps(), emits: { "update:height": (height) => true }, setup(props, { attrs, emit, slots }) { const { resizeRef, contentRect } = useResizeObserver(void 0, "border"); watch(() => contentRect.value?.height, (height) => { if (height != null) emit("update:height", height); }); useRender(() => props.renderless ? createBaseVNode(Fragment, null, [slots.default?.({ itemRef: resizeRef })]) : createBaseVNode("div", mergeProps({ "ref": resizeRef, "class": ["v-virtual-scroll__item", props.class], "style": props.style }, attrs), [slots.default?.()])); } }); //#endregion //#region node_modules/vuetify/lib/composables/virtual.js var UP = -1; var DOWN = 1; /** Determines how large each batch of items should be */ var BUFFER_PX = 100; var makeVirtualProps = propsFactory({ itemHeight: { type: [Number, String], default: null }, itemKey: { type: [ String, Array, Function ], default: null }, height: [Number, String] }, "virtual"); function useVirtual(props, items) { const display = useDisplay(); const itemHeight = shallowRef(0); watchEffect(() => { itemHeight.value = parseFloat(props.itemHeight || 0); }); const first = shallowRef(0); const last = shallowRef(Math.ceil((parseInt(props.height) || display.height.value) / (itemHeight.value || 16)) || 1); const paddingTop = shallowRef(0); const paddingBottom = shallowRef(0); /** The scrollable element */ const containerRef = ref(); /** An element marking the top of the scrollable area, * used to add an offset if there's padding or other elements above the virtual list */ const markerRef = ref(); /** markerRef's offsetTop, lazily evaluated */ let markerOffset = 0; const { resizeRef, contentRect } = useResizeObserver(); watchEffect(() => { resizeRef.value = containerRef.value; }); const viewportHeight = computed(() => { return containerRef.value === document.documentElement ? display.height.value : contentRect.value?.height || parseInt(props.height) || 0; }); /** All static elements have been rendered and we have an assumed item height */ const hasInitialRender = computed(() => { return !!(containerRef.value && markerRef.value && viewportHeight.value && itemHeight.value); }); let sizes = Array.from({ length: items.value.length }); let offsets = Array.from({ length: items.value.length }); const updateTime = shallowRef(0); let targetScrollIndex = -1; function getSize(index) { return sizes[index] || itemHeight.value; } const updateOffsets = debounce(() => { const start = performance.now(); offsets[0] = 0; const length = items.value.length; for (let i = 1; i <= length; i++) offsets[i] = (offsets[i - 1] || 0) + getSize(i - 1); updateTime.value = Math.max(updateTime.value, performance.now() - start); }, updateTime); const unwatch = watch(hasInitialRender, (v) => { if (!v) return; unwatch(); markerOffset = markerRef.value.offsetTop; updateOffsets.immediate(); calculateVisibleItems(); if (!~targetScrollIndex) return; nextTick(() => { IN_BROWSER && window.requestAnimationFrame(() => { scrollToIndex(targetScrollIndex); targetScrollIndex = -1; }); }); }); onScopeDispose(() => { updateOffsets.clear(); }); function handleItemResize(index, height) { const prevHeight = sizes[index]; const prevMinHeight = itemHeight.value; itemHeight.value = prevMinHeight ? Math.min(itemHeight.value, height) : height; if (prevHeight !== height || prevMinHeight !== itemHeight.value) { sizes[index] = height; updateOffsets(); } } function calculateOffset(index) { index = clamp(index, 0, items.value.length); const whole = Math.floor(index); const fraction = index % 1; const next = whole + 1; const wholeOffset = offsets[whole] || 0; return wholeOffset + ((offsets[next] || wholeOffset) - wholeOffset) * fraction; } function calculateIndex(scrollTop) { return binaryClosest(offsets, scrollTop); } let lastScrollTop = 0; let scrollVelocity = 0; let lastScrollTime = 0; watch(viewportHeight, (val, oldVal) => { calculateVisibleItems(); if (val < oldVal) requestAnimationFrame(() => { scrollVelocity = 0; calculateVisibleItems(); }); }); let scrollTimeout = -1; function handleScroll() { if (!containerRef.value || !markerRef.value) return; const scrollTop = containerRef.value.scrollTop; const scrollTime = performance.now(); if (scrollTime - lastScrollTime > 500) { scrollVelocity = Math.sign(scrollTop - lastScrollTop); markerOffset = markerRef.value.offsetTop; } else scrollVelocity = scrollTop - lastScrollTop; lastScrollTop = scrollTop; lastScrollTime = scrollTime; window.clearTimeout(scrollTimeout); scrollTimeout = window.setTimeout(handleScrollend, 500); calculateVisibleItems(); } function handleScrollend() { if (!containerRef.value || !markerRef.value) return; scrollVelocity = 0; lastScrollTime = 0; window.clearTimeout(scrollTimeout); calculateVisibleItems(); } let raf = -1; function calculateVisibleItems() { cancelAnimationFrame(raf); raf = requestAnimationFrame(_calculateVisibleItems); } function _calculateVisibleItems() { if (!containerRef.value || !viewportHeight.value || !itemHeight.value) return; const scrollTop = lastScrollTop - markerOffset; const direction = Math.sign(scrollVelocity); const start = clamp(calculateIndex(Math.max(0, scrollTop - BUFFER_PX)), 0, items.value.length); const end = clamp(calculateIndex(scrollTop + viewportHeight.value + BUFFER_PX) + 1, start + 1, items.value.length); if ((direction !== UP || start < first.value) && (direction !== DOWN || end > last.value)) { const topOverflow = calculateOffset(first.value) - calculateOffset(start); const bottomOverflow = calculateOffset(end) - calculateOffset(last.value); if (Math.max(topOverflow, bottomOverflow) > BUFFER_PX) { first.value = start; last.value = end; } else { if (start <= 0) first.value = start; if (end >= items.value.length) last.value = end; } } paddingTop.value = calculateOffset(first.value); paddingBottom.value = calculateOffset(items.value.length) - calculateOffset(last.value); } function scrollToIndex(index) { const offset = calculateOffset(index); if (!containerRef.value || index && !offset) targetScrollIndex = index; else containerRef.value.scrollTop = offset; } const computedItems = computed(() => { return items.value.slice(first.value, last.value).map((item, index) => { const _index = index + first.value; return { raw: item, index: _index, key: getPropertyFromItem(item, props.itemKey, _index) }; }); }); watch(items, () => { sizes = Array.from({ length: items.value.length }); offsets = Array.from({ length: items.value.length }); updateOffsets.immediate(); calculateVisibleItems(); }, { deep: 1 }); return { calculateVisibleItems, containerRef, markerRef, computedItems, paddingTop, paddingBottom, scrollToIndex, handleScroll, handleScrollend, handleItemResize }; } function binaryClosest(arr, val) { let high = arr.length - 1; let low = 0; let mid = 0; let item = null; let target = -1; if (arr[high] < val) return high; while (low <= high) { mid = low + high >> 1; item = arr[mid]; if (item > val) high = mid - 1; else if (item < val) { target = mid; low = mid + 1; } else if (item === val) return mid; else return low; } return target; } //#endregion //#region node_modules/vuetify/lib/components/VVirtualScroll/VVirtualScroll.js var makeVVirtualScrollProps = propsFactory({ items: { type: Array, default: () => [] }, renderless: Boolean, ...makeVirtualProps(), ...makeComponentProps(), ...makeDimensionProps() }, "VVirtualScroll"); var VVirtualScroll = genericComponent()({ name: "VVirtualScroll", props: makeVVirtualScrollProps(), setup(props, { slots }) { const vm = getCurrentInstance("VVirtualScroll"); const { dimensionStyles } = useDimension(props); const { calculateVisibleItems, containerRef, markerRef, handleScroll, handleScrollend, handleItemResize, scrollToIndex, paddingTop, paddingBottom, computedItems } = useVirtual(props, toRef(() => props.items)); useToggleScope(() => props.renderless, () => { function handleListeners(add = false) { const method = add ? "addEventListener" : "removeEventListener"; if (!IN_BROWSER) return; if (containerRef.value === document.documentElement) { document[method]("scroll", handleScroll, { passive: true }); document[method]("scrollend", handleScrollend); } else { containerRef.value?.[method]("scroll", handleScroll, { passive: true }); containerRef.value?.[method]("scrollend", handleScrollend); } } onMounted(() => { containerRef.value = getScrollParent(vm.vnode.el, true); handleListeners(true); }); onScopeDispose(handleListeners); }); useRender(() => { const children = computedItems.value.map((item) => createVNode(VVirtualScrollItem, { "key": item.key, "renderless": props.renderless, "onUpdate:height": (height) => handleItemResize(item.index, height) }, { default: (slotProps) => slots.default?.({ item: item.raw, index: item.index, ...slotProps }) })); return props.renderless ? createBaseVNode(Fragment, null, [ createBaseVNode("div", { "ref": markerRef, "class": "v-virtual-scroll__spacer", "style": { paddingTop: convertToUnit(paddingTop.value) } }, null), children, createBaseVNode("div", { "class": "v-virtual-scroll__spacer", "style": { paddingBottom: convertToUnit(paddingBottom.value) } }, null) ]) : createBaseVNode("div", { "ref": containerRef, "class": normalizeClass(["v-virtual-scroll", props.class]), "onScrollPassive": handleScroll, "onScrollend": handleScrollend, "style": normalizeStyle([dimensionStyles.value, props.style]) }, [createBaseVNode("div", { "ref": markerRef, "class": "v-virtual-scroll__container", "style": { paddingTop: convertToUnit(paddingTop.value), paddingBottom: convertToUnit(paddingBottom.value) } }, [children])]); }); return { calculateVisibleItems, scrollToIndex }; } }); //#endregion //#region node_modules/vuetify/lib/components/VSelect/useScrolling.js function useScrolling(listRef, textFieldRef) { const isScrolling = shallowRef(false); let scrollTimeout; function onListScroll(e) { cancelAnimationFrame(scrollTimeout); isScrolling.value = true; scrollTimeout = requestAnimationFrame(() => { scrollTimeout = requestAnimationFrame(() => { isScrolling.value = false; }); }); } async function finishScrolling() { await new Promise((resolve) => requestAnimationFrame(resolve)); await new Promise((resolve) => requestAnimationFrame(resolve)); await new Promise((resolve) => requestAnimationFrame(resolve)); await new Promise((resolve) => { if (isScrolling.value) { const stop = watch(isScrolling, () => { stop(); resolve(); }); } else resolve(); }); } async function onListKeydown(e) { if (e.key === "Tab") textFieldRef.value?.focus(); if (![ "PageDown", "PageUp", "Home", "End" ].includes(e.key)) return; const el = listRef.value?.$el; if (!el) return; if (e.key === "Home" || e.key === "End") el.scrollTo({ top: e.key === "Home" ? 0 : el.scrollHeight, behavior: "smooth" }); await finishScrolling(); const children = el.querySelectorAll(":scope > :not(.v-virtual-scroll__spacer)"); if (e.key === "PageDown" || e.key === "Home") { const top = el.getBoundingClientRect().top; for (const child of children) if (child.getBoundingClientRect().top >= top) { child.focus(); break; } } else { const bottom = el.getBoundingClientRect().bottom; for (const child of [...children].reverse()) if (child.getBoundingClientRect().bottom <= bottom) { child.focus(); break; } } } return { onScrollPassive: onListScroll, onKeydown: onListKeydown }; } //#endregion //#region node_modules/vuetify/lib/composables/focusGroups.js function useFocusGroups({ groups, onLeave }) { function getContentRef(group) { return group.type === "list" ? group.contentRef.value?.$el : group.contentRef.value; } function getChildren(group) { const contentRef = getContentRef(group); return contentRef ? focusableChildren(contentRef) : []; } function onTabKeydown(e) { const target = e.target; const direction = e.shiftKey ? "backward" : "forward"; const children = groups.map(getChildren); const currentGroupIndex = groups.map((g) => g.type === "list" ? g.contentRef.value?.$el : g.contentRef.value).findIndex((el) => el?.contains(target)); const nextIndex = nextFocusGroup(children, currentGroupIndex, direction, target); if (nextIndex === null) { const originGroup = groups[currentGroupIndex]; const origin = children[currentGroupIndex]; if (originGroup.type === "list" || (direction === "forward" ? origin.at(-1) === e.target : origin.at(0) === e.target)) onLeave(); } else { e.preventDefault(); e.stopImmediatePropagation(); const nextGroup = groups[nextIndex]; if (nextGroup.type === "list" && toValue(nextGroup.displayItemsCount) > 0) nextGroup.contentRef.value?.focus(0); else { const fromBefore = direction === "forward"; children[nextIndex].at(fromBefore ? 0 : -1).focus(); } } } function nextFocusGroup(children, currentIndex, direction, target) { const originGroup = groups[currentIndex]; const origin = children[currentIndex]; if (originGroup.type !== "list") { if (!(direction === "forward" ? origin.at(-1) === target : origin.at(0) === target)) return null; } const step = direction === "forward" ? 1 : -1; for (let i = currentIndex + step; i >= 0 && i < groups.length; i += step) { const group = groups[i]; if (children[i].length > 0 || group.type === "list" && toValue(group.displayItemsCount) > 0) return i; } return null; } return { onTabKeydown }; } //#endregion //#region node_modules/vuetify/lib/composables/filter.js /** * - boolean: match without highlight * - number: single match (index), length already known * - []: single match (start, end) * - [][]: multiple matches (start, end), shouldn't overlap */ var defaultFilter = (value, query, item) => { if (value == null || query == null) return -1; if (!query.length) return 0; value = value.toString().toLocaleLowerCase(); query = query.toString().toLocaleLowerCase(); const result = []; let idx = value.indexOf(query); while (~idx) { result.push([idx, idx + query.length]); idx = value.indexOf(query, idx + query.length); } return result.length ? result : -1; }; function normaliseMatch(match, query) { if (match == null || typeof match === "boolean" || match === -1) return; if (typeof match === "number") return [[match, match + query.length]]; if (Array.isArray(match[0])) return match; return [match]; } var makeFilterProps = propsFactory({ customFilter: Function, customKeyFilter: Object, filterKeys: [Array, String], filterMode: { type: String, default: "intersection" }, noFilter: Boolean }, "filter"); function filterItems(items, query, options) { const array = []; const filter = options?.default ?? defaultFilter; const keys = options?.filterKeys ? wrapInArray(options.filterKeys) : false; const customFiltersLength = Object.keys(options?.customKeyFilter ?? {}).length; if (!items?.length) return array; let lookAheadItems = []; loop: for (let i = 0; i < items.length; i++) { const [item, transformed = item] = wrapInArray(items[i]); const customMatches = {}; const defaultMatches = {}; let match = -1; if ((query || customFiltersLength > 0) && !options?.noFilter) { let hasOnlyCustomFilters = false; if (typeof item === "object") { if (item.type === "divider" || item.type === "subheader") { if (lookAheadItems.at(-1)?.type !== "divider" || item.type !== "subheader") lookAheadItems = []; lookAheadItems.push({ index: i, matches: {}, type: item.type }); continue; } const filterKeys = keys || Object.keys(transformed); hasOnlyCustomFilters = filterKeys.length === customFiltersLength; for (const key of filterKeys) { const value = getPropertyFromItem(transformed, key); const keyFilter = options?.customKeyFilter?.[key]; match = keyFilter ? keyFilter(value, query, item) : filter(value, query, item); if (match !== -1 && match !== false) if (keyFilter) customMatches[key] = normaliseMatch(match, query); else defaultMatches[key] = normaliseMatch(match, query); else if (options?.filterMode === "every") continue loop; } } else { match = filter(item, query, item); if (match !== -1 && match !== false) defaultMatches.title = normaliseMatch(match, query); } const defaultMatchesLength = Object.keys(defaultMatches).length; const customMatchesLength = Object.keys(customMatches).length; if (!defaultMatchesLength && !customMatchesLength) continue; if (options?.filterMode === "union" && customMatchesLength !== customFiltersLength && !defaultMatchesLength) continue; if (options?.filterMode === "intersection" && (customMatchesLength !== customFiltersLength || !defaultMatchesLength && customFiltersLength > 0 && !hasOnlyCustomFilters)) continue; } if (lookAheadItems.length) { array.push(...lookAheadItems); lookAheadItems = []; } array.push({ index: i, matches: { ...defaultMatches, ...customMatches } }); } return array; } function useFilter(props, items, query, options) { const filteredItems = shallowRef([]); const filteredMatches = shallowRef(/* @__PURE__ */ new Map()); const transformedItems = computed(() => options?.transform ? unref(items).map((item) => [item, options.transform(item)]) : unref(items)); watchEffect(() => { const _query = typeof query === "function" ? query() : unref(query); const strQuery = typeof _query !== "string" && typeof _query !== "number" ? "" : String(_query); const results = filterItems(transformedItems.value, strQuery, { customKeyFilter: { ...props.customKeyFilter, ...unref(options?.customKeyFilter) }, default: props.customFilter, filterKeys: props.filterKeys, filterMode: props.filterMode, noFilter: props.noFilter }); const originalItems = unref(items); const _filteredItems = []; const _filteredMatches = /* @__PURE__ */ new Map(); results.forEach(({ index, matches }) => { const item = originalItems[index]; _filteredItems.push(item); _filteredMatches.set(item.value, matches); }); filteredItems.value = _filteredItems; filteredMatches.value = _filteredMatches; }); function getMatches(item) { return filteredMatches.value.get(item.value); } return { filteredItems, filteredMatches, getMatches }; } function highlightResult(name, text, matches) { if (matches == null || !matches.length) return text; return matches.map((match, i) => { const start = i === 0 ? 0 : matches[i - 1][1]; const result = [createBaseVNode("span", { "class": normalizeClass(`${name}__unmask`) }, [text.slice(start, match[0])]), createBaseVNode("span", { "class": normalizeClass(`${name}__mask`) }, [text.slice(match[0], match[1])])]; if (i === matches.length - 1) result.push(createBaseVNode("span", { "class": normalizeClass(`${name}__unmask`) }, [text.slice(match[1])])); return createBaseVNode(Fragment, null, [result]); }); } //#endregion //#region node_modules/vuetify/lib/composables/menuActivator.js var makeMenuActivatorProps = propsFactory({ closeText: { type: String, default: "$vuetify.close" }, openText: { type: String, default: "$vuetify.open" } }, "autocomplete"); function useMenuActivator(props, isOpen) { const uid = useId(); const menuId = computed(() => `menu-${uid}`); return { menuId, ariaExpanded: toRef(() => toValue(isOpen)), ariaControls: toRef(() => menuId.value) }; } //#endregion //#region node_modules/vuetify/lib/components/VSelect/VSelect.js var makeSelectProps = propsFactory({ chips: Boolean, closableChips: Boolean, eager: Boolean, hideNoData: Boolean, hideSelected: Boolean, listProps: { type: Object }, menu: Boolean, menuElevation: [Number, String], menuIcon: { type: IconValue, default: "$dropdown" }, menuProps: { type: Object }, multiple: Boolean, noDataText: { type: String, default: "$vuetify.noDataText" }, openOnClear: Boolean, itemColor: String, noAutoScroll: Boolean, ...makeMenuActivatorProps(), ...makeItemsProps({ itemChildren: false }) }, "Select"); var makeVSelectProps = propsFactory({ search: String, ...makeFilterProps({ filterKeys: ["title"] }), ...makeSelectProps(), ...omit(makeVTextFieldProps({ modelValue: null, role: "combobox" }), ["validationValue", "dirty"]), ...makeTransitionProps({ transition: { component: VDialogTransition } }) }, "VSelect"); var VSelect = genericComponent()({ name: "VSelect", props: makeVSelectProps(), emits: { "update:focused": (focused) => true, "update:modelValue": (value) => true, "update:menu": (ue) => true, "update:search": (value) => true }, setup(props, { slots }) { const { t } = useLocale(); const vTextFieldRef = ref(); const vMenuRef = ref(); const headerRef = ref(); const footerRef = ref(); const vVirtualScrollRef = ref(); const { items, transformIn, transformOut } = useItems(props); const search = useProxiedModel(props, "search", ""); const { filteredItems, getMatches } = useFilter(props, items, () => search.value); const model = useProxiedModel(props, "modelValue", [], (v) => transformIn(v === null ? [null] : wrapInArray(v)), (v) => { const transformed = transformOut(v); return props.multiple ? transformed : transformed[0] ?? null; }); const counterValue = computed(() => { return typeof props.counterValue === "function" ? props.counterValue(model.value) : typeof props.counterValue === "number" ? props.counterValue : model.value.length; }); const form = useForm(props); const autocomplete = useAutocomplete(props); const selectedValues = computed(() => model.value.map((selection) => selection.value)); const isFocused = shallowRef(false); const closableChips = toRef(() => props.closableChips && !form.isReadonly.value && !form.isDisabled.value); const { InputIcon } = useInputIcon(props); let keyboardLookupPrefix = ""; let keyboardLookupIndex = 0; let keyboardLookupLastTime; const displayItems = computed(() => { const baseItems = search.value ? filteredItems.value : items.value; if (props.hideSelected) return baseItems.filter((item) => !model.value.some((s) => (props.valueComparator || deepEqual)(s, item))); return baseItems; }); const menuDisabled = computed(() => props.hideNoData && !displayItems.value.length || form.isReadonly.value || form.isDisabled.value); const _menu = useProxiedModel(props, "menu"); const menu = computed({ get: () => _menu.value, set: (v) => { if (_menu.value && !v && vMenuRef.value?.ΨopenChildren.size) return; if (v && menuDisabled.value) return; _menu.value = v; } }); const { menuId, ariaExpanded, ariaControls } = useMenuActivator(props, menu); const computedMenuProps = computed(() => { return { ...props.menuProps, activatorProps: { ...props.menuProps?.activatorProps || {}, "aria-haspopup": "listbox" } }; }); const listRef = ref(); const listEvents = useScrolling(listRef, vTextFieldRef); const { onTabKeydown } = useFocusGroups({ groups: [ { type: "element", contentRef: headerRef }, { type: "list", contentRef: listRef, displayItemsCount: () => displayItems.value.length }, { type: "element", contentRef: footerRef } ], onLeave: () => { menu.value = false; vTextFieldRef.value?.focus(); } }); function onClear(e) { if (props.openOnClear) menu.value = true; } function onMousedownControl() { if (menuDisabled.value) return; menu.value = !menu.value; } function onMenuKeydown(e) { if (e.key === "Tab") onTabKeydown(e); if (listRef.value?.$el.contains(e.target) && checkPrintable(e)) onKeydown(e); } function onKeydown(e) { if (!e.key || form.isReadonly.value) return; if ([ "Enter", " ", "ArrowDown", "ArrowUp", "Home", "End" ].includes(e.key)) e.preventDefault(); if ([ "Enter", "ArrowDown", " " ].includes(e.key)) menu.value = true; if (["Escape", "Tab"].includes(e.key)) menu.value = false; if (props.clearable && e.key === "Backspace") { e.preventDefault(); model.value = []; onClear(e); return; } if (e.key === "Home") listRef.value?.focus("first"); else if (e.key === "End") listRef.value?.focus("last"); const KEYBOARD_LOOKUP_THRESHOLD = 1e3; if (!checkPrintable(e)) return; const now = performance.now(); if (now - keyboardLookupLastTime > KEYBOARD_LOOKUP_THRESHOLD) { keyboardLookupPrefix = ""; keyboardLookupIndex = 0; } keyboardLookupPrefix += e.key.toLowerCase(); keyboardLookupLastTime = now; const items = displayItems.value; function findItem() { let result = findItemBase(); if (result) return result; if (keyboardLookupPrefix.at(-1) === keyboardLookupPrefix.at(-2)) { keyboardLookupPrefix = keyboardLookupPrefix.slice(0, -1); keyboardLookupIndex++; result = findItemBase(); if (result) return result; } keyboardLookupIndex = 0; result = findItemBase(); if (result) return result; keyboardLookupPrefix = e.key.toLowerCase(); return findItemBase(); } function findItemBase() { for (let i = keyboardLookupIndex; i < items.length; i++) { const _item = items[i]; if (_item.title.toLowerCase().startsWith(keyboardLookupPrefix)) return [_item, i]; } } const result = findItem(); if (!result) return; const [item, index] = result; keyboardLookupIndex = index; listRef.value?.focus(index); if (!props.multiple) model.value = [item]; } /** @param set - null means toggle */ function select(item, set = true) { if (item.props.disabled) return; if (props.multiple) { const index = model.value.findIndex((selection) => (props.valueComparator || deepEqual)(selection.value, item.value)); const add = set == null ? !~index : set; if (~index) { const value = add ? [...model.value, item] : [...model.value]; value.splice(index, 1); model.value = value; } else if (add) model.value = [...model.value, item]; } else { model.value = set !== false ? [item] : []; nextTick(() => { menu.value = false; }); } } function onBlur(e) { const target = e.target; if (!vTextFieldRef.value?.$el.contains(target)) menu.value = false; } function getSelectedIndex() { return displayItems.value.findIndex((item) => model.value.some((s) => (props.valueComparator || deepEqual)(s.value, item.value))); } function getSelectedFocusableIndex() { if (!model.value.length) return -1; const comparator = props.valueComparator || deepEqual; let focusableIndex = 0; for (const item of displayItems.value) { if (model.value.some((s) => comparator(s.value, item.value))) return item.props.disabled ? -1 : focusableIndex; if (!item.props.disabled) focusableIndex++; } return -1; } function onAfterEnter() { if (props.eager) vVirtualScrollRef.value?.calculateVisibleItems(); if (listRef.value && isFocused.value) { const index = getSelectedFocusableIndex(); listRef.value.focus(index >= 0 ? index : "first"); } } function onAfterLeave() { search.value = ""; if (isFocused.value) vTextFieldRef.value?.focus(); } function onFocusin(e) { isFocused.value = true; } function onFocusout(e) { if (!vTextFieldRef.value?.$el.contains(e.relatedTarget) && !e.currentTarget.contains(e.relatedTarget)) isFocused.value = false; } function onModelUpdate(v) { if (v == null) model.value = []; else if (matchesSelector(vTextFieldRef.value, ":autofill") || matchesSelector(vTextFieldRef.value, ":-webkit-autofill")) { const item = items.value.find((item) => item.title === v); if (item) select(item); } else if (vTextFieldRef.value) vTextFieldRef.value.value = ""; } watch(menu, () => { if (!props.hideSelected && menu.value && model.value.length) { const index = getSelectedIndex(); IN_BROWSER && !props.noAutoScroll && window.requestAnimationFrame(() => { index >= 0 && vVirtualScrollRef.value?.scrollToIndex(index); }); } }); watch(items, (newVal, oldVal) => { if (menu.value) return; if (isFocused.value && props.hideNoData && !oldVal.length && newVal.length) menu.value = true; }); useRender(() => { const hasChips = !!(props.chips || slots.chip); const hasList = !!(!props.hideNoData || displayItems.value.length || slots["prepend-item"] || slots["append-item"] || slots["no-data"]); const isDirty = model.value.length > 0; const textFieldProps = VTextField.filterProps(props); const placeholder = isDirty || !isFocused.value && props.label && !props.persistentPlaceholder ? void 0 : props.placeholder; const menuSlotProps = { search, filteredItems: filteredItems.value }; return createVNode(VTextField, mergeProps({ "ref": vTextFieldRef }, textFieldProps, { "modelValue": model.value.map((v) => v.props.title).join(", "), "name": void 0, "onUpdate:modelValue": onModelUpdate, "focused": isFocused.value, "onUpdate:focused": ($event) => isFocused.value = $event, "validationValue": model.externalValue, "counterValue": counterValue.value, "dirty": isDirty, "class": [ "v-select", { "v-select--active-menu": menu.value, "v-select--chips": !!props.chips, [`v-select--${props.multiple ? "multiple" : "single"}`]: true, "v-select--selected": model.value.length, "v-select--selection-slot": !!slots.selection }, props.class ], "style": props.style, "inputmode": "none", "placeholder": placeholder, "onClick:clear": onClear, "onMousedown:control": onMousedownControl, "onBlur": onBlur, "onKeydown": onKeydown, "aria-expanded": ariaExpanded.value, "aria-controls": ariaControls.value }), { ...slots, default: ({ id }) => createBaseVNode(Fragment, null, [ createBaseVNode("select", { "hidden": true, "multiple": props.multiple, "name": autocomplete.fieldName.value }, [items.value.map((item) => createBaseVNode("option", { "key": item.value, "value": item.value, "selected": selectedValues.value.includes(item.value) }, null))]), createVNode(VMenu, mergeProps({ "id": menuId.value, "ref": vMenuRef, "modelValue": menu.value, "onUpdate:modelValue": ($event) => menu.value = $event, "activator": "parent", "contentClass": "v-select__content", "disabled": menuDisabled.value, "eager": props.eager, "maxHeight": 310, "openOnClick": false, "closeOnContentClick": false, "transition": props.transition, "onAfterEnter": onAfterEnter, "onAfterLeave": onAfterLeave }, computedMenuProps.value), { default: () => [createVNode(VSheet, { "elevation": props.menuElevation, "onFocusin": onFocusin, "onFocusout": onFocusout, "onKeydown": onMenuKeydown }, { default: () => [ slots["menu-header"] && createBaseVNode("header", { "ref": headerRef }, [slots["menu-header"](menuSlotProps)]), hasList && createVNode(VList, mergeProps({ "key": "select-list", "ref": listRef, "selected": selectedValues.value, "selectStrategy": props.multiple ? "independent" : "single-independent", "tabindex": "-1", "selectable": !!displayItems.value.length, "aria-live": "polite", "aria-labelledby": `${id.value}-label`, "aria-multiselectable": props.multiple, "color": props.itemColor ?? props.color }, listEvents, props.listProps), { default: () => [ slots["prepend-item"]?.(), !displayItems.value.length && !props.hideNoData && (slots["no-data"]?.() ?? createVNode(VListItem, { "key": "no-data", "title": t(props.noDataText) }, null)), createVNode(VVirtualScroll, { "ref": vVirtualScrollRef, "renderless": true, "items": displayItems.value, "itemKey": "value" }, { default: ({ item, index, itemRef }) => { const camelizedProps = camelizeProps(item.props); const itemProps = mergeProps(item.props, { ref: itemRef, key: item.value, onClick: () => select(item, null), "aria-posinset": index + 1, "aria-setsize": displayItems.value.length }); if (item.type === "divider") return slots.divider?.({ props: item.raw, index }) ?? createVNode(VDivider, mergeProps(item.props, { "key": `divider-${index}` }), null); if (item.type === "subheader") return slots.subheader?.({ props: item.raw, index }) ?? createVNode(VListSubheader, mergeProps(item.props, { "key": `subheader-${index}` }), null); return slots.item?.({ item: item.raw, internalItem: item, index, props: itemProps }) ?? createVNode(VListItem, mergeProps(itemProps, { "role": "option" }), { prepend: ({ isSelected }) => createBaseVNode(Fragment, null, [ props.multiple && !props.hideSelected ? createVNode(VCheckboxBtn, { "key": item.value, "modelValue": isSelected, "ripple": false, "tabindex": "-1", "aria-hidden": true, "onClick": (event) => event.preventDefault() }, null) : void 0, camelizedProps.prependAvatar && createVNode(VAvatar, { "image": camelizedProps.prependAvatar }, null), camelizedProps.prependIcon && createVNode(VIcon, { "icon": camelizedProps.prependIcon }, null) ]), title: () => { return search.value ? highlightResult("v-select", item.title, getMatches(item)?.title) : item.title; } }); } }), slots["append-item"]?.() ] }), slots["menu-footer"] && createBaseVNode("footer", { "ref": footerRef }, [slots["menu-footer"](menuSlotProps)]) ] })] }), model.value.map((item, index) => { function onChipClose(e) { e.stopPropagation(); e.preventDefault(); select(item, false); } const slotProps = mergeProps(VChip.filterProps(item.props), { "onClick:close": onChipClose, onKeydown(e) { if (e.key !== "Enter" && e.key !== " ") return; e.preventDefault(); e.stopPropagation(); onChipClose(e); }, onMousedown(e) { e.preventDefault(); e.stopPropagation(); }, modelValue: true, "onUpdate:modelValue": void 0 }); const hasSlot = hasChips ? !!slots.chip : !!slots.selection; const slotContent = hasSlot ? ensureValidVNode(hasChips ? slots.chip({ item: item.raw, internalItem: item, index, props: slotProps }) : slots.selection({ item: item.raw, internalItem: item, index })) : void 0; if (hasSlot && !slotContent) return void 0; return createBaseVNode("div", { "key": item.value, "class": "v-select__selection" }, [hasChips ? !slots.chip ? createVNode(VChip, mergeProps({ "key": "chip", "closable": closableChips.value, "size": "small", "text": item.title, "disabled": item.props.disabled }, slotProps), null) : createVNode(VDefaultsProvider, { "key": "chip-defaults", "defaults": { VChip: { closable: closableChips.value, size: "small", text: item.title } } }, { default: () => [slotContent] }) : slotContent ?? createBaseVNode("span", { "class": "v-select__selection-text" }, [item.title, props.multiple && index < model.value.length - 1 && createBaseVNode("span", { "class": "v-select__selection-comma" }, [createTextVNode(",")])])]); }) ]), "append-inner": (...args) => createBaseVNode(Fragment, null, [ slots["append-inner"]?.(...args), props.menuIcon ? createVNode(VIcon, { "class": "v-select__menu-icon", "color": vTextFieldRef.value?.fieldIconColor, "icon": props.menuIcon, "aria-hidden": true }, null) : void 0, props.appendInnerIcon && createVNode(InputIcon, { "key": "append-icon", "name": "appendInner", "color": args[0].iconColor.value }, null) ]) }); }); return forwardRefs({ isFocused, menu, search, filteredItems, select }, vTextFieldRef); } }); //#endregion export { VSelect }; //# sourceMappingURL=vuetify_components_VSelect.js.map