@alfakit/vue 0.1.2 → 0.1.6
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/CHANGELOG.md +8 -0
- package/dist/AlfakitRoot.js.map +1 -1
- package/dist/AlfakitRoot.vue.d.ts.map +1 -1
- package/dist/AlfakitRoot.vue_vue_type_script_setup_true_lang.js +3 -1
- package/dist/AlfakitRoot.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/actions/ActionGroupMenu.js.map +1 -1
- package/dist/components/actions/ActionGroupMenu.vue.d.ts.map +1 -1
- package/dist/components/actions/ActionGroupMenu.vue_vue_type_script_setup_true_lang.js +69 -65
- package/dist/components/actions/ActionGroupMenu.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/actions/ActionModal.js.map +1 -1
- package/dist/components/actions/ActionModal.vue.d.ts.map +1 -1
- package/dist/components/actions/ActionModal.vue_vue_type_script_setup_true_lang.js +17 -15
- package/dist/components/actions/ActionModal.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/ai/AiCopilot.js.map +1 -1
- package/dist/components/ai/AiCopilot.vue.d.ts +2 -0
- package/dist/components/ai/AiCopilot.vue.d.ts.map +1 -1
- package/dist/components/ai/AiCopilot.vue_vue_type_script_setup_true_lang.js +7 -2
- package/dist/components/ai/AiCopilot.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/cms/CmsPage.vue_vue_type_script_setup_true_lang.js +19 -19
- package/dist/components/cms/CmsPage.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/cms/LivePreview.js.map +1 -1
- package/dist/components/cms/LivePreview.vue.d.ts.map +1 -1
- package/dist/components/cms/LivePreview.vue_vue_type_script_setup_true_lang.js +83 -83
- package/dist/components/cms/LivePreview.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/BuilderField.js.map +1 -1
- package/dist/components/fields/BuilderField.vue.d.ts.map +1 -1
- package/dist/components/fields/BuilderField.vue_vue_type_script_setup_true_lang.js +162 -157
- package/dist/components/fields/BuilderField.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/ImageEditorDialog.js.map +1 -1
- package/dist/components/fields/ImageEditorDialog.vue.d.ts.map +1 -1
- package/dist/components/fields/ImageEditorDialog.vue_vue_type_script_setup_true_lang.js +46 -46
- package/dist/components/fields/ImageEditorDialog.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/KeyValueField.js.map +1 -1
- package/dist/components/fields/KeyValueField.vue.d.ts.map +1 -1
- package/dist/components/fields/KeyValueField.vue_vue_type_script_setup_true_lang.js +66 -66
- package/dist/components/fields/KeyValueField.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/ModalTablePicker.js.map +1 -1
- package/dist/components/fields/ModalTablePicker.vue.d.ts.map +1 -1
- package/dist/components/fields/ModalTablePicker.vue_vue_type_script_setup_true_lang.js +113 -113
- package/dist/components/fields/ModalTablePicker.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/RepeaterField.js.map +1 -1
- package/dist/components/fields/RepeaterField.vue.d.ts.map +1 -1
- package/dist/components/fields/RepeaterField.vue_vue_type_script_setup_true_lang.js +12 -12
- package/dist/components/fields/RepeaterField.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/RichEditorInput.js.map +1 -1
- package/dist/components/fields/RichEditorInput.vue.d.ts.map +1 -1
- package/dist/components/fields/RichEditorInput.vue_vue_type_script_setup_true_lang.js +166 -165
- package/dist/components/fields/RichEditorInput.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/SliderField.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/fields/item-actions.d.ts +2 -2
- package/dist/components/fields/item-actions.d.ts.map +1 -1
- package/dist/components/fields/item-actions.js +31 -31
- package/dist/components/fields/item-actions.js.map +1 -1
- package/dist/components/form/FormBlock.js.map +1 -1
- package/dist/components/form/FormBlock.vue.d.ts.map +1 -1
- package/dist/components/form/FormBlock.vue_vue_type_script_setup_true_lang.js +1 -1
- package/dist/components/form/FormBlock.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/form/form-context.js +25 -25
- package/dist/components/form/form-context.js.map +1 -1
- package/dist/components/kanban/KanbanBoard.js.map +1 -1
- package/dist/components/kanban/KanbanBoard.vue.d.ts.map +1 -1
- package/dist/components/kanban/KanbanBoard.vue_vue_type_script_setup_true_lang.js +5 -2
- package/dist/components/kanban/KanbanBoard.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/kanban/KanbanColumnHeader.js.map +1 -1
- package/dist/components/kanban/KanbanColumnHeader.vue.d.ts.map +1 -1
- package/dist/components/kanban/KanbanColumnHeader.vue_vue_type_script_setup_true_lang.js +64 -64
- package/dist/components/kanban/KanbanColumnHeader.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/layout/SectionComponent.js.map +1 -1
- package/dist/components/layout/SectionComponent.vue.d.ts.map +1 -1
- package/dist/components/layout/SectionComponent.vue_vue_type_script_setup_true_lang.js +23 -23
- package/dist/components/layout/SectionComponent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/DebugPanel.vue_vue_type_script_setup_true_lang.js +8 -8
- package/dist/components/panel/DebugPanel.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/GlobalSearchPalette.js.map +1 -1
- package/dist/components/panel/GlobalSearchPalette.vue.d.ts.map +1 -1
- package/dist/components/panel/GlobalSearchPalette.vue_vue_type_script_setup_true_lang.js +102 -96
- package/dist/components/panel/GlobalSearchPalette.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/NavGroup.vue_vue_type_script_setup_true_lang.js +10 -10
- package/dist/components/panel/NavGroup.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/NavGroupFlyout.vue_vue_type_script_setup_true_lang.js +9 -9
- package/dist/components/panel/NavGroupFlyout.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/NavItem.vue_vue_type_script_setup_true_lang.js +16 -16
- package/dist/components/panel/NavItem.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/NavSubItem.vue_vue_type_script_setup_true_lang.js +10 -10
- package/dist/components/panel/NavSubItem.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/TenantMenu.vue_vue_type_script_setup_true_lang.js +35 -35
- package/dist/components/panel/TenantMenu.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/panel/Topbar.vue_vue_type_script_setup_true_lang.js +11 -11
- package/dist/components/panel/Topbar.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/realtime/use-live-updates.d.ts.map +1 -1
- package/dist/components/realtime/use-live-updates.js +24 -23
- package/dist/components/realtime/use-live-updates.js.map +1 -1
- package/dist/components/table/BooleanCell.vue_vue_type_script_setup_true_lang.js +2 -1
- package/dist/components/table/BooleanCell.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/ColumnHeader.js.map +1 -1
- package/dist/components/table/ColumnHeader.vue.d.ts.map +1 -1
- package/dist/components/table/ColumnHeader.vue_vue_type_script_setup_true_lang.js +55 -49
- package/dist/components/table/ColumnHeader.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/ColumnManager.js.map +1 -1
- package/dist/components/table/ColumnManager.vue.d.ts.map +1 -1
- package/dist/components/table/ColumnManager.vue_vue_type_script_setup_true_lang.js +5 -4
- package/dist/components/table/ColumnManager.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/ContentLayoutSort.js.map +1 -1
- package/dist/components/table/ContentLayoutSort.vue.d.ts.map +1 -1
- package/dist/components/table/ContentLayoutSort.vue_vue_type_script_setup_true_lang.js +5 -5
- package/dist/components/table/ContentLayoutSort.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/SelectCell.vue_vue_type_script_setup_true_lang.js +2 -1
- package/dist/components/table/SelectCell.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/SelectComboboxCell.vue_vue_type_script_setup_true_lang.js +2 -1
- package/dist/components/table/SelectComboboxCell.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/TableCellContent.js.map +1 -1
- package/dist/components/table/TableCellContent.vue.d.ts.map +1 -1
- package/dist/components/table/TableCellContent.vue_vue_type_script_setup_true_lang.js +4 -3
- package/dist/components/table/TableCellContent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/TablePagination.js.map +1 -1
- package/dist/components/table/TablePagination.vue.d.ts.map +1 -1
- package/dist/components/table/TablePagination.vue_vue_type_script_setup_true_lang.js +87 -87
- package/dist/components/table/TablePagination.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/TextInputCell.vue_vue_type_script_setup_true_lang.js +2 -1
- package/dist/components/table/TextInputCell.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/table/cell-update.d.ts +6 -0
- package/dist/components/table/cell-update.d.ts.map +1 -1
- package/dist/components/table/cell-update.js.map +1 -1
- package/dist/components/translation-manager/TranslationManagerView.vue_vue_type_script_setup_true_lang.js +1 -1
- package/dist/components/translation-manager/TranslationManagerView.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/ui/CommandAutoHighlight.js +7 -0
- package/dist/components/ui/CommandAutoHighlight.js.map +1 -0
- package/dist/components/ui/CommandAutoHighlight.vue.d.ts +21 -0
- package/dist/components/ui/CommandAutoHighlight.vue.d.ts.map +1 -0
- package/dist/components/ui/CommandAutoHighlight.vue_vue_type_script_setup_true_lang.js +18 -0
- package/dist/components/ui/CommandAutoHighlight.vue_vue_type_script_setup_true_lang.js.map +1 -0
- package/dist/components/ui/DialogContent.js.map +1 -1
- package/dist/components/ui/DialogContent.vue.d.ts.map +1 -1
- package/dist/components/ui/DialogContent.vue_vue_type_script_setup_true_lang.js +13 -12
- package/dist/components/ui/DialogContent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/ui/PopoverContent.js.map +1 -1
- package/dist/components/ui/PopoverContent.vue.d.ts.map +1 -1
- package/dist/components/ui/PopoverContent.vue_vue_type_script_setup_true_lang.js +9 -8
- package/dist/components/ui/PopoverContent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/ui/SheetContent.js.map +1 -1
- package/dist/components/ui/SheetContent.vue.d.ts.map +1 -1
- package/dist/components/ui/SheetContent.vue_vue_type_script_setup_true_lang.js +13 -12
- package/dist/components/ui/SheetContent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/components/ui/TooltipContent.js.map +1 -1
- package/dist/components/ui/TooltipContent.vue.d.ts.map +1 -1
- package/dist/components/ui/TooltipContent.vue_vue_type_script_setup_true_lang.js +9 -8
- package/dist/components/ui/TooltipContent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/context.d.ts +7 -0
- package/dist/context.d.ts.map +1 -1
- package/dist/context.js +29 -26
- package/dist/context.js.map +1 -1
- package/dist/create-alfakit.d.ts.map +1 -1
- package/dist/create-alfakit.js +33 -31
- package/dist/create-alfakit.js.map +1 -1
- package/dist/eject-manifest.json +11 -2
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +219 -217
- package/dist/layouts/AppLayout.vue_vue_type_script_setup_true_lang.js +8 -8
- package/dist/layouts/AppLayout.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/layouts/AuthLayout.vue_vue_type_script_setup_true_lang.js +9 -9
- package/dist/layouts/FullscreenLayout.vue_vue_type_script_setup_true_lang.js +8 -8
- package/dist/layouts/FullscreenLayout.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/layouts/TopNavLayout.vue_vue_type_script_setup_true_lang.js +15 -15
- package/dist/layouts/TopNavLayout.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/layouts/lazy-layouts.d.ts +10 -0
- package/dist/layouts/lazy-layouts.d.ts.map +1 -0
- package/dist/layouts/lazy-layouts.js +8 -0
- package/dist/layouts/lazy-layouts.js.map +1 -0
- package/dist/layouts/panel-layouts.d.ts +8 -0
- package/dist/layouts/panel-layouts.d.ts.map +1 -0
- package/dist/layouts/panel-layouts.js +15 -0
- package/dist/layouts/panel-layouts.js.map +1 -0
- package/dist/lib/lazy.d.ts.map +1 -1
- package/dist/lib/lazy.js +2 -2
- package/dist/lib/lazy.js.map +1 -1
- package/dist/pages/PageShell.js.map +1 -1
- package/dist/pages/PageShell.vue.d.ts.map +1 -1
- package/dist/pages/PageShell.vue_vue_type_script_setup_true_lang.js +39 -42
- package/dist/pages/PageShell.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/standalone/AlfakitComponent.js.map +1 -1
- package/dist/standalone/AlfakitComponent.vue.d.ts.map +1 -1
- package/dist/standalone/AlfakitComponent.vue_vue_type_script_setup_true_lang.js +56 -52
- package/dist/standalone/AlfakitComponent.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/standalone.css +7 -0
- package/dist/starter-kit/AlfakitStarterKitRoot.js.map +1 -1
- package/dist/starter-kit/AlfakitStarterKitRoot.vue.d.ts +2 -2
- package/dist/starter-kit/AlfakitStarterKitRoot.vue.d.ts.map +1 -1
- package/dist/starter-kit/AlfakitStarterKitRoot.vue_vue_type_script_setup_true_lang.js +17 -12
- package/dist/starter-kit/AlfakitStarterKitRoot.vue_vue_type_script_setup_true_lang.js.map +1 -1
- package/dist/starter-kit/dashboard-widgets.d.ts +54 -0
- package/dist/starter-kit/dashboard-widgets.d.ts.map +1 -0
- package/dist/starter-kit/dashboard-widgets.js +54 -0
- package/dist/starter-kit/dashboard-widgets.js.map +1 -0
- package/dist/starter-kit/index.d.ts +2 -1
- package/dist/starter-kit/index.d.ts.map +1 -1
- package/dist/starter-kit/index.js +5 -4
- package/dist/starter-kit/runtime.d.ts +6 -0
- package/dist/starter-kit/runtime.d.ts.map +1 -1
- package/dist/starter-kit/runtime.js +19 -15
- package/dist/starter-kit/runtime.js.map +1 -1
- package/dist/starter-kit/starter-kit.d.ts.map +1 -1
- package/dist/starter-kit/starter-kit.js +8 -8
- package/dist/starter-kit/starter-kit.js.map +1 -1
- package/dist/starter-kit/widgets/CopilotTrigger.js +7 -0
- package/dist/starter-kit/widgets/CopilotTrigger.js.map +1 -0
- package/dist/starter-kit/widgets/CopilotTrigger.vue.d.ts +12 -0
- package/dist/starter-kit/widgets/CopilotTrigger.vue.d.ts.map +1 -0
- package/dist/starter-kit/widgets/CopilotTrigger.vue_vue_type_script_setup_true_lang.js +23 -0
- package/dist/starter-kit/widgets/CopilotTrigger.vue_vue_type_script_setup_true_lang.js.map +1 -0
- package/dist/starter-kit/widgets/LoadedCopilot.js +7 -0
- package/dist/starter-kit/widgets/LoadedCopilot.js.map +1 -0
- package/dist/starter-kit/widgets/LoadedCopilot.vue.d.ts +8 -0
- package/dist/starter-kit/widgets/LoadedCopilot.vue.d.ts.map +1 -0
- package/dist/starter-kit/widgets/LoadedCopilot.vue_vue_type_script_setup_true_lang.js +31 -0
- package/dist/starter-kit/widgets/LoadedCopilot.vue_vue_type_script_setup_true_lang.js.map +1 -0
- package/dist/starter-kit/widgets/StarterKitImpersonationBanner.js +7 -0
- package/dist/starter-kit/widgets/StarterKitImpersonationBanner.js.map +1 -0
- package/dist/starter-kit/widgets/StarterKitImpersonationBanner.vue.d.ts +8 -0
- package/dist/starter-kit/widgets/StarterKitImpersonationBanner.vue.d.ts.map +1 -0
- package/dist/starter-kit/widgets/StarterKitImpersonationBanner.vue_vue_type_script_setup_true_lang.js +34 -0
- package/dist/starter-kit/widgets/StarterKitImpersonationBanner.vue_vue_type_script_setup_true_lang.js.map +1 -0
- package/dist/starter-kit/widgets/index.d.ts +40 -9
- package/dist/starter-kit/widgets/index.d.ts.map +1 -1
- package/dist/starter-kit/widgets/index.js +21 -18
- package/dist/starter-kit/widgets/index.js.map +1 -1
- package/dist/starter-kit/widgets/loaded.d.ts +10 -0
- package/dist/starter-kit/widgets/loaded.d.ts.map +1 -0
- package/dist/starter-kit/widgets/loaded.js +5 -0
- package/dist/styles.css +9 -2
- package/dist/themes.css +6 -1
- package/package.json +2 -2
- package/src/AlfakitRoot.vue +9 -1
- package/src/components/actions/ActionGroupMenu.vue +13 -1
- package/src/components/actions/ActionModal.vue +9 -0
- package/src/components/ai/AiCopilot.vue +7 -1
- package/src/components/cms/LivePreview.vue +8 -2
- package/src/components/fields/BuilderField.vue +15 -2
- package/src/components/fields/ImageEditorDialog.vue +7 -3
- package/src/components/fields/KeyValueField.vue +3 -2
- package/src/components/fields/ModalTablePicker.vue +7 -2
- package/src/components/fields/RepeaterField.vue +2 -3
- package/src/components/fields/RichEditorInput.vue +3 -0
- package/src/components/fields/item-actions.ts +31 -10
- package/src/components/form/FormBlock.vue +2 -1
- package/src/components/form/form-context.ts +2 -2
- package/src/components/kanban/KanbanBoard.vue +15 -3
- package/src/components/kanban/KanbanColumnHeader.vue +6 -4
- package/src/components/layout/SectionComponent.vue +10 -4
- package/src/components/panel/GlobalSearchPalette.vue +2 -0
- package/src/components/realtime/use-live-updates.ts +3 -1
- package/src/components/table/ColumnHeader.vue +23 -12
- package/src/components/table/ColumnManager.vue +12 -8
- package/src/components/table/ContentLayoutSort.vue +7 -1
- package/src/components/table/TableCellContent.vue +4 -2
- package/src/components/table/TablePagination.vue +12 -7
- package/src/components/table/cell-update.ts +6 -0
- package/src/components/ui/CommandAutoHighlight.vue +27 -0
- package/src/components/ui/DialogContent.vue +5 -1
- package/src/components/ui/PopoverContent.vue +5 -1
- package/src/components/ui/SheetContent.vue +5 -1
- package/src/components/ui/TooltipContent.vue +5 -1
- package/src/context.ts +10 -0
- package/src/create-alfakit.ts +5 -0
- package/src/index.ts +2 -0
- package/src/layouts/lazy-layouts.ts +14 -0
- package/src/layouts/panel-layouts.ts +17 -0
- package/src/lib/lazy.ts +11 -1
- package/src/pages/PageShell.vue +5 -6
- package/src/standalone/AlfakitComponent.vue +17 -6
- package/src/starter-kit/AlfakitStarterKitRoot.vue +12 -3
- package/src/starter-kit/dashboard-widgets.ts +93 -0
- package/src/starter-kit/index.ts +7 -1
- package/src/starter-kit/runtime.ts +17 -1
- package/src/starter-kit/starter-kit.ts +2 -1
- package/src/starter-kit/widgets/CopilotTrigger.vue +58 -0
- package/src/starter-kit/widgets/LoadedCopilot.vue +29 -0
- package/src/starter-kit/widgets/StarterKitImpersonationBanner.vue +57 -0
- package/src/starter-kit/widgets/index.ts +56 -11
- package/src/starter-kit/widgets/loaded.ts +9 -0
- package/src/styles.css +9 -2
|
@@ -97,30 +97,32 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
97
97
|
};
|
|
98
98
|
Ee(() => void E(We)), M(() => I.hidden, () => void E(We), { flush: "post" });
|
|
99
99
|
let Ge = v(() => Be[xe(H.value)]), Ke = v(() => xe(H.value) === "end" ? "sm:me-auto" : void 0), qe = v(() => we(H.value.slideOverPosition, Ve.value)), Je = U ? ee(Te(U)) : null, q = v(() => be(H.value, Je?.value)), J = De(""), Ye = v(() => I.modal.errors[me]?.[0]), Xe = Se(V, B), Ze = (e) => {
|
|
100
|
+
U ? U.whenSettled(() => Qe(e)) : Qe(e);
|
|
101
|
+
}, Qe = (e) => {
|
|
100
102
|
let t = U?.state.values ?? {}, n = {
|
|
101
103
|
...H.value.passwordConfirmation ? { password: J.value } : {},
|
|
102
104
|
...e ? { createAnother: !0 } : {}
|
|
103
105
|
};
|
|
104
106
|
Object.keys(n).length > 0 ? L.execute(B, V, t, n) : L.execute(B, V, t);
|
|
105
|
-
}, Y = () => Ze(!1),
|
|
107
|
+
}, Y = () => Ze(!1), $e = () => Ze(!0);
|
|
106
108
|
M(() => H.value.form, (e, t) => {
|
|
107
109
|
e && e !== t && U?.fill(e);
|
|
108
110
|
}), M(() => I.modal.refocus, (e, t, n) => {
|
|
109
111
|
let r = H.value.form?.components;
|
|
110
112
|
e && r && n(Ce(() => document.getElementById(`action-form-${B.name}`), r));
|
|
111
113
|
});
|
|
112
|
-
let
|
|
113
|
-
_e(H.value, U,
|
|
114
|
+
let et = () => L.cancelModal(B.name), X = z("unsaved_changes_close", {}, "You have unsaved changes. Close anyway?"), Z = () => {
|
|
115
|
+
_e(H.value, U, X) && et();
|
|
114
116
|
};
|
|
115
|
-
O(ye(H.value, U,
|
|
116
|
-
let
|
|
117
|
+
O(ye(H.value, U, X));
|
|
118
|
+
let tt = v(() => H.value.cancelColor ? a(s, H.value.cancelColor) : ""), nt = v(() => H.value.createAnotherColor ? a(s, H.value.createAnotherColor) : ""), Q = v(() => H.value.heading ?? B.label ?? z("actions", {}, "Actions")), rt = (e) => {
|
|
117
119
|
!e && !I.modal.processing && Z();
|
|
118
|
-
}, $ = v(() => !!(H.value.submitLabel || H.value.cancelLabel || H.value.extraFooterActions?.length)),
|
|
120
|
+
}, $ = v(() => !!(H.value.submitLabel || H.value.cancelLabel || H.value.extraFooterActions?.length)), it = v(() => !!(H.value.content || U || H.value.contentFooter || H.value.passwordConfirmation));
|
|
119
121
|
return (e, t) => H.value.slideOver ? (k(), y(se, {
|
|
120
122
|
key: 0,
|
|
121
123
|
open: !I.hidden,
|
|
122
124
|
modal: !H.value.clickThrough,
|
|
123
|
-
"onUpdate:open":
|
|
125
|
+
"onUpdate:open": rt
|
|
124
126
|
}, {
|
|
125
127
|
default: N(() => [w(ce, {
|
|
126
128
|
side: qe.value,
|
|
@@ -210,7 +212,7 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
210
212
|
key: 1,
|
|
211
213
|
type: "button",
|
|
212
214
|
variant: "outline",
|
|
213
|
-
class: D(
|
|
215
|
+
class: D(tt.value),
|
|
214
216
|
disabled: I.modal.processing,
|
|
215
217
|
onClick: Z
|
|
216
218
|
}, {
|
|
@@ -222,9 +224,9 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
222
224
|
type: "button",
|
|
223
225
|
variant: "outline",
|
|
224
226
|
"data-slot": "create-another",
|
|
225
|
-
class: D(
|
|
227
|
+
class: D(nt.value),
|
|
226
228
|
disabled: I.modal.processing,
|
|
227
|
-
onClick:
|
|
229
|
+
onClick: $e
|
|
228
230
|
}, {
|
|
229
231
|
default: N(() => [H.value.createAnotherIcon ? (k(), y(j(l), {
|
|
230
232
|
key: 0,
|
|
@@ -265,7 +267,7 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
265
267
|
key: 1,
|
|
266
268
|
open: !I.hidden,
|
|
267
269
|
modal: !H.value.clickThrough,
|
|
268
|
-
"onUpdate:open":
|
|
270
|
+
"onUpdate:open": rt
|
|
269
271
|
}, {
|
|
270
272
|
default: N(() => [w(ie, {
|
|
271
273
|
class: D(j(i)("max-h-[calc(100vh-2rem)] overflow-y-auto", F[H.value.width] ?? "sm:max-w-lg", G.value)),
|
|
@@ -300,7 +302,7 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
300
302
|
}))])], 2)]),
|
|
301
303
|
_: 1
|
|
302
304
|
}, 8, ["class"]),
|
|
303
|
-
|
|
305
|
+
it.value ? (k(), x("div", Re, [
|
|
304
306
|
H.value.content ? (k(), y(p, {
|
|
305
307
|
key: 0,
|
|
306
308
|
components: H.value.content
|
|
@@ -354,7 +356,7 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
354
356
|
key: 1,
|
|
355
357
|
type: "button",
|
|
356
358
|
variant: "outline",
|
|
357
|
-
class: D(
|
|
359
|
+
class: D(tt.value),
|
|
358
360
|
disabled: I.modal.processing,
|
|
359
361
|
onClick: Z
|
|
360
362
|
}, {
|
|
@@ -366,9 +368,9 @@ var ke = ["data-alfakit-modal"], Ae = { class: "flex flex-col gap-1.5" }, je = [
|
|
|
366
368
|
type: "button",
|
|
367
369
|
variant: "outline",
|
|
368
370
|
"data-slot": "create-another",
|
|
369
|
-
class: D(
|
|
371
|
+
class: D(nt.value),
|
|
370
372
|
disabled: I.modal.processing,
|
|
371
|
-
onClick:
|
|
373
|
+
onClick: $e
|
|
372
374
|
}, {
|
|
373
375
|
default: N(() => [H.value.createAnotherIcon ? (k(), y(j(l), {
|
|
374
376
|
key: 0,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ActionModal.vue_vue_type_script_setup_true_lang.js","names":["_openBlock","_createBlock","Sheet","_withCtx","_createVNode","SheetContent","_normalizeClass","_unref","_createElementVNode","SheetHeader","_createElementBlock","Icon","_createCommentVNode","SheetTitle","_createTextVNode","_toDisplayString","SheetDescription","SchemaRenderer","Slot","_withModifiers","ActionModalPassword","SheetFooter","ActionList","Button","Spinner","Dialog","DialogContent","DialogHeader","DialogTitle","DialogDescription","DialogFooter","Icon_default","Button_default","Spinner_default","ActionList_default","SchemaRenderer_default","Slot_default","Dialog_default","DialogContent_default","DialogDescription_default","DialogHeader_default","DialogTitle_default","Sheet_default","SheetContent_default","SheetDescription_default","SheetHeader_default","SheetTitle_default","DialogFooter_default","SheetFooter_default","ActionModalPassword_default","_hoisted_1","_hoisted_2","_hoisted_3","_hoisted_4","_hoisted_5","_hoisted_6","_hoisted_7","_hoisted_8","_hoisted_9","_hoisted_10","_hoisted_11","ActionModal_vue_vue_type_script_setup_true_lang_default","WIDTHS","FOOTER_JUSTIFY","props","__props","runner","useActionRunner","panel","usePanel","direction","useDirection","t","useT","action","context","schema","computed","form","FormStore","actionFormComponent","formIdPrefix","notifications","showToast","n","actionFormParams","provideForm","formState","useStore","watch","errors","onScopeDispose","windowClass","windowAttributes","_class","rest","modalId","useId","setAttributes","name","value","attributes","element","applyOverlayAttributes","overlay","onMounted","nextTick","footerJustify","modalFooterAlignment","footerActionsClass","side","slideOverSide","progress","wizardProgressStore","submitVisible","isModalSubmitVisible","password","ref","passwordError","PASSWORD_CONFIRMATION_INPUT","footerContext","nestedActionContext","run","values","options","createAnother","submit","submitAnother","payload","previous","components","refocus","onCleanup","scheduleAutofocus","close","unsavedMessage","requestClose","confirmModalClose","guardModalUnload","cancelClass","colorClass","outlineButtonColorClasses","createAnotherClass","title","onOpenChange","open","hasFooter","hasBody","openBlock","createBlock","withCtx","createVNode","normalizeClass","unref","cn","_cache","event","createElementVNode","createElementBlock","iconBackgroundColorClasses","createCommentVNode","createTextVNode","toDisplayString","withModifiers","$event","solidButtonColorClasses"],"sources":["../../../src/components/actions/ActionModal.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport type { OpenModal } from '@alfakit/core'\nimport {\n actionFormComponent,\n formIdPrefix,\n actionFormParams,\n confirmModalClose,\n FormStore,\n guardModalUnload,\n isModalSubmitVisible,\n modalFooterAlignment,\n nestedActionContext,\n PASSWORD_CONFIRMATION_INPUT,\n scheduleAutofocus,\n slideOverSide,\n wizardProgressStore,\n} from '@alfakit/core'\nimport { computed, nextTick, onMounted, onScopeDispose, ref, useId, watch } from 'vue'\nimport { useStore } from '../../composables/use-store'\nimport { useActionRunner, useDirection, usePanel, useT } from '../../context'\nimport {\n colorClass,\n iconBackgroundColorClasses,\n outlineButtonColorClasses,\n solidButtonColorClasses,\n} from '../../lib/colors'\nimport { Icon } from '../../lib/icons'\nimport { cn } from '../../lib/utils'\nimport { provideForm } from '../form/form-context'\nimport Slot from '../panel/Slot.vue'\nimport SchemaRenderer from '../schema/SchemaRenderer.vue'\nimport Button from '../ui/Button.vue'\nimport Dialog from '../ui/Dialog.vue'\nimport DialogContent from '../ui/DialogContent.vue'\nimport DialogDescription from '../ui/DialogDescription.vue'\nimport DialogFooter from '../ui/DialogFooter.vue'\nimport DialogHeader from '../ui/DialogHeader.vue'\nimport DialogTitle from '../ui/DialogTitle.vue'\nimport Sheet from '../ui/Sheet.vue'\nimport SheetContent from '../ui/SheetContent.vue'\nimport SheetDescription from '../ui/SheetDescription.vue'\nimport SheetFooter from '../ui/SheetFooter.vue'\nimport SheetHeader from '../ui/SheetHeader.vue'\nimport SheetTitle from '../ui/SheetTitle.vue'\nimport Spinner from '../ui/Spinner.vue'\nimport ActionList from './ActionList.vue'\nimport ActionModalPassword from './ActionModalPassword.vue'\nimport { showToast } from '../notifications/flash-toasts'\n\nconst WIDTHS: Record<string, string> = {\n '3xs': 'sm:max-w-3xs',\n '2xs': 'sm:max-w-2xs',\n xs: 'sm:max-w-xs',\n sm: 'sm:max-w-sm',\n md: 'sm:max-w-md',\n lg: 'sm:max-w-lg',\n xl: 'sm:max-w-xl',\n '2xl': 'sm:max-w-2xl',\n '3xl': 'sm:max-w-3xl',\n '4xl': 'sm:max-w-4xl',\n '5xl': 'sm:max-w-5xl',\n '6xl': 'sm:max-w-6xl',\n '7xl': 'sm:max-w-7xl',\n none: 'sm:max-w-none',\n min: 'sm:max-w-min',\n max: 'sm:max-w-max',\n fit: 'sm:max-w-fit',\n prose: 'sm:max-w-prose',\n container: 'sm:container',\n 'screen-sm': 'sm:max-w-(--breakpoint-sm)',\n 'screen-md': 'sm:max-w-(--breakpoint-md)',\n 'screen-lg': 'sm:max-w-(--breakpoint-lg)',\n 'screen-xl': 'sm:max-w-(--breakpoint-xl)',\n 'screen-2xl': 'sm:max-w-(--breakpoint-2xl)',\n full: 'sm:max-w-[calc(100%-2rem)]',\n screen: 'sm:max-w-[calc(100%-2rem)] h-[calc(100%-2rem)]',\n}\n\nconst FOOTER_JUSTIFY: Record<string, string> = {\n start: 'sm:justify-start',\n center: 'sm:justify-center',\n end: 'sm:justify-end',\n between: 'sm:justify-between',\n}\n\nconst props = withDefaults(defineProps<{ modal: OpenModal; hidden?: boolean }>(), {\n hidden: false,\n})\n\nconst runner = useActionRunner()\nconst panel = usePanel()\nconst direction = useDirection()\nconst t = useT()\n\nconst action = props.modal.action\nconst context = props.modal.context\nconst schema = computed(() => props.modal.modal)\n\nconst form = (() => {\n if (!schema.value.form) {\n return null\n }\n\n return new FormStore(schema.value.form, {\n token: context.token,\n component: actionFormComponent(action, context),\n // Own field ids: the modal opens over a form whose fields may share names.\n idPrefix: formIdPrefix(actionFormComponent(action, context)),\n record: context.record ?? null,\n refreshUrl: panel.value.endpoints.schemaRefresh,\n optionsUrl: panel.value.endpoints.schemaOptions,\n validateUrl: panel.value.endpoints.schemaValidate,\n // A halted wizard step shows what its hook sent.\n onNotifications: (notifications) => notifications.forEach((n) => showToast(n)),\n params: actionFormParams(context),\n })\n})()\n\nif (form) {\n provideForm(form)\n}\n\nconst formState = form ? useStore(form.store) : null\n\nwatch(\n () => props.modal.errors,\n (errors) => form?.setErrors(errors),\n { immediate: true },\n)\n\nonScopeDispose(() => form?.destroy())\n\n// Nested actions read this form (`$mountedActions`, `getRawData()`) and write into it\n// (`fillData()`).\nif (form) {\n onScopeDispose(runner.registerModalForm(action, context, form))\n}\n\n// `extraModalWindowAttributes()`: `class` joins the window's classes.\nconst windowClass = computed(() => schema.value.windowAttributes?.class as string | undefined)\nconst windowAttributes = computed(() => {\n const { class: _class, ...rest } = schema.value.windowAttributes ?? {}\n\n return rest\n})\n\n// `extraModalOverlayAttributes()`: the backdrop is the content's previous sibling.\nconst modalId = useId()\n\n// A marker inside the content finds the window and its backdrop (the dialog primitives\n// render through a portal and don't pass other attributes on).\nconst setAttributes = (element: Element, attributes: Record<string, unknown>) => {\n for (const [name, value] of Object.entries(attributes)) {\n if (value === null || value === undefined || value === false) continue\n\n if (name === 'class') {\n element.classList.add(...String(value).split(/\\s+/).filter(Boolean))\n } else {\n element.setAttribute(name, value === true ? '' : String(value))\n }\n }\n}\n\nconst applyOverlayAttributes = () => {\n if (props.hidden || typeof document === 'undefined') return\n\n const element = document\n .querySelector(`[data-alfakit-modal=\"${modalId}\"]`)\n ?.closest('[role=\"dialog\"]')\n const overlay = element?.previousElementSibling\n\n if (element) setAttributes(element, windowAttributes.value)\n\n if (overlay?.getAttribute('data-slot')?.endsWith('-overlay') && schema.value.overlayAttributes) {\n setAttributes(overlay, schema.value.overlayAttributes)\n }\n}\n\nonMounted(() => void nextTick(applyOverlayAttributes))\nwatch(\n () => props.hidden,\n () => void nextTick(applyOverlayAttributes),\n { flush: 'post' },\n)\n\nconst footerJustify = computed(() => FOOTER_JUSTIFY[modalFooterAlignment(schema.value)])\nconst footerActionsClass = computed(() =>\n modalFooterAlignment(schema.value) === 'end' ? 'sm:me-auto' : undefined,\n)\nconst side = computed(() => slideOverSide(schema.value.slideOverPosition, direction.value))\n\n// A wizard form reports its step, so the submit button waits for the last one.\nconst progress = form ? useStore(wizardProgressStore(form)) : null\nconst submitVisible = computed(() => isModalSubmitVisible(schema.value, progress?.value))\n\nconst password = ref('')\nconst passwordError = computed(() => props.modal.errors[PASSWORD_CONFIRMATION_INPUT]?.[0])\nconst footerContext = nestedActionContext(context, action)\n\nconst run = (createAnother: boolean) => {\n const values = form?.state.values ?? {}\n const options = {\n ...(schema.value.passwordConfirmation ? { password: password.value } : {}),\n ...(createAnother ? { createAnother: true } : {}),\n }\n\n if (Object.keys(options).length > 0) {\n runner.execute(action, context, values, options)\n } else {\n runner.execute(action, context, values)\n }\n}\nconst submit = () => run(false)\n// \"Create & create another\": the runner reloads the modal, and its fresh form fills this one.\nconst submitAnother = () => run(true)\n\nwatch(\n () => schema.value.form,\n (payload, previous) => {\n if (payload && payload !== previous) form?.fill(payload)\n },\n)\n\n// \"Create & create another\": back to the `autofocus()` field of the fresh form.\nwatch(\n () => props.modal.refocus,\n (refocus, _previous, onCleanup) => {\n const components = schema.value.form?.components\n\n if (!refocus || !components) return\n\n onCleanup(\n scheduleAutofocus(() => document.getElementById(`action-form-${action.name}`), components),\n )\n },\n)\n\n// Dismissing the modal (not submitting it): `cancelParentActionsOnClose()` applies.\nconst close = () => runner.cancelModal(action.name)\nconst unsavedMessage = t('unsaved_changes_close', {}, 'You have unsaved changes. Close anyway?')\n// Cancel, Escape, clicking away and the close button ask first when the form changed.\nconst requestClose = () => {\n if (confirmModalClose(schema.value, form, unsavedMessage)) close()\n}\nonScopeDispose(guardModalUnload(schema.value, form, unsavedMessage))\nconst cancelClass = computed(() =>\n schema.value.cancelColor ? colorClass(outlineButtonColorClasses, schema.value.cancelColor) : '',\n)\n// `createAnotherAction()`: the \"Create & create another\" button's colour.\nconst createAnotherClass = computed(() =>\n schema.value.createAnotherColor\n ? colorClass(outlineButtonColorClasses, schema.value.createAnotherColor)\n : '',\n)\n// Every dialog needs an accessible name: without a heading it stays visually hidden.\nconst title = computed(() => schema.value.heading ?? action.label ?? t('actions', {}, 'Actions'))\n\nconst onOpenChange = (open: boolean) => {\n if (!open && !props.modal.processing) {\n requestClose()\n }\n}\n\nconst hasFooter = computed(() =>\n Boolean(\n schema.value.submitLabel || schema.value.cancelLabel || schema.value.extraFooterActions?.length,\n ),\n)\nconst hasBody = computed(() =>\n Boolean(\n schema.value.content || form || schema.value.contentFooter || schema.value.passwordConfirmation,\n ),\n)\n</script>\n\n<template>\n <Sheet\n v-if=\"schema.slideOver\"\n :open=\"!props.hidden\"\n :modal=\"!schema.clickThrough\"\n @update:open=\"onOpenChange\"\n >\n <SheetContent\n :side=\"side\"\n :class=\"\n cn('flex w-full flex-col gap-0 p-0', WIDTHS[schema.width] ?? 'sm:max-w-md', windowClass)\n \"\n :show-close-button=\"schema.closeButton\"\n @interact-outside=\"(event) => !schema.closeByClickingAway && event.preventDefault()\"\n @escape-key-down=\"(event) => !schema.closeByEscaping && event.preventDefault()\"\n >\n <span :data-alfakit-modal=\"modalId\" hidden />\n <SheetHeader class=\"border-b\">\n <div\n :class=\"\n cn('flex gap-4', schema.alignment === 'center' && 'flex-col items-center text-center')\n \"\n >\n <div\n v-if=\"schema.icon\"\n :class=\"\n cn(\n 'flex size-10 shrink-0 items-center justify-center rounded-full',\n colorClass(iconBackgroundColorClasses, schema.iconColor, 'primary'),\n )\n \"\n >\n <Icon :name=\"schema.icon\" class=\"size-5\" />\n </div>\n <div class=\"flex flex-col gap-1.5\">\n <SheetTitle :class=\"cn(!schema.heading && 'sr-only')\">{{ title }}</SheetTitle>\n <SheetDescription v-if=\"schema.description\"\n ><span v-html=\"schema.description\"\n /></SheetDescription>\n <SheetDescription v-else class=\"sr-only\">{{ title }}</SheetDescription>\n </div>\n </div>\n </SheetHeader>\n <div class=\"flex-1 overflow-y-auto p-4\">\n <div class=\"flex flex-col gap-6\">\n <SchemaRenderer v-if=\"schema.content\" :components=\"schema.content\" />\n <Slot\n v-if=\"form && formState\"\n name=\"modal.schema.before\"\n :data=\"{ action: action.name }\"\n />\n <form\n v-if=\"form && formState\"\n :id=\"`action-form-${action.name}`\"\n @submit.prevent=\"submit\"\n >\n <SchemaRenderer :components=\"formState.components\" :columns=\"formState.columns\" />\n </form>\n <Slot\n v-if=\"form && formState\"\n name=\"modal.schema.after\"\n :data=\"{ action: action.name }\"\n />\n <SchemaRenderer v-if=\"schema.contentFooter\" :components=\"schema.contentFooter\" />\n <ActionModalPassword\n v-if=\"schema.passwordConfirmation\"\n v-model=\"password\"\n :error=\"passwordError\"\n @submit=\"submit\"\n />\n </div>\n </div>\n <SheetFooter\n v-if=\"hasFooter\"\n :class=\"cn('border-t', schema.stickyFooter && 'bg-background sticky bottom-0')\"\n >\n <div\n :class=\"\n cn('flex w-full flex-col-reverse gap-2 sm:flex-row sm:items-center', footerJustify)\n \"\n >\n <ActionList\n v-if=\"schema.extraFooterActions\"\n :actions=\"schema.extraFooterActions\"\n :context=\"footerContext\"\n :class=\"footerActionsClass\"\n />\n <Button\n v-if=\"schema.cancelLabel\"\n type=\"button\"\n variant=\"outline\"\n :class=\"cancelClass\"\n :disabled=\"props.modal.processing\"\n @click=\"requestClose\"\n >{{ schema.cancelLabel }}</Button\n >\n <Button\n v-if=\"schema.createAnotherLabel && schema.submitLabel && submitVisible\"\n type=\"button\"\n variant=\"outline\"\n data-slot=\"create-another\"\n :class=\"createAnotherClass\"\n :disabled=\"props.modal.processing\"\n @click=\"submitAnother\"\n ><Icon v-if=\"schema.createAnotherIcon\" :name=\"schema.createAnotherIcon\" />{{\n schema.createAnotherLabel\n }}</Button\n >\n <Button\n v-if=\"schema.submitLabel && submitVisible\"\n type=\"button\"\n :class=\"colorClass(solidButtonColorClasses, schema.submitColor, 'primary')\"\n :disabled=\"props.modal.processing\"\n :autofocus=\"schema.autofocus && !form\"\n @click=\"submit\"\n >\n <Spinner v-if=\"props.modal.processing\" />\n <Icon v-else-if=\"schema.submitIcon\" :name=\"schema.submitIcon\" />\n {{ schema.submitLabel }}\n </Button>\n </div>\n </SheetFooter>\n </SheetContent>\n </Sheet>\n <Dialog v-else :open=\"!props.hidden\" :modal=\"!schema.clickThrough\" @update:open=\"onOpenChange\">\n <DialogContent\n :class=\"\n cn(\n 'max-h-[calc(100vh-2rem)] overflow-y-auto',\n WIDTHS[schema.width] ?? 'sm:max-w-lg',\n windowClass,\n )\n \"\n :show-close-button=\"schema.closeButton\"\n @interact-outside=\"(event) => !schema.closeByClickingAway && event.preventDefault()\"\n @escape-key-down=\"(event) => !schema.closeByEscaping && event.preventDefault()\"\n >\n <span :data-alfakit-modal=\"modalId\" hidden />\n <!-- A sticky header stays pinned to the top of the scrolling dialog, edge to edge. -->\n <DialogHeader\n :class=\"\n cn(\n schema.stickyHeader &&\n 'bg-background sticky -top-6 z-10 -mx-6 -mt-6 rounded-t-lg border-b px-6 pt-6 pb-4',\n )\n \"\n >\n <div\n :class=\"\n cn('flex gap-4', schema.alignment === 'center' && 'flex-col items-center text-center')\n \"\n >\n <div\n v-if=\"schema.icon\"\n :class=\"\n cn(\n 'flex size-10 shrink-0 items-center justify-center rounded-full',\n colorClass(iconBackgroundColorClasses, schema.iconColor, 'primary'),\n )\n \"\n >\n <Icon :name=\"schema.icon\" class=\"size-5\" />\n </div>\n <div class=\"flex flex-col gap-1.5\">\n <DialogTitle :class=\"cn(!schema.heading && 'sr-only')\">{{ title }}</DialogTitle>\n <DialogDescription v-if=\"schema.description\"\n ><span v-html=\"schema.description\"\n /></DialogDescription>\n <DialogDescription v-else class=\"sr-only\">{{ title }}</DialogDescription>\n </div>\n </div>\n </DialogHeader>\n <div v-if=\"hasBody\" class=\"flex flex-col gap-6\">\n <SchemaRenderer v-if=\"schema.content\" :components=\"schema.content\" />\n <Slot v-if=\"form && formState\" name=\"modal.schema.before\" :data=\"{ action: action.name }\" />\n <form v-if=\"form && formState\" :id=\"`action-form-${action.name}`\" @submit.prevent=\"submit\">\n <SchemaRenderer :components=\"formState.components\" :columns=\"formState.columns\" />\n </form>\n <Slot v-if=\"form && formState\" name=\"modal.schema.after\" :data=\"{ action: action.name }\" />\n <SchemaRenderer v-if=\"schema.contentFooter\" :components=\"schema.contentFooter\" />\n <ActionModalPassword\n v-if=\"schema.passwordConfirmation\"\n v-model=\"password\"\n :error=\"passwordError\"\n @submit=\"submit\"\n />\n </div>\n <!-- A sticky footer stays pinned to the bottom of the scrolling dialog, edge to edge. -->\n <DialogFooter\n v-if=\"hasFooter\"\n :class=\"\n cn(\n schema.stickyFooter &&\n 'bg-background sticky bottom-0 -mx-6 -mb-6 rounded-b-lg border-t px-6 py-4',\n )\n \"\n >\n <div\n :class=\"\n cn('flex w-full flex-col-reverse gap-2 sm:flex-row sm:items-center', footerJustify)\n \"\n >\n <ActionList\n v-if=\"schema.extraFooterActions\"\n :actions=\"schema.extraFooterActions\"\n :context=\"footerContext\"\n :class=\"footerActionsClass\"\n />\n <Button\n v-if=\"schema.cancelLabel\"\n type=\"button\"\n variant=\"outline\"\n :class=\"cancelClass\"\n :disabled=\"props.modal.processing\"\n @click=\"requestClose\"\n >{{ schema.cancelLabel }}</Button\n >\n <Button\n v-if=\"schema.createAnotherLabel && schema.submitLabel && submitVisible\"\n type=\"button\"\n variant=\"outline\"\n data-slot=\"create-another\"\n :class=\"createAnotherClass\"\n :disabled=\"props.modal.processing\"\n @click=\"submitAnother\"\n ><Icon v-if=\"schema.createAnotherIcon\" :name=\"schema.createAnotherIcon\" />{{\n schema.createAnotherLabel\n }}</Button\n >\n <Button\n v-if=\"schema.submitLabel && submitVisible\"\n type=\"button\"\n :class=\"colorClass(solidButtonColorClasses, schema.submitColor, 'primary')\"\n :disabled=\"props.modal.processing\"\n :autofocus=\"schema.autofocus && !form\"\n @click=\"submit\"\n >\n <Spinner v-if=\"props.modal.processing\" />\n <Icon v-else-if=\"schema.submitIcon\" :name=\"schema.submitIcon\" />\n {{ schema.submitLabel }}\n </Button>\n </div>\n </DialogFooter>\n </DialogContent>\n </Dialog>\n</template>\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"ActionModal.vue_vue_type_script_setup_true_lang.js","names":["_openBlock","_createBlock","Sheet","_withCtx","_createVNode","SheetContent","_normalizeClass","_unref","_createElementVNode","SheetHeader","_createElementBlock","Icon","_createCommentVNode","SheetTitle","_createTextVNode","_toDisplayString","SheetDescription","SchemaRenderer","Slot","_withModifiers","ActionModalPassword","SheetFooter","ActionList","Button","Spinner","Dialog","DialogContent","DialogHeader","DialogTitle","DialogDescription","DialogFooter","Icon_default","Button_default","Spinner_default","ActionList_default","SchemaRenderer_default","Slot_default","Dialog_default","DialogContent_default","DialogDescription_default","DialogHeader_default","DialogTitle_default","Sheet_default","SheetContent_default","SheetDescription_default","SheetHeader_default","SheetTitle_default","DialogFooter_default","SheetFooter_default","ActionModalPassword_default","_hoisted_1","_hoisted_2","_hoisted_3","_hoisted_4","_hoisted_5","_hoisted_6","_hoisted_7","_hoisted_8","_hoisted_9","_hoisted_10","_hoisted_11","ActionModal_vue_vue_type_script_setup_true_lang_default","WIDTHS","FOOTER_JUSTIFY","props","__props","runner","useActionRunner","panel","usePanel","direction","useDirection","t","useT","action","context","schema","computed","form","FormStore","actionFormComponent","formIdPrefix","notifications","showToast","n","actionFormParams","provideForm","formState","useStore","watch","errors","onScopeDispose","windowClass","windowAttributes","_class","rest","modalId","useId","setAttributes","name","value","attributes","element","applyOverlayAttributes","overlay","onMounted","nextTick","footerJustify","modalFooterAlignment","footerActionsClass","side","slideOverSide","progress","wizardProgressStore","submitVisible","isModalSubmitVisible","password","ref","passwordError","PASSWORD_CONFIRMATION_INPUT","footerContext","nestedActionContext","run","execute","createAnother","values","options","submit","submitAnother","payload","previous","components","refocus","onCleanup","scheduleAutofocus","close","unsavedMessage","requestClose","confirmModalClose","guardModalUnload","cancelClass","colorClass","outlineButtonColorClasses","createAnotherClass","title","onOpenChange","open","hasFooter","hasBody","openBlock","createBlock","withCtx","createVNode","normalizeClass","unref","cn","_cache","event","createElementVNode","createElementBlock","iconBackgroundColorClasses","createCommentVNode","createTextVNode","toDisplayString","withModifiers","$event","solidButtonColorClasses"],"sources":["../../../src/components/actions/ActionModal.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport type { OpenModal } from '@alfakit/core'\nimport {\n actionFormComponent,\n formIdPrefix,\n actionFormParams,\n confirmModalClose,\n FormStore,\n guardModalUnload,\n isModalSubmitVisible,\n modalFooterAlignment,\n nestedActionContext,\n PASSWORD_CONFIRMATION_INPUT,\n scheduleAutofocus,\n slideOverSide,\n wizardProgressStore,\n} from '@alfakit/core'\nimport { computed, nextTick, onMounted, onScopeDispose, ref, useId, watch } from 'vue'\nimport { useStore } from '../../composables/use-store'\nimport { useActionRunner, useDirection, usePanel, useT } from '../../context'\nimport {\n colorClass,\n iconBackgroundColorClasses,\n outlineButtonColorClasses,\n solidButtonColorClasses,\n} from '../../lib/colors'\nimport { Icon } from '../../lib/icons'\nimport { cn } from '../../lib/utils'\nimport { provideForm } from '../form/form-context'\nimport Slot from '../panel/Slot.vue'\nimport SchemaRenderer from '../schema/SchemaRenderer.vue'\nimport Button from '../ui/Button.vue'\nimport Dialog from '../ui/Dialog.vue'\nimport DialogContent from '../ui/DialogContent.vue'\nimport DialogDescription from '../ui/DialogDescription.vue'\nimport DialogFooter from '../ui/DialogFooter.vue'\nimport DialogHeader from '../ui/DialogHeader.vue'\nimport DialogTitle from '../ui/DialogTitle.vue'\nimport Sheet from '../ui/Sheet.vue'\nimport SheetContent from '../ui/SheetContent.vue'\nimport SheetDescription from '../ui/SheetDescription.vue'\nimport SheetFooter from '../ui/SheetFooter.vue'\nimport SheetHeader from '../ui/SheetHeader.vue'\nimport SheetTitle from '../ui/SheetTitle.vue'\nimport Spinner from '../ui/Spinner.vue'\nimport ActionList from './ActionList.vue'\nimport ActionModalPassword from './ActionModalPassword.vue'\nimport { showToast } from '../notifications/flash-toasts'\n\nconst WIDTHS: Record<string, string> = {\n '3xs': 'sm:max-w-3xs',\n '2xs': 'sm:max-w-2xs',\n xs: 'sm:max-w-xs',\n sm: 'sm:max-w-sm',\n md: 'sm:max-w-md',\n lg: 'sm:max-w-lg',\n xl: 'sm:max-w-xl',\n '2xl': 'sm:max-w-2xl',\n '3xl': 'sm:max-w-3xl',\n '4xl': 'sm:max-w-4xl',\n '5xl': 'sm:max-w-5xl',\n '6xl': 'sm:max-w-6xl',\n '7xl': 'sm:max-w-7xl',\n none: 'sm:max-w-none',\n min: 'sm:max-w-min',\n max: 'sm:max-w-max',\n fit: 'sm:max-w-fit',\n prose: 'sm:max-w-prose',\n container: 'sm:container',\n 'screen-sm': 'sm:max-w-(--breakpoint-sm)',\n 'screen-md': 'sm:max-w-(--breakpoint-md)',\n 'screen-lg': 'sm:max-w-(--breakpoint-lg)',\n 'screen-xl': 'sm:max-w-(--breakpoint-xl)',\n 'screen-2xl': 'sm:max-w-(--breakpoint-2xl)',\n full: 'sm:max-w-[calc(100%-2rem)]',\n screen: 'sm:max-w-[calc(100%-2rem)] h-[calc(100%-2rem)]',\n}\n\nconst FOOTER_JUSTIFY: Record<string, string> = {\n start: 'sm:justify-start',\n center: 'sm:justify-center',\n end: 'sm:justify-end',\n between: 'sm:justify-between',\n}\n\nconst props = withDefaults(defineProps<{ modal: OpenModal; hidden?: boolean }>(), {\n hidden: false,\n})\n\nconst runner = useActionRunner()\nconst panel = usePanel()\nconst direction = useDirection()\nconst t = useT()\n\nconst action = props.modal.action\nconst context = props.modal.context\nconst schema = computed(() => props.modal.modal)\n\nconst form = (() => {\n if (!schema.value.form) {\n return null\n }\n\n return new FormStore(schema.value.form, {\n token: context.token,\n component: actionFormComponent(action, context),\n // Own field ids: the modal opens over a form whose fields may share names.\n idPrefix: formIdPrefix(actionFormComponent(action, context)),\n record: context.record ?? null,\n refreshUrl: panel.value.endpoints.schemaRefresh,\n optionsUrl: panel.value.endpoints.schemaOptions,\n validateUrl: panel.value.endpoints.schemaValidate,\n // A halted wizard step shows what its hook sent.\n onNotifications: (notifications) => notifications.forEach((n) => showToast(n)),\n params: actionFormParams(context),\n })\n})()\n\nif (form) {\n provideForm(form)\n}\n\nconst formState = form ? useStore(form.store) : null\n\nwatch(\n () => props.modal.errors,\n (errors) => form?.setErrors(errors),\n { immediate: true },\n)\n\nonScopeDispose(() => form?.destroy())\n\n// Nested actions read this form (`$mountedActions`, `getRawData()`) and write into it\n// (`fillData()`).\nif (form) {\n onScopeDispose(runner.registerModalForm(action, context, form))\n}\n\n// `extraModalWindowAttributes()`: `class` joins the window's classes.\nconst windowClass = computed(() => schema.value.windowAttributes?.class as string | undefined)\nconst windowAttributes = computed(() => {\n const { class: _class, ...rest } = schema.value.windowAttributes ?? {}\n\n return rest\n})\n\n// `extraModalOverlayAttributes()`: the backdrop is the content's previous sibling.\nconst modalId = useId()\n\n// A marker inside the content finds the window and its backdrop (the dialog primitives\n// render through a portal and don't pass other attributes on).\nconst setAttributes = (element: Element, attributes: Record<string, unknown>) => {\n for (const [name, value] of Object.entries(attributes)) {\n if (value === null || value === undefined || value === false) continue\n\n if (name === 'class') {\n element.classList.add(...String(value).split(/\\s+/).filter(Boolean))\n } else {\n element.setAttribute(name, value === true ? '' : String(value))\n }\n }\n}\n\nconst applyOverlayAttributes = () => {\n if (props.hidden || typeof document === 'undefined') return\n\n const element = document\n .querySelector(`[data-alfakit-modal=\"${modalId}\"]`)\n ?.closest('[role=\"dialog\"]')\n const overlay = element?.previousElementSibling\n\n if (element) setAttributes(element, windowAttributes.value)\n\n if (overlay?.getAttribute('data-slot')?.endsWith('-overlay') && schema.value.overlayAttributes) {\n setAttributes(overlay, schema.value.overlayAttributes)\n }\n}\n\nonMounted(() => void nextTick(applyOverlayAttributes))\nwatch(\n () => props.hidden,\n () => void nextTick(applyOverlayAttributes),\n { flush: 'post' },\n)\n\nconst footerJustify = computed(() => FOOTER_JUSTIFY[modalFooterAlignment(schema.value)])\nconst footerActionsClass = computed(() =>\n modalFooterAlignment(schema.value) === 'end' ? 'sm:me-auto' : undefined,\n)\nconst side = computed(() => slideOverSide(schema.value.slideOverPosition, direction.value))\n\n// A wizard form reports its step, so the submit button waits for the last one.\nconst progress = form ? useStore(wizardProgressStore(form)) : null\nconst submitVisible = computed(() => isModalSubmitVisible(schema.value, progress?.value))\n\nconst password = ref('')\nconst passwordError = computed(() => props.modal.errors[PASSWORD_CONFIRMATION_INPUT]?.[0])\nconst footerContext = nestedActionContext(context, action)\n\nconst run = (createAnother: boolean) => {\n // A click that blurred a live field started a refresh: send the state it returns.\n if (form) {\n form.whenSettled(() => execute(createAnother))\n } else {\n execute(createAnother)\n }\n}\n\nconst execute = (createAnother: boolean) => {\n const values = form?.state.values ?? {}\n const options = {\n ...(schema.value.passwordConfirmation ? { password: password.value } : {}),\n ...(createAnother ? { createAnother: true } : {}),\n }\n\n if (Object.keys(options).length > 0) {\n runner.execute(action, context, values, options)\n } else {\n runner.execute(action, context, values)\n }\n}\nconst submit = () => run(false)\n// \"Create & create another\": the runner reloads the modal, and its fresh form fills this one.\nconst submitAnother = () => run(true)\n\nwatch(\n () => schema.value.form,\n (payload, previous) => {\n if (payload && payload !== previous) form?.fill(payload)\n },\n)\n\n// \"Create & create another\": back to the `autofocus()` field of the fresh form.\nwatch(\n () => props.modal.refocus,\n (refocus, _previous, onCleanup) => {\n const components = schema.value.form?.components\n\n if (!refocus || !components) return\n\n onCleanup(\n scheduleAutofocus(() => document.getElementById(`action-form-${action.name}`), components),\n )\n },\n)\n\n// Dismissing the modal (not submitting it): `cancelParentActionsOnClose()` applies.\nconst close = () => runner.cancelModal(action.name)\nconst unsavedMessage = t('unsaved_changes_close', {}, 'You have unsaved changes. Close anyway?')\n// Cancel, Escape, clicking away and the close button ask first when the form changed.\nconst requestClose = () => {\n if (confirmModalClose(schema.value, form, unsavedMessage)) close()\n}\nonScopeDispose(guardModalUnload(schema.value, form, unsavedMessage))\nconst cancelClass = computed(() =>\n schema.value.cancelColor ? colorClass(outlineButtonColorClasses, schema.value.cancelColor) : '',\n)\n// `createAnotherAction()`: the \"Create & create another\" button's colour.\nconst createAnotherClass = computed(() =>\n schema.value.createAnotherColor\n ? colorClass(outlineButtonColorClasses, schema.value.createAnotherColor)\n : '',\n)\n// Every dialog needs an accessible name: without a heading it stays visually hidden.\nconst title = computed(() => schema.value.heading ?? action.label ?? t('actions', {}, 'Actions'))\n\nconst onOpenChange = (open: boolean) => {\n if (!open && !props.modal.processing) {\n requestClose()\n }\n}\n\nconst hasFooter = computed(() =>\n Boolean(\n schema.value.submitLabel || schema.value.cancelLabel || schema.value.extraFooterActions?.length,\n ),\n)\nconst hasBody = computed(() =>\n Boolean(\n schema.value.content || form || schema.value.contentFooter || schema.value.passwordConfirmation,\n ),\n)\n</script>\n\n<template>\n <Sheet\n v-if=\"schema.slideOver\"\n :open=\"!props.hidden\"\n :modal=\"!schema.clickThrough\"\n @update:open=\"onOpenChange\"\n >\n <SheetContent\n :side=\"side\"\n :class=\"\n cn('flex w-full flex-col gap-0 p-0', WIDTHS[schema.width] ?? 'sm:max-w-md', windowClass)\n \"\n :show-close-button=\"schema.closeButton\"\n @interact-outside=\"(event) => !schema.closeByClickingAway && event.preventDefault()\"\n @escape-key-down=\"(event) => !schema.closeByEscaping && event.preventDefault()\"\n >\n <span :data-alfakit-modal=\"modalId\" hidden />\n <SheetHeader class=\"border-b\">\n <div\n :class=\"\n cn('flex gap-4', schema.alignment === 'center' && 'flex-col items-center text-center')\n \"\n >\n <div\n v-if=\"schema.icon\"\n :class=\"\n cn(\n 'flex size-10 shrink-0 items-center justify-center rounded-full',\n colorClass(iconBackgroundColorClasses, schema.iconColor, 'primary'),\n )\n \"\n >\n <Icon :name=\"schema.icon\" class=\"size-5\" />\n </div>\n <div class=\"flex flex-col gap-1.5\">\n <SheetTitle :class=\"cn(!schema.heading && 'sr-only')\">{{ title }}</SheetTitle>\n <SheetDescription v-if=\"schema.description\"\n ><span v-html=\"schema.description\"\n /></SheetDescription>\n <SheetDescription v-else class=\"sr-only\">{{ title }}</SheetDescription>\n </div>\n </div>\n </SheetHeader>\n <div class=\"flex-1 overflow-y-auto p-4\">\n <div class=\"flex flex-col gap-6\">\n <SchemaRenderer v-if=\"schema.content\" :components=\"schema.content\" />\n <Slot\n v-if=\"form && formState\"\n name=\"modal.schema.before\"\n :data=\"{ action: action.name }\"\n />\n <form\n v-if=\"form && formState\"\n :id=\"`action-form-${action.name}`\"\n @submit.prevent=\"submit\"\n >\n <SchemaRenderer :components=\"formState.components\" :columns=\"formState.columns\" />\n </form>\n <Slot\n v-if=\"form && formState\"\n name=\"modal.schema.after\"\n :data=\"{ action: action.name }\"\n />\n <SchemaRenderer v-if=\"schema.contentFooter\" :components=\"schema.contentFooter\" />\n <ActionModalPassword\n v-if=\"schema.passwordConfirmation\"\n v-model=\"password\"\n :error=\"passwordError\"\n @submit=\"submit\"\n />\n </div>\n </div>\n <SheetFooter\n v-if=\"hasFooter\"\n :class=\"cn('border-t', schema.stickyFooter && 'bg-background sticky bottom-0')\"\n >\n <div\n :class=\"\n cn('flex w-full flex-col-reverse gap-2 sm:flex-row sm:items-center', footerJustify)\n \"\n >\n <ActionList\n v-if=\"schema.extraFooterActions\"\n :actions=\"schema.extraFooterActions\"\n :context=\"footerContext\"\n :class=\"footerActionsClass\"\n />\n <Button\n v-if=\"schema.cancelLabel\"\n type=\"button\"\n variant=\"outline\"\n :class=\"cancelClass\"\n :disabled=\"props.modal.processing\"\n @click=\"requestClose\"\n >{{ schema.cancelLabel }}</Button\n >\n <Button\n v-if=\"schema.createAnotherLabel && schema.submitLabel && submitVisible\"\n type=\"button\"\n variant=\"outline\"\n data-slot=\"create-another\"\n :class=\"createAnotherClass\"\n :disabled=\"props.modal.processing\"\n @click=\"submitAnother\"\n ><Icon v-if=\"schema.createAnotherIcon\" :name=\"schema.createAnotherIcon\" />{{\n schema.createAnotherLabel\n }}</Button\n >\n <Button\n v-if=\"schema.submitLabel && submitVisible\"\n type=\"button\"\n :class=\"colorClass(solidButtonColorClasses, schema.submitColor, 'primary')\"\n :disabled=\"props.modal.processing\"\n :autofocus=\"schema.autofocus && !form\"\n @click=\"submit\"\n >\n <Spinner v-if=\"props.modal.processing\" />\n <Icon v-else-if=\"schema.submitIcon\" :name=\"schema.submitIcon\" />\n {{ schema.submitLabel }}\n </Button>\n </div>\n </SheetFooter>\n </SheetContent>\n </Sheet>\n <Dialog v-else :open=\"!props.hidden\" :modal=\"!schema.clickThrough\" @update:open=\"onOpenChange\">\n <DialogContent\n :class=\"\n cn(\n 'max-h-[calc(100vh-2rem)] overflow-y-auto',\n WIDTHS[schema.width] ?? 'sm:max-w-lg',\n windowClass,\n )\n \"\n :show-close-button=\"schema.closeButton\"\n @interact-outside=\"(event) => !schema.closeByClickingAway && event.preventDefault()\"\n @escape-key-down=\"(event) => !schema.closeByEscaping && event.preventDefault()\"\n >\n <span :data-alfakit-modal=\"modalId\" hidden />\n <!-- A sticky header stays pinned to the top of the scrolling dialog, edge to edge. -->\n <DialogHeader\n :class=\"\n cn(\n schema.stickyHeader &&\n 'bg-background sticky -top-6 z-10 -mx-6 -mt-6 rounded-t-lg border-b px-6 pt-6 pb-4',\n )\n \"\n >\n <div\n :class=\"\n cn('flex gap-4', schema.alignment === 'center' && 'flex-col items-center text-center')\n \"\n >\n <div\n v-if=\"schema.icon\"\n :class=\"\n cn(\n 'flex size-10 shrink-0 items-center justify-center rounded-full',\n colorClass(iconBackgroundColorClasses, schema.iconColor, 'primary'),\n )\n \"\n >\n <Icon :name=\"schema.icon\" class=\"size-5\" />\n </div>\n <div class=\"flex flex-col gap-1.5\">\n <DialogTitle :class=\"cn(!schema.heading && 'sr-only')\">{{ title }}</DialogTitle>\n <DialogDescription v-if=\"schema.description\"\n ><span v-html=\"schema.description\"\n /></DialogDescription>\n <DialogDescription v-else class=\"sr-only\">{{ title }}</DialogDescription>\n </div>\n </div>\n </DialogHeader>\n <div v-if=\"hasBody\" class=\"flex flex-col gap-6\">\n <SchemaRenderer v-if=\"schema.content\" :components=\"schema.content\" />\n <Slot v-if=\"form && formState\" name=\"modal.schema.before\" :data=\"{ action: action.name }\" />\n <form v-if=\"form && formState\" :id=\"`action-form-${action.name}`\" @submit.prevent=\"submit\">\n <SchemaRenderer :components=\"formState.components\" :columns=\"formState.columns\" />\n </form>\n <Slot v-if=\"form && formState\" name=\"modal.schema.after\" :data=\"{ action: action.name }\" />\n <SchemaRenderer v-if=\"schema.contentFooter\" :components=\"schema.contentFooter\" />\n <ActionModalPassword\n v-if=\"schema.passwordConfirmation\"\n v-model=\"password\"\n :error=\"passwordError\"\n @submit=\"submit\"\n />\n </div>\n <!-- A sticky footer stays pinned to the bottom of the scrolling dialog, edge to edge. -->\n <DialogFooter\n v-if=\"hasFooter\"\n :class=\"\n cn(\n schema.stickyFooter &&\n 'bg-background sticky bottom-0 -mx-6 -mb-6 rounded-b-lg border-t px-6 py-4',\n )\n \"\n >\n <div\n :class=\"\n cn('flex w-full flex-col-reverse gap-2 sm:flex-row sm:items-center', footerJustify)\n \"\n >\n <ActionList\n v-if=\"schema.extraFooterActions\"\n :actions=\"schema.extraFooterActions\"\n :context=\"footerContext\"\n :class=\"footerActionsClass\"\n />\n <Button\n v-if=\"schema.cancelLabel\"\n type=\"button\"\n variant=\"outline\"\n :class=\"cancelClass\"\n :disabled=\"props.modal.processing\"\n @click=\"requestClose\"\n >{{ schema.cancelLabel }}</Button\n >\n <Button\n v-if=\"schema.createAnotherLabel && schema.submitLabel && submitVisible\"\n type=\"button\"\n variant=\"outline\"\n data-slot=\"create-another\"\n :class=\"createAnotherClass\"\n :disabled=\"props.modal.processing\"\n @click=\"submitAnother\"\n ><Icon v-if=\"schema.createAnotherIcon\" :name=\"schema.createAnotherIcon\" />{{\n schema.createAnotherLabel\n }}</Button\n >\n <Button\n v-if=\"schema.submitLabel && submitVisible\"\n type=\"button\"\n :class=\"colorClass(solidButtonColorClasses, schema.submitColor, 'primary')\"\n :disabled=\"props.modal.processing\"\n :autofocus=\"schema.autofocus && !form\"\n @click=\"submit\"\n >\n <Spinner v-if=\"props.modal.processing\" />\n <Icon v-else-if=\"schema.submitIcon\" :name=\"schema.submitIcon\" />\n {{ schema.submitLabel }}\n </Button>\n </div>\n </DialogFooter>\n </DialogContent>\n </Dialog>\n</template>\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AiCopilot.js","names":["_sfc_main","AiCopilot_vue_vue_type_script_setup_true_lang_default","AiCopilot_default"],"sources":["../../../src/components/ai/AiCopilot.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { type AiCopilotSchema, CopilotController, shortcuts } from '@alfakit/core'\nimport { SparklesIcon } from '@lucide/vue'\nimport { computed, onBeforeUnmount, ref, shallowRef, watch } from 'vue'\nimport { useT } from '../../context'\nimport Button from '../ui/Button.vue'\nimport { CopilotPanel, preloadCopilotPanel } from './copilot-lazy'\n\n/**\n * The copilot of alfasix/alfakit-ai (`ai:copilot`): a topbar button (and `mod+j`) opening\n * a chat slide-over. Questions, tools and actions run on the server; proposed actions\n * run only when the user confirms them in the chat.\n */\nconst props = defineProps<{
|
|
1
|
+
{"version":3,"file":"AiCopilot.js","names":["_sfc_main","AiCopilot_vue_vue_type_script_setup_true_lang_default","AiCopilot_default"],"sources":["../../../src/components/ai/AiCopilot.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { type AiCopilotSchema, CopilotController, shortcuts } from '@alfakit/core'\nimport { SparklesIcon } from '@lucide/vue'\nimport { computed, onBeforeUnmount, ref, shallowRef, watch } from 'vue'\nimport { useT } from '../../context'\nimport Button from '../ui/Button.vue'\nimport { CopilotPanel, preloadCopilotPanel } from './copilot-lazy'\n\n/**\n * The copilot of alfasix/alfakit-ai (`ai:copilot`): a topbar button (and `mod+j`) opening\n * a chat slide-over. Questions, tools and actions run on the server; proposed actions\n * run only when the user confirms them in the chat.\n */\nconst props = defineProps<{\n component: AiCopilotSchema\n /** Open once mounted (starter kit header: clicked or `mod+j` before its code loaded). */\n autoOpen?: boolean\n}>()\nconst t = useT()\n// One controller per panel: Inertia visits pass new props objects.\nconst controller = new CopilotController(props.component)\nconst state = shallowRef(controller.state)\nconst mounted = ref(false)\nconst label = computed(() => t('ai.open', {}, 'Open AI copilot'))\n\nconst unsubscribe = controller.subscribe((next) => {\n state.value = next\n\n if (next.open) mounted.value = true\n})\n\nif (props.autoOpen && props.component.canUse !== false) controller.open()\n\nlet unregister: (() => void) | undefined\n\nwatch(\n () => [JSON.stringify(props.component.keyBindings ?? []), label.value] as const,\n ([keys, text]) => {\n unregister?.()\n unregister = undefined\n\n const bindings = JSON.parse(keys) as string[]\n\n if (bindings.length === 0) return\n\n unregister = shortcuts.register({\n id: 'ai.copilot',\n keys: bindings,\n label: text,\n group: 'general',\n allowInInputs: true,\n handler: () => controller.toggle(),\n })\n },\n { immediate: true },\n)\n\nonBeforeUnmount(() => {\n unsubscribe()\n unregister?.()\n})\n</script>\n\n<template>\n <div v-if=\"props.component.canUse !== false\" data-slot=\"ai-copilot\" class=\"contents\">\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"icon\"\n data-slot=\"ai-copilot-trigger\"\n :aria-label=\"label\"\n :aria-expanded=\"state.open\"\n aria-haspopup=\"dialog\"\n :title=\"label\"\n @click=\"controller.open()\"\n @pointerenter=\"preloadCopilotPanel()\"\n @focus=\"preloadCopilotPanel()\"\n >\n <SparklesIcon aria-hidden=\"true\" />\n </Button>\n <CopilotPanel v-if=\"mounted\" :controller=\"controller\" />\n </div>\n</template>\n"],"mappings":""}
|
|
@@ -6,6 +6,8 @@ import { type AiCopilotSchema } from '@alfakit/core';
|
|
|
6
6
|
*/
|
|
7
7
|
type __VLS_Props = {
|
|
8
8
|
component: AiCopilotSchema;
|
|
9
|
+
/** Open once mounted (starter kit header: clicked or `mod+j` before its code loaded). */
|
|
10
|
+
autoOpen?: boolean;
|
|
9
11
|
};
|
|
10
12
|
declare const _default: import("vue").DefineComponent<__VLS_Props, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {}, string, import("vue").PublicProps, Readonly<__VLS_Props> & Readonly<{}>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
|
|
11
13
|
export default _default;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AiCopilot.vue.d.ts","sourceRoot":"","sources":["../../../src/components/ai/AiCopilot.vue"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"AiCopilot.vue.d.ts","sourceRoot":"","sources":["../../../src/components/ai/AiCopilot.vue"],"names":[],"mappings":"AAqFA,OAAO,EAAE,KAAK,eAAe,EAAgC,MAAM,eAAe,CAAA;AAOlF;;;;GAIG;AACH,KAAK,WAAW,GAAG;IACjB,SAAS,EAAE,eAAe,CAAA;IAC1B,yFAAyF;IACzF,QAAQ,CAAC,EAAE,OAAO,CAAA;CACnB,CAAC;;AA4JF,wBAMG"}
|
|
@@ -11,11 +11,16 @@ var b = {
|
|
|
11
11
|
class: "contents"
|
|
12
12
|
}, x = /*@__PURE__*/ d({
|
|
13
13
|
__name: "AiCopilot",
|
|
14
|
-
props: {
|
|
14
|
+
props: {
|
|
15
|
+
component: {},
|
|
16
|
+
autoOpen: { type: Boolean }
|
|
17
|
+
},
|
|
15
18
|
setup(d) {
|
|
16
19
|
let x = d, S = e(), C = new i(x.component), w = h(C.state), T = m(!1), E = o(() => S("ai.open", {}, "Open AI copilot")), D = C.subscribe((e) => {
|
|
17
20
|
w.value = e, e.open && (T.value = !0);
|
|
18
|
-
})
|
|
21
|
+
});
|
|
22
|
+
x.autoOpen && x.component.canUse !== !1 && C.open();
|
|
23
|
+
let O;
|
|
19
24
|
return _(() => [JSON.stringify(x.component.keyBindings ?? []), E.value], ([e, t]) => {
|
|
20
25
|
O?.(), O = void 0;
|
|
21
26
|
let n = JSON.parse(e);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AiCopilot.vue_vue_type_script_setup_true_lang.js","names":["_openBlock","_createElementBlock","_createVNode","Button","_unref","_withCtx","_createBlock","_createCommentVNode","Button_default","_hoisted_1","AiCopilot_vue_vue_type_script_setup_true_lang_default","props","__props","t","useT","controller","CopilotController","state","shallowRef","mounted","ref","label","computed","unsubscribe","next","unregister","watch","keys","text","bindings","shortcuts","onBeforeUnmount","createCommentVNode","openBlock","createElementBlock","createVNode","_cache","unref","preloadCopilotPanel","withCtx","SparklesIcon","createBlock","CopilotPanel"],"sources":["../../../src/components/ai/AiCopilot.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { type AiCopilotSchema, CopilotController, shortcuts } from '@alfakit/core'\nimport { SparklesIcon } from '@lucide/vue'\nimport { computed, onBeforeUnmount, ref, shallowRef, watch } from 'vue'\nimport { useT } from '../../context'\nimport Button from '../ui/Button.vue'\nimport { CopilotPanel, preloadCopilotPanel } from './copilot-lazy'\n\n/**\n * The copilot of alfasix/alfakit-ai (`ai:copilot`): a topbar button (and `mod+j`) opening\n * a chat slide-over. Questions, tools and actions run on the server; proposed actions\n * run only when the user confirms them in the chat.\n */\nconst props = defineProps<{
|
|
1
|
+
{"version":3,"file":"AiCopilot.vue_vue_type_script_setup_true_lang.js","names":["_openBlock","_createElementBlock","_createVNode","Button","_unref","_withCtx","_createBlock","_createCommentVNode","Button_default","_hoisted_1","AiCopilot_vue_vue_type_script_setup_true_lang_default","props","__props","t","useT","controller","CopilotController","state","shallowRef","mounted","ref","label","computed","unsubscribe","next","unregister","watch","keys","text","bindings","shortcuts","onBeforeUnmount","createCommentVNode","openBlock","createElementBlock","createVNode","_cache","unref","preloadCopilotPanel","withCtx","SparklesIcon","createBlock","CopilotPanel"],"sources":["../../../src/components/ai/AiCopilot.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { type AiCopilotSchema, CopilotController, shortcuts } from '@alfakit/core'\nimport { SparklesIcon } from '@lucide/vue'\nimport { computed, onBeforeUnmount, ref, shallowRef, watch } from 'vue'\nimport { useT } from '../../context'\nimport Button from '../ui/Button.vue'\nimport { CopilotPanel, preloadCopilotPanel } from './copilot-lazy'\n\n/**\n * The copilot of alfasix/alfakit-ai (`ai:copilot`): a topbar button (and `mod+j`) opening\n * a chat slide-over. Questions, tools and actions run on the server; proposed actions\n * run only when the user confirms them in the chat.\n */\nconst props = defineProps<{\n component: AiCopilotSchema\n /** Open once mounted (starter kit header: clicked or `mod+j` before its code loaded). */\n autoOpen?: boolean\n}>()\nconst t = useT()\n// One controller per panel: Inertia visits pass new props objects.\nconst controller = new CopilotController(props.component)\nconst state = shallowRef(controller.state)\nconst mounted = ref(false)\nconst label = computed(() => t('ai.open', {}, 'Open AI copilot'))\n\nconst unsubscribe = controller.subscribe((next) => {\n state.value = next\n\n if (next.open) mounted.value = true\n})\n\nif (props.autoOpen && props.component.canUse !== false) controller.open()\n\nlet unregister: (() => void) | undefined\n\nwatch(\n () => [JSON.stringify(props.component.keyBindings ?? []), label.value] as const,\n ([keys, text]) => {\n unregister?.()\n unregister = undefined\n\n const bindings = JSON.parse(keys) as string[]\n\n if (bindings.length === 0) return\n\n unregister = shortcuts.register({\n id: 'ai.copilot',\n keys: bindings,\n label: text,\n group: 'general',\n allowInInputs: true,\n handler: () => controller.toggle(),\n })\n },\n { immediate: true },\n)\n\nonBeforeUnmount(() => {\n unsubscribe()\n unregister?.()\n})\n</script>\n\n<template>\n <div v-if=\"props.component.canUse !== false\" data-slot=\"ai-copilot\" class=\"contents\">\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"icon\"\n data-slot=\"ai-copilot-trigger\"\n :aria-label=\"label\"\n :aria-expanded=\"state.open\"\n aria-haspopup=\"dialog\"\n :title=\"label\"\n @click=\"controller.open()\"\n @pointerenter=\"preloadCopilotPanel()\"\n @focus=\"preloadCopilotPanel()\"\n >\n <SparklesIcon aria-hidden=\"true\" />\n </Button>\n <CopilotPanel v-if=\"mounted\" :controller=\"controller\" />\n </div>\n</template>\n"],"mappings":";;;;;;;;;;;;;;;;;;EAaA,IAAMW,IAAQC,GAKRC,IAAIC,EAAK,GAETC,IAAa,IAAIC,EAAkBL,EAAM,SAAS,GAClDM,IAAQC,EAAWH,EAAW,KAAK,GACnCI,IAAUC,EAAI,EAAK,GACnBC,IAAQC,QAAeT,EAAE,WAAW,CAAC,GAAG,iBAAiB,CAAC,GAE1DU,IAAcR,EAAW,WAAW,MAAS;GAGjD,AAFA,EAAM,QAAQS,GAEVA,EAAK,SAAM,EAAQ,QAAQ;EACjC,CAAC;EAED,AAAIb,EAAM,YAAYA,EAAM,UAAU,WAAW,MAAOI,EAAW,KAAK;EAExE,IAAIU;SAEJC,QACQ,CAAC,KAAK,UAAUf,EAAM,UAAU,eAAe,CAAC,CAAC,GAAGU,EAAM,KAAK,IACpE,CAACM,GAAMC,OAAU;GAEhB,AADAH,IAAa,GACb,IAAa,KAAA;GAEb,IAAMI,IAAW,KAAK,MAAMF,CAAI;GAEhC,AAAIE,EAAS,WAAW,MAExB,IAAaC,EAAU,SAAS;IAC9B,IAAI;IACJ,MAAMD;IACN,OAAOD;IACP,OAAO;IACP,eAAe;IACf,eAAeb,EAAW,OAAO;GACnC,CAAC;EACH,GACA,EAAE,WAAW,GAAK,CACpB,GAEAgB,QAAsB;GAEpB,AADAR,EAAY,GACZE,IAAa;EACf,CAAC,aAIYd,EAAM,UAAU,WAAM,kBAAjCX,EAAA,GAAAC,EAiBM,OAjBNQ,GAiBM,CAhBJP,EAcSC,GAAA;GAbP,MAAK;GACL,SAAQ;GACR,MAAK;GACL,aAAU;GACT,cAAYkB,EAAA;GACZ,iBAAeJ,EAAA,MAAM;GACtB,iBAAc;GACb,OAAOI,EAAA;GACP,SAAK,AAAAe,EAAA,QAAA,MAAEhC,EAAAW,CAAA,CAAU,CAAC,KAAI;GACtB,gBAAY,AAAAqB,EAAA,QAAA,MAAEhC,EAAAkC,CAAA,CAAmB,CAAA;GACjC,SAAK,AAAAF,EAAA,QAAA,MAAEhC,EAAAkC,CAAA,CAAmB,CAAA;;GAE3B,SAAAjC,QAAmC,CAAnCH,EAAmCE,EAAAoC,CAAA,GAAA,EAArB,eAAY,OAAM,CAAA,CAAA,CAAA;;;;;;EAEd,CAAA,GAAArB,EAAA,SAApBnB,EAAA,GAAAM,EAAwDF,EAAAsC,CAAA,GAAA;;GAA1B,YAAYtC,EAAAW,CAAA"}
|
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
import { useOptionalRegistry as e } from "../../context.js";
|
|
2
|
-
import t from "
|
|
3
|
-
import n from "
|
|
4
|
-
import r from "
|
|
5
|
-
import i from "
|
|
6
|
-
import a from "
|
|
7
|
-
import o from "../ui/
|
|
8
|
-
import
|
|
9
|
-
import c from "
|
|
10
|
-
import l from "
|
|
11
|
-
import u from "
|
|
12
|
-
import d from "
|
|
2
|
+
import { provideCms as t } from "./context.js";
|
|
3
|
+
import n from "./CmsBlocks.js";
|
|
4
|
+
import r from "./CmsFooter.js";
|
|
5
|
+
import i from "./CmsHead.js";
|
|
6
|
+
import a from "./CmsHeader.js";
|
|
7
|
+
import o from "../ui/Breadcrumb.js";
|
|
8
|
+
import s from "../ui/BreadcrumbItem.js";
|
|
9
|
+
import c from "../ui/BreadcrumbLink.js";
|
|
10
|
+
import l from "../ui/BreadcrumbList.js";
|
|
11
|
+
import u from "../ui/BreadcrumbPage.js";
|
|
12
|
+
import d from "../ui/BreadcrumbSeparator.js";
|
|
13
13
|
import { CMS_FOOTER_KEY as f, CMS_HEADER_KEY as p, cmsPayload as m } from "@alfakit/core";
|
|
14
14
|
import { usePage as h } from "@inertiajs/vue3";
|
|
15
15
|
import { Fragment as g, computed as _, createBlock as v, createCommentVNode as y, createElementBlock as b, createElementVNode as x, createTextVNode as S, createVNode as C, defineAsyncComponent as w, defineComponent as T, openBlock as E, renderList as D, renderSlot as O, resolveDynamicComponent as k, toDisplayString as A, unref as j, watchEffect as M, withCtx as N } from "vue";
|
|
@@ -51,10 +51,10 @@ var F = [
|
|
|
51
51
|
return () => null;
|
|
52
52
|
}
|
|
53
53
|
}
|
|
54
|
-
let W = U(), G = _(() => H.cms ?? m(W())), K =
|
|
54
|
+
let W = U(), G = _(() => H.cms ?? m(W())), K = t(() => G.value, () => H.components), q = e(), J = _(() => q?.resolve(p) ?? a), Y = _(() => q?.resolve(f) ?? r), X = (e, t) => K.value.t(e, {}, t), Z = w(() => import("./AdminBar.js"));
|
|
55
55
|
return M(() => {
|
|
56
56
|
typeof document < "u" && G.value && (document.documentElement.lang = G.value.site.tag, document.documentElement.dir = G.value.site.direction);
|
|
57
|
-
}), (e,
|
|
57
|
+
}), (e, t) => G.value ? (E(), b(g, { key: 0 }, [C(i, { seo: G.value.page.seo }, null, 8, ["seo"]), x("div", {
|
|
58
58
|
dir: G.value.site.direction,
|
|
59
59
|
lang: G.value.site.tag,
|
|
60
60
|
"data-slot": "cms-page",
|
|
@@ -67,17 +67,17 @@ var F = [
|
|
|
67
67
|
"aria-hidden": "true"
|
|
68
68
|
}), x("span", null, [x("strong", R, A(X("cms.preview", "Preview")), 1), S(" · " + A(X("cms.preview_notice", "This is a preview. Visitors don't see unpublished changes.")), 1)])])) : y("", !0),
|
|
69
69
|
(E(), v(k(J.value), { cms: G.value }, null, 8, ["cms"])),
|
|
70
|
-
x("main", z, [G.value.page.breadcrumbs.length > 1 ? (E(), v(
|
|
70
|
+
x("main", z, [G.value.page.breadcrumbs.length > 1 ? (E(), v(o, {
|
|
71
71
|
key: 0,
|
|
72
72
|
"aria-label": X("cms.breadcrumbs", "Breadcrumbs"),
|
|
73
73
|
class: "mx-auto max-w-6xl px-4 pt-6 sm:px-6 lg:px-8"
|
|
74
74
|
}, {
|
|
75
|
-
default: N(() => [C(
|
|
76
|
-
default: N(() => [(E(!0), b(g, null, D(G.value.page.breadcrumbs, (e, t) => (E(), b(g, { key: e.url }, [t > 0 ? (E(), v(
|
|
77
|
-
default: N(() => [t === G.value.page.breadcrumbs.length - 1 ? (E(), v(
|
|
75
|
+
default: N(() => [C(l, null, {
|
|
76
|
+
default: N(() => [(E(!0), b(g, null, D(G.value.page.breadcrumbs, (e, t) => (E(), b(g, { key: e.url }, [t > 0 ? (E(), v(d, { key: 0 })) : y("", !0), C(s, null, {
|
|
77
|
+
default: N(() => [t === G.value.page.breadcrumbs.length - 1 ? (E(), v(u, { key: 0 }, {
|
|
78
78
|
default: N(() => [S(A(e.label), 1)]),
|
|
79
79
|
_: 2
|
|
80
|
-
}, 1024)) : (E(), v(
|
|
80
|
+
}, 1024)) : (E(), v(c, {
|
|
81
81
|
key: 1,
|
|
82
82
|
href: e.url
|
|
83
83
|
}, {
|
|
@@ -89,7 +89,7 @@ var F = [
|
|
|
89
89
|
_: 1
|
|
90
90
|
})]),
|
|
91
91
|
_: 1
|
|
92
|
-
}, 8, ["aria-label"])) : y("", !0), O(e.$slots, "default", { cms: G.value }, () => [G.value.page.blocks.length > 0 ? (E(), v(
|
|
92
|
+
}, 8, ["aria-label"])) : y("", !0), O(e.$slots, "default", { cms: G.value }, () => [G.value.page.blocks.length > 0 ? (E(), v(n, {
|
|
93
93
|
key: 0,
|
|
94
94
|
blocks: G.value.page.blocks
|
|
95
95
|
}, null, 8, ["blocks"])) : (E(), b("p", B, A(X("cms.empty_page", "This page has no content yet.")), 1))])]),
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CmsPage.vue_vue_type_script_setup_true_lang.js","names":["CmsHeader","CmsFooter","_openBlock","_createElementBlock","_Fragment","_createVNode","CmsHead","_createElementVNode","_toDisplayString","_unref","_createTextVNode","_createCommentVNode","_createBlock","_resolveDynamicComponent","Breadcrumb","_withCtx","BreadcrumbList","_renderList","BreadcrumbSeparator","BreadcrumbItem","BreadcrumbPage","BreadcrumbLink","_renderSlot","CmsBlocks","
|
|
1
|
+
{"version":3,"file":"CmsPage.vue_vue_type_script_setup_true_lang.js","names":["CmsHeader","CmsFooter","_openBlock","_createElementBlock","_Fragment","_createVNode","CmsHead","_createElementVNode","_toDisplayString","_unref","_createTextVNode","_createCommentVNode","_createBlock","_resolveDynamicComponent","Breadcrumb","_withCtx","BreadcrumbList","_renderList","BreadcrumbSeparator","BreadcrumbItem","BreadcrumbPage","BreadcrumbLink","_renderSlot","CmsBlocks","CmsBlocks_default","CmsFooter_default","CmsHead_default","CmsHeader_default","Breadcrumb_default","BreadcrumbItem_default","BreadcrumbLink_default","BreadcrumbList_default","BreadcrumbPage_default","BreadcrumbSeparator_default","_hoisted_1","_hoisted_2","_hoisted_3","_hoisted_4","_hoisted_5","_hoisted_6","_hoisted_7","CmsPage_vue_vue_type_script_setup_true_lang_default","props","__props","usePageProps","page","usePage","pageProps","cms","computed","cmsPayload","context","provideCms","registry","useOptionalRegistry","header","CMS_HEADER_KEY","footer","CMS_FOOTER_KEY","t","key","fallback","CmsAdminBar","defineAsyncComponent","watchEffect","openBlock","createElementBlock","Fragment","createVNode","createElementVNode","toDisplayString","unref","EyeIcon","createTextVNode","createCommentVNode","createBlock","resolveDynamicComponent","withCtx","renderList","crumb","index","renderSlot","_ctx"],"sources":["../../../src/components/cms/CmsPage.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { CMS_FOOTER_KEY, CMS_HEADER_KEY, cmsPayload, type CmsPayload } from '@alfakit/core'\nimport { usePage } from '@inertiajs/vue3'\nimport { EyeIcon } from '@lucide/vue'\nimport { computed, defineAsyncComponent, watchEffect } from 'vue'\nimport { useOptionalRegistry, type AnyComponent } from '../../context'\nimport Breadcrumb from '../ui/Breadcrumb.vue'\nimport BreadcrumbItem from '../ui/BreadcrumbItem.vue'\nimport BreadcrumbLink from '../ui/BreadcrumbLink.vue'\nimport BreadcrumbList from '../ui/BreadcrumbList.vue'\nimport BreadcrumbPage from '../ui/BreadcrumbPage.vue'\nimport BreadcrumbSeparator from '../ui/BreadcrumbSeparator.vue'\nimport CmsBlocks from './CmsBlocks.vue'\nimport CmsFooter from './CmsFooter.vue'\nimport CmsHead from './CmsHead.vue'\nimport CmsHeader from './CmsHeader.vue'\nimport { provideCms } from './context'\n\n/**\n * The `Alfakit/CmsPage` Inertia page (public CMS pages and previews). Register it in your\n * public site's Inertia app: `createAlfakit({ pages: { 'Alfakit/CmsPage': CmsPage } })`.\n *\n * Replace the header or footer with `cms:header` / `cms:footer` registry components, a\n * block with `cms:block:{type}`, or build your own page from `CmsBlocks` and `CmsHead`.\n */\nconst props = defineProps<{ cms?: CmsPayload; components?: Record<string, AnyComponent> }>()\n\nfunction usePageProps(): () => unknown {\n try {\n const page = usePage()\n\n return () => page.props\n } catch {\n return () => null\n }\n}\n\nconst pageProps = usePageProps()\nconst cms = computed(() => props.cms ?? cmsPayload(pageProps()))\nconst context = provideCms(\n () => cms.value,\n () => props.components,\n)\nconst registry = useOptionalRegistry()\nconst header = computed<AnyComponent>(() => registry?.resolve(CMS_HEADER_KEY) ?? CmsHeader)\nconst footer = computed<AnyComponent>(() => registry?.resolve(CMS_FOOTER_KEY) ?? CmsFooter)\n\nconst t = (key: string, fallback: string) => context.value.t(key, {}, fallback)\n\n// The admin bar loads only for signed-in editors (the server sends `cms.admin` to them alone).\nconst CmsAdminBar = defineAsyncComponent(() => import('./AdminBar.vue'))\n\nwatchEffect(() => {\n if (typeof document === 'undefined' || !cms.value) return\n\n document.documentElement.lang = cms.value.site.tag\n document.documentElement.dir = cms.value.site.direction\n})\n</script>\n\n<template>\n <template v-if=\"cms\">\n <CmsHead :seo=\"cms.page.seo\" />\n <div\n :dir=\"cms.site.direction\"\n :lang=\"cms.site.tag\"\n data-slot=\"cms-page\"\n :data-layout=\"cms.page.layout ?? undefined\"\n class=\"bg-background text-foreground flex min-h-svh flex-col\"\n >\n <a\n href=\"#cms-content\"\n class=\"bg-background focus-visible:ring-ring/50 sr-only z-50 rounded-md px-4 py-2 focus:not-sr-only focus:absolute focus:start-4 focus:top-4 focus-visible:ring-[3px]\"\n >\n {{ t('cms.skip_to_content', 'Skip to content') }}\n </a>\n <div\n v-if=\"cms.preview\"\n role=\"status\"\n data-slot=\"cms-preview-banner\"\n class=\"flex items-center justify-center gap-2 bg-amber-100 px-4 py-2 text-sm text-amber-950 dark:bg-amber-950 dark:text-amber-100\"\n >\n <EyeIcon class=\"size-4 shrink-0\" aria-hidden=\"true\" />\n <span>\n <strong class=\"font-semibold\">{{ t('cms.preview', 'Preview') }}</strong> ·\n {{\n t('cms.preview_notice', \"This is a preview. Visitors don't see unpublished changes.\")\n }}\n </span>\n </div>\n <component :is=\"header\" :cms=\"cms\" />\n <main id=\"cms-content\" tabindex=\"-1\" class=\"flex-1 outline-none\" data-slot=\"cms-content\">\n <Breadcrumb\n v-if=\"cms.page.breadcrumbs.length > 1\"\n :aria-label=\"t('cms.breadcrumbs', 'Breadcrumbs')\"\n class=\"mx-auto max-w-6xl px-4 pt-6 sm:px-6 lg:px-8\"\n >\n <BreadcrumbList>\n <template v-for=\"(crumb, index) in cms.page.breadcrumbs\" :key=\"crumb.url\">\n <BreadcrumbSeparator v-if=\"index > 0\" />\n <BreadcrumbItem>\n <BreadcrumbPage v-if=\"index === cms.page.breadcrumbs.length - 1\">{{\n crumb.label\n }}</BreadcrumbPage>\n <BreadcrumbLink v-else :href=\"crumb.url\">{{ crumb.label }}</BreadcrumbLink>\n </BreadcrumbItem>\n </template>\n </BreadcrumbList>\n </Breadcrumb>\n <slot :cms=\"cms\">\n <CmsBlocks v-if=\"cms.page.blocks.length > 0\" :blocks=\"cms.page.blocks\" />\n <p v-else class=\"text-muted-foreground mx-auto max-w-3xl px-4 py-24 text-center\">\n {{ t('cms.empty_page', 'This page has no content yet.') }}\n </p>\n </slot>\n </main>\n <component :is=\"footer\" :cms=\"cms\" />\n <!-- eslint-disable-next-line vue/no-v-html -- built on the server (Credit::poweredBy) -->\n <div v-if=\"cms.poweredBy\" data-slot=\"cms-powered-by\" v-html=\"cms.poweredBy\" />\n <CmsAdminBar v-if=\"cms.admin\" :admin=\"cms.admin\" />\n </div>\n </template>\n</template>\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"LivePreview.js","names":["_sfc_main","LivePreview_vue_vue_type_script_setup_true_lang_default","LivePreview_default"],"sources":["../../../src/components/cms/LivePreview.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport {\n CMS_PREVIEW_DEVICES,\n CmsAutosave,\n callCmsAutosave,\n cmsPreviewFitsBeside,\n cmsPreviewOpensOnLoad,\n rememberedCmsPreview,\n resolveStickyOffset,\n reserveCmsPreviewSpace,\n type CmsAutosaveSnapshot,\n type CmsLivePreviewSchema,\n type CmsPreviewDevice,\n} from '@alfakit/core'\nimport {\n CheckIcon,\n CircleAlertIcon,\n EyeIcon,\n LoaderCircleIcon,\n Maximize2Icon,\n Minimize2Icon,\n MonitorIcon,\n SmartphoneIcon,\n TabletIcon,\n XIcon,\n} from '@lucide/vue'\nimport { computed, onBeforeUnmount, onMounted, ref, shallowRef, watch } from 'vue'\nimport { usePageSchema, usePanel, useT } from '../../context'\nimport { cn } from '../../lib/utils'\nimport { useOptionalFormStore } from '../form/form-context'\nimport ActionList from '../actions/ActionList.vue'\nimport Badge from '../ui/Badge.vue'\nimport Button from '../ui/Button.vue'\n\n/**\n * The page editor's autosave status and live preview (schema type `CmsLivePreview`).\n * Changes are autosaved as a draft a moment after typing stops; the preview pane shows\n * the signed preview of that draft beside the form, full screen, or at tablet and phone\n * widths.\n */\nconst props = defineProps<{ component: CmsLivePreviewSchema }>()\n\nconst t = useT()\nconst form = useOptionalFormStore()\nconst page = usePageSchema()\nconst panel = usePanel()\nconst root = ref<HTMLElement | null>(null)\nconst open = ref(false)\nconst fullScreen = ref(false)\n// Too narrow for the form beside the pane (e.g. 1280px with the sidebar): full-screen overlay.\nconst overlay = ref(false)\nconst expanded = computed(() => fullScreen.value || overlay.value)\nconst device = ref<CmsPreviewDevice>('desktop')\nconst snapshot = shallowRef<CmsAutosaveSnapshot>({\n status: props.component.savedAt ? 'saved' : 'idle',\n savedAt: props.component.savedAt ?? null,\n previewUrl: props.component.previewUrl,\n version: 0,\n hasChanges: props.component.hasChanges ?? false,\n})\nconst top = ref('0px')\nconst actionContext = computed(() => ({ token: page.value?.token ?? '', component: 'page' }))\nconst status = computed(() =>\n snapshot.value.hasChanges && props.component.changedStatus\n ? props.component.changedStatus\n : props.component.status,\n)\n/** Badge colours of the status (the server's `PageState` colours). */\nconst STATUS_COLORS: Record<string, string> = {\n gray: 'border-border bg-muted text-foreground',\n success: 'border-emerald-600/30 bg-emerald-500/10 text-emerald-700 dark:text-emerald-300',\n warning: 'border-amber-600/30 bg-amber-500/10 text-amber-700 dark:text-amber-300',\n info: 'border-sky-600/30 bg-sky-500/10 text-sky-700 dark:text-sky-300',\n danger: 'border-red-600/30 bg-red-500/10 text-red-700 dark:text-red-300',\n}\n\nconst devices = Object.keys(CMS_PREVIEW_DEVICES) as CmsPreviewDevice[]\nconst icons = { desktop: MonitorIcon, tablet: TabletIcon, phone: SmartphoneIcon }\nconst labels = { desktop: 'Desktop', tablet: 'Tablet', phone: 'Phone' }\nconst width = computed(() => CMS_PREVIEW_DEVICES[device.value])\n\nconst statusLabel = computed(() => {\n switch (snapshot.value.status) {\n case 'saving':\n return t('cms.saving', {}, 'Saving…')\n case 'saved':\n return t('cms.saved', {}, 'Draft saved automatically')\n case 'pending':\n return t('cms.unsaved', {}, 'Unsaved changes')\n case 'error':\n return t(\n 'cms.save_failed',\n {},\n \"Your latest changes couldn't be saved. They will be tried again.\",\n )\n default:\n return ''\n }\n})\n\nlet autosave: CmsAutosave | null = null\nlet unsubscribe: (() => void) | null = null\nlet release: () => void = () => {}\n\nfunction onKey(event: KeyboardEvent) {\n if (event.key !== 'Escape' || !open.value) return\n if (fullScreen.value && !overlay.value) fullScreen.value = false\n else setOpen(false)\n}\n\n/** Open or collapse the pane, remembering the choice for the next visit. */\nfunction setOpen(next: boolean) {\n open.value = next\n rememberedCmsPreview(next ? 'open' : 'closed')\n}\n\nfunction measure() {\n if (open.value) overlay.value = !cmsPreviewFitsBeside(root.value)\n}\n\nonMounted(() => {\n window.addEventListener('keydown', onKey)\n window.addEventListener('resize', measure)\n // Stick right under the panel's topbar when it sticks too.\n top.value = resolveStickyOffset(null)\n // Wide screens open the pane beside the form; the viewer's last choice wins.\n if (props.component.previewUrl && cmsPreviewOpensOnLoad(root.value)) open.value = true\n\n if (!form) return\n\n autosave = new CmsAutosave({\n debounce: props.component.debounce,\n previewUrl: props.component.previewUrl,\n savedAt: props.component.savedAt,\n hasChanges: props.component.hasChanges,\n save: (state) =>\n callCmsAutosave(props.component.autosaveMethod, state, {\n token: page.value?.token ?? '',\n endpoint: panel.value?.endpoints?.pageCall ?? '',\n }),\n onChange: (next) => (snapshot.value = next),\n })\n\n let values = form.state.values\n unsubscribe = form.subscribe((state) => {\n if (state.values !== values) {\n values = state.values\n autosave?.schedule(state.values)\n }\n })\n})\n\n// Side by side, the form makes room for the pane.\nwatch(open, measure)\nwatch([open, expanded], ([isOpen, isFull]) => {\n release()\n release = isOpen && !isFull ? reserveCmsPreviewSpace(root.value, 'min(50vw, 56rem)') : () => {}\n})\n\nonBeforeUnmount(() => {\n window.removeEventListener('keydown', onKey)\n window.removeEventListener('resize', measure)\n unsubscribe?.()\n release()\n const current = autosave\n void current?.flush().finally(() => current.dispose())\n})\n</script>\n\n<template>\n <div\n ref=\"root\"\n data-slot=\"cms-live-preview\"\n :style=\"{ top }\"\n class=\"bg-background sticky z-20 flex flex-wrap items-center gap-x-4 gap-y-2 rounded-xl border px-3 py-2.5 shadow-sm\"\n >\n <div class=\"flex min-w-0 flex-1 basis-64 flex-col gap-0.5\">\n <p\n v-if=\"status\"\n class=\"flex flex-wrap items-center gap-x-2 gap-y-1 text-sm\"\n data-slot=\"cms-editor-status\"\n >\n <Badge\n variant=\"outline\"\n :data-color=\"status.color\"\n :class=\"STATUS_COLORS[status.color] ?? ''\"\n >{{ status.label }}</Badge\n >\n <span class=\"text-muted-foreground\">{{ status.description }}</span>\n </p>\n <p\n class=\"text-muted-foreground flex min-h-4 items-center gap-1.5 text-xs\"\n role=\"status\"\n aria-live=\"polite\"\n >\n <LoaderCircleIcon\n v-if=\"snapshot.status === 'saving'\"\n class=\"size-4 animate-spin\"\n aria-hidden=\"true\"\n />\n <CircleAlertIcon\n v-else-if=\"snapshot.status === 'error'\"\n class=\"text-destructive size-4\"\n aria-hidden=\"true\"\n />\n <CheckIcon v-else-if=\"snapshot.status === 'saved'\" class=\"size-4\" aria-hidden=\"true\" />\n {{ statusLabel }}\n </p>\n </div>\n <div class=\"flex flex-wrap items-center gap-2\">\n <Button\n v-if=\"snapshot.previewUrl\"\n type=\"button\"\n :variant=\"open ? 'secondary' : 'outline'\"\n size=\"sm\"\n :aria-pressed=\"open\"\n :title=\"\n t('cms.live_preview_help', {}, 'See the page as visitors will, updated as you type.')\n \"\n data-slot=\"cms-live-preview-toggle\"\n @click=\"setOpen(!open)\"\n >\n <EyeIcon aria-hidden=\"true\" />\n {{\n open\n ? t('cms.hide_preview', {}, 'Hide preview')\n : t('cms.live_preview', {}, 'Live preview')\n }}\n </Button>\n <div v-if=\"props.component.actions?.length\" @pointerdown.capture=\"autosave?.flush()\">\n <ActionList :actions=\"props.component.actions\" :context=\"actionContext\" size=\"sm\" />\n </div>\n </div>\n <section\n v-if=\"open && snapshot.previewUrl\"\n :aria-label=\"t('cms.live_preview', {}, 'Live preview')\"\n data-slot=\"cms-live-preview-pane\"\n :data-full-screen=\"expanded || undefined\"\n :style=\"{ top: expanded ? '0px' : top }\"\n :class=\"\n cn(\n 'bg-background fixed end-0 bottom-0 z-50 flex flex-col border-s shadow-xl',\n expanded ? 'inset-x-0 border-s-0' : 'w-full lg:w-[min(50vw,56rem)]',\n )\n \"\n >\n <header class=\"flex items-center justify-between gap-2 border-b px-3 py-2\">\n <div\n class=\"flex items-center gap-1\"\n role=\"group\"\n :aria-label=\"t('cms.preview_width', {}, 'Preview width')\"\n >\n <Button\n v-for=\"name in devices\"\n :key=\"name\"\n type=\"button\"\n :variant=\"device === name ? 'secondary' : 'ghost'\"\n size=\"icon-sm\"\n :aria-pressed=\"device === name\"\n @click=\"device = name\"\n >\n <component :is=\"icons[name]\" aria-hidden=\"true\" />\n <span class=\"sr-only\">{{ t(`cms.device_${name}`, {}, labels[name]) }}</span>\n </Button>\n </div>\n <p class=\"text-muted-foreground hidden truncate text-xs sm:block\">{{ statusLabel }}</p>\n <div class=\"flex items-center gap-1\">\n <Button\n v-if=\"!overlay\"\n type=\"button\"\n variant=\"ghost\"\n size=\"icon-sm\"\n :aria-pressed=\"fullScreen\"\n @click=\"fullScreen = !fullScreen\"\n >\n <Minimize2Icon v-if=\"fullScreen\" aria-hidden=\"true\" />\n <Maximize2Icon v-else aria-hidden=\"true\" />\n <span class=\"sr-only\">{{\n fullScreen\n ? t('cms.exit_full_screen', {}, 'Exit full screen')\n : t('cms.full_screen', {}, 'Full screen')\n }}</span>\n </Button>\n <Button type=\"button\" variant=\"ghost\" size=\"icon-sm\" @click=\"setOpen(false)\">\n <XIcon aria-hidden=\"true\" />\n <span class=\"sr-only\">{{ t('cms.close_preview', {}, 'Close preview') }}</span>\n </Button>\n </div>\n </header>\n <div class=\"bg-muted/40 flex flex-1 justify-center overflow-auto p-3\">\n <iframe\n :key=\"snapshot.version\"\n :src=\"snapshot.previewUrl\"\n :title=\"t('cms.preview_frame', {}, 'Page preview')\"\n class=\"bg-background h-full rounded-md border shadow-sm\"\n :style=\"{ width: width === null ? '100%' : `${width}px`, maxWidth: '100%' }\"\n />\n </div>\n </section>\n </div>\n</template>\n"],"mappings":""}
|
|
1
|
+
{"version":3,"file":"LivePreview.js","names":["_sfc_main","LivePreview_vue_vue_type_script_setup_true_lang_default","LivePreview_default"],"sources":["../../../src/components/cms/LivePreview.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport {\n CMS_PREVIEW_DEVICES,\n CmsAutosave,\n callCmsAutosave,\n cmsPreviewFitsBeside,\n cmsPreviewOpensOnLoad,\n rememberedCmsPreview,\n resolveStickyOffset,\n reserveCmsPreviewSpace,\n type CmsAutosaveSnapshot,\n type CmsLivePreviewSchema,\n type CmsPreviewDevice,\n} from '@alfakit/core'\nimport {\n CheckIcon,\n CircleAlertIcon,\n EyeIcon,\n LoaderCircleIcon,\n Maximize2Icon,\n Minimize2Icon,\n MonitorIcon,\n SmartphoneIcon,\n TabletIcon,\n XIcon,\n} from '@lucide/vue'\nimport { computed, onBeforeUnmount, onMounted, ref, shallowRef, watch } from 'vue'\nimport { usePageSchema, usePanel, useT } from '../../context'\nimport { cn } from '../../lib/utils'\nimport { useOptionalFormStore } from '../form/form-context'\nimport ActionList from '../actions/ActionList.vue'\nimport Badge from '../ui/Badge.vue'\nimport Button from '../ui/Button.vue'\n\n/**\n * The page editor's autosave status and live preview (schema type `CmsLivePreview`).\n * Changes are autosaved as a draft a moment after typing stops; the preview pane shows\n * the signed preview of that draft beside the form, full screen, or at tablet and phone\n * widths.\n */\nconst props = defineProps<{ component: CmsLivePreviewSchema }>()\n\nconst t = useT()\nconst form = useOptionalFormStore()\nconst page = usePageSchema()\nconst panel = usePanel()\nconst root = ref<HTMLElement | null>(null)\nconst open = ref(false)\nconst fullScreen = ref(false)\n// Too narrow for the form beside the pane (e.g. 1280px with the sidebar): full-screen overlay.\nconst overlay = ref(false)\nconst expanded = computed(() => fullScreen.value || overlay.value)\nconst device = ref<CmsPreviewDevice>('desktop')\nconst snapshot = shallowRef<CmsAutosaveSnapshot>({\n status: props.component.savedAt ? 'saved' : 'idle',\n savedAt: props.component.savedAt ?? null,\n previewUrl: props.component.previewUrl,\n version: 0,\n hasChanges: props.component.hasChanges ?? false,\n})\nconst top = ref('0px')\nconst actionContext = computed(() => ({ token: page.value?.token ?? '', component: 'page' }))\nconst status = computed(() =>\n snapshot.value.hasChanges && props.component.changedStatus\n ? props.component.changedStatus\n : props.component.status,\n)\n// \"Publish changes\" appears as soon as an autosave makes the draft differ.\nconst actions = computed(() =>\n snapshot.value.hasChanges && props.component.changedActions\n ? props.component.changedActions\n : props.component.actions,\n)\n/** Badge colours of the status (the server's `PageState` colours). */\nconst STATUS_COLORS: Record<string, string> = {\n gray: 'border-border bg-muted text-foreground',\n success: 'border-emerald-600/30 bg-emerald-500/10 text-emerald-700 dark:text-emerald-300',\n warning: 'border-amber-600/30 bg-amber-500/10 text-amber-700 dark:text-amber-300',\n info: 'border-sky-600/30 bg-sky-500/10 text-sky-700 dark:text-sky-300',\n danger: 'border-red-600/30 bg-red-500/10 text-red-700 dark:text-red-300',\n}\n\nconst devices = Object.keys(CMS_PREVIEW_DEVICES) as CmsPreviewDevice[]\nconst icons = { desktop: MonitorIcon, tablet: TabletIcon, phone: SmartphoneIcon }\nconst labels = { desktop: 'Desktop', tablet: 'Tablet', phone: 'Phone' }\nconst width = computed(() => CMS_PREVIEW_DEVICES[device.value])\n\nconst statusLabel = computed(() => {\n switch (snapshot.value.status) {\n case 'saving':\n return t('cms.saving', {}, 'Saving…')\n case 'saved':\n return t('cms.saved', {}, 'Draft saved automatically')\n case 'pending':\n return t('cms.unsaved', {}, 'Unsaved changes')\n case 'error':\n return t(\n 'cms.save_failed',\n {},\n \"Your latest changes couldn't be saved. They will be tried again.\",\n )\n default:\n return ''\n }\n})\n\nlet autosave: CmsAutosave | null = null\nlet unsubscribe: (() => void) | null = null\nlet release: () => void = () => {}\n\nfunction onKey(event: KeyboardEvent) {\n if (event.key !== 'Escape' || !open.value) return\n if (fullScreen.value && !overlay.value) fullScreen.value = false\n else setOpen(false)\n}\n\n/** Open or collapse the pane, remembering the choice for the next visit. */\nfunction setOpen(next: boolean) {\n open.value = next\n rememberedCmsPreview(next ? 'open' : 'closed')\n}\n\nfunction measure() {\n if (open.value) overlay.value = !cmsPreviewFitsBeside(root.value)\n}\n\nonMounted(() => {\n window.addEventListener('keydown', onKey)\n window.addEventListener('resize', measure)\n // Stick right under the panel's topbar when it sticks too.\n top.value = resolveStickyOffset(null)\n // Wide screens open the pane beside the form; the viewer's last choice wins.\n if (props.component.previewUrl && cmsPreviewOpensOnLoad(root.value)) open.value = true\n\n if (!form) return\n\n autosave = new CmsAutosave({\n debounce: props.component.debounce,\n previewUrl: props.component.previewUrl,\n savedAt: props.component.savedAt,\n hasChanges: props.component.hasChanges,\n save: (state) =>\n callCmsAutosave(props.component.autosaveMethod, state, {\n token: page.value?.token ?? '',\n endpoint: panel.value?.endpoints?.pageCall ?? '',\n }),\n onChange: (next) => (snapshot.value = next),\n })\n\n let values = form.state.values\n unsubscribe = form.subscribe((state) => {\n if (state.values !== values) {\n values = state.values\n autosave?.schedule(state.values)\n }\n })\n})\n\n// Side by side, the form makes room for the pane.\nwatch(open, measure)\nwatch([open, expanded], ([isOpen, isFull]) => {\n release()\n release = isOpen && !isFull ? reserveCmsPreviewSpace(root.value, 'min(50vw, 56rem)') : () => {}\n})\n\nonBeforeUnmount(() => {\n window.removeEventListener('keydown', onKey)\n window.removeEventListener('resize', measure)\n unsubscribe?.()\n release()\n const current = autosave\n void current?.flush().finally(() => current.dispose())\n})\n</script>\n\n<template>\n <div\n ref=\"root\"\n data-slot=\"cms-live-preview\"\n :style=\"{ top }\"\n class=\"bg-background sticky z-20 flex flex-wrap items-center gap-x-4 gap-y-2 rounded-xl border px-3 py-2.5 shadow-sm\"\n >\n <div class=\"flex min-w-0 flex-1 basis-64 flex-col gap-0.5\">\n <p\n v-if=\"status\"\n class=\"flex flex-wrap items-center gap-x-2 gap-y-1 text-sm\"\n data-slot=\"cms-editor-status\"\n >\n <Badge\n variant=\"outline\"\n :data-color=\"status.color\"\n :class=\"STATUS_COLORS[status.color] ?? ''\"\n >{{ status.label }}</Badge\n >\n <span class=\"text-muted-foreground\">{{ status.description }}</span>\n </p>\n <p\n class=\"text-muted-foreground flex min-h-4 items-center gap-1.5 text-xs\"\n role=\"status\"\n aria-live=\"polite\"\n >\n <LoaderCircleIcon\n v-if=\"snapshot.status === 'saving'\"\n class=\"size-4 animate-spin\"\n aria-hidden=\"true\"\n />\n <CircleAlertIcon\n v-else-if=\"snapshot.status === 'error'\"\n class=\"text-destructive size-4\"\n aria-hidden=\"true\"\n />\n <CheckIcon v-else-if=\"snapshot.status === 'saved'\" class=\"size-4\" aria-hidden=\"true\" />\n {{ statusLabel }}\n </p>\n </div>\n <div class=\"flex flex-wrap items-center gap-2\">\n <Button\n v-if=\"snapshot.previewUrl\"\n type=\"button\"\n :variant=\"open ? 'secondary' : 'outline'\"\n size=\"sm\"\n :aria-pressed=\"open\"\n :title=\"\n t('cms.live_preview_help', {}, 'See the page as visitors will, updated as you type.')\n \"\n data-slot=\"cms-live-preview-toggle\"\n @click=\"setOpen(!open)\"\n >\n <EyeIcon aria-hidden=\"true\" />\n {{\n open\n ? t('cms.hide_preview', {}, 'Hide preview')\n : t('cms.live_preview', {}, 'Live preview')\n }}\n </Button>\n <div v-if=\"actions?.length\" @pointerdown.capture=\"autosave?.flush()\">\n <ActionList :actions=\"actions\" :context=\"actionContext\" size=\"sm\" />\n </div>\n </div>\n <section\n v-if=\"open && snapshot.previewUrl\"\n :aria-label=\"t('cms.live_preview', {}, 'Live preview')\"\n data-slot=\"cms-live-preview-pane\"\n :data-full-screen=\"expanded || undefined\"\n :style=\"{ top: expanded ? '0px' : top }\"\n :class=\"\n cn(\n 'bg-background fixed end-0 bottom-0 z-50 flex flex-col border-s shadow-xl',\n expanded ? 'inset-x-0 border-s-0' : 'w-full lg:w-[min(50vw,56rem)]',\n )\n \"\n >\n <header class=\"flex items-center justify-between gap-2 border-b px-3 py-2\">\n <div\n class=\"flex items-center gap-1\"\n role=\"group\"\n :aria-label=\"t('cms.preview_width', {}, 'Preview width')\"\n >\n <Button\n v-for=\"name in devices\"\n :key=\"name\"\n type=\"button\"\n :variant=\"device === name ? 'secondary' : 'ghost'\"\n size=\"icon-sm\"\n :aria-pressed=\"device === name\"\n @click=\"device = name\"\n >\n <component :is=\"icons[name]\" aria-hidden=\"true\" />\n <span class=\"sr-only\">{{ t(`cms.device_${name}`, {}, labels[name]) }}</span>\n </Button>\n </div>\n <p class=\"text-muted-foreground hidden truncate text-xs sm:block\">{{ statusLabel }}</p>\n <div class=\"flex items-center gap-1\">\n <Button\n v-if=\"!overlay\"\n type=\"button\"\n variant=\"ghost\"\n size=\"icon-sm\"\n :aria-pressed=\"fullScreen\"\n @click=\"fullScreen = !fullScreen\"\n >\n <Minimize2Icon v-if=\"fullScreen\" aria-hidden=\"true\" />\n <Maximize2Icon v-else aria-hidden=\"true\" />\n <span class=\"sr-only\">{{\n fullScreen\n ? t('cms.exit_full_screen', {}, 'Exit full screen')\n : t('cms.full_screen', {}, 'Full screen')\n }}</span>\n </Button>\n <Button type=\"button\" variant=\"ghost\" size=\"icon-sm\" @click=\"setOpen(false)\">\n <XIcon aria-hidden=\"true\" />\n <span class=\"sr-only\">{{ t('cms.close_preview', {}, 'Close preview') }}</span>\n </Button>\n </div>\n </header>\n <div class=\"bg-muted/40 flex flex-1 justify-center overflow-auto p-3\">\n <iframe\n :key=\"snapshot.version\"\n :src=\"snapshot.previewUrl\"\n :title=\"t('cms.preview_frame', {}, 'Page preview')\"\n class=\"bg-background h-full rounded-md border shadow-sm\"\n :style=\"{ width: width === null ? '100%' : `${width}px`, maxWidth: '100%' }\"\n />\n </div>\n </section>\n </div>\n</template>\n"],"mappings":""}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"LivePreview.vue.d.ts","sourceRoot":"","sources":["../../../src/components/cms/LivePreview.vue"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"LivePreview.vue.d.ts","sourceRoot":"","sources":["../../../src/components/cms/LivePreview.vue"],"names":[],"mappings":"AAqTA,OAAO,EAUL,KAAK,oBAAoB,EAE1B,MAAM,eAAe,CAAA;AAqBtB;;;;;GAKG;AACH,KAAK,WAAW,GAAG;IAAE,SAAS,EAAE,oBAAoB,CAAA;CAAE,CAAC;;AAqlBvD,wBAMG"}
|