nuxt-ui-elements 0.1.20 → 0.1.22

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/dist/module.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "nuxt-ui-elements",
3
3
  "configKey": "uiElements",
4
- "version": "0.1.20",
4
+ "version": "0.1.22",
5
5
  "builder": {
6
6
  "@nuxt/module-builder": "1.0.2",
7
7
  "unbuild": "3.6.1"
package/dist/module.mjs CHANGED
@@ -69,8 +69,76 @@ const dialogConfirm = (options) => ({
69
69
  }
70
70
  });
71
71
 
72
+ const dialogAlert = (options) => ({
73
+ slots: {
74
+ content: "divide-y-0 bg-default ring-0",
75
+ header: "relative flex items-center gap-1.5 p-4 sm:px-6 min-h-16",
76
+ icon: "shrink-0 size-12",
77
+ title: "text-lg font-semibold",
78
+ description: "text-sm opacity-90",
79
+ body: "p-2 sm:p-5 sm:pt-0",
80
+ footer: "justify-center gap-3"
81
+ },
82
+ variants: {
83
+ size: {
84
+ sm: {
85
+ content: "sm:max-w-md"
86
+ },
87
+ md: {
88
+ content: "sm:max-w-3xl"
89
+ }
90
+ },
91
+ color: {
92
+ ...Object.fromEntries((options.theme.colors || []).map((color) => [color, ""])),
93
+ neutral: ""
94
+ },
95
+ variant: {
96
+ solid: "",
97
+ outline: ""
98
+ }
99
+ },
100
+ compoundVariants: [
101
+ // Solid variants - dynamically generated for all theme colors
102
+ ...(options.theme.colors || []).map((color) => ({
103
+ color,
104
+ variant: "solid",
105
+ class: {
106
+ content: `bg-${color} text-inverted`
107
+ }
108
+ })),
109
+ {
110
+ color: "neutral",
111
+ variant: "solid",
112
+ class: {
113
+ content: "text-inverted bg-inverted"
114
+ }
115
+ },
116
+ // Outline variants - dynamically generated for all theme colors
117
+ ...(options.theme.colors || []).map((color) => ({
118
+ color,
119
+ variant: "outline",
120
+ class: {
121
+ content: `bg-gradient-to-b from-${color}/5 to-${color}/5 bg-default text-${color} !ring !ring-inset !ring-${color}`
122
+ }
123
+ })),
124
+ {
125
+ color: "neutral",
126
+ variant: "outline",
127
+ class: {
128
+ content: "text-highlighted bg-elevated !ring !ring-inset !ring-accented"
129
+ }
130
+ }
131
+ ],
132
+ defaultVariants: {
133
+ color: "primary",
134
+ variant: "solid",
135
+ size: "sm"
136
+ }
137
+ });
138
+
72
139
  const theme = {
73
140
  __proto__: null,
141
+ dialogAlert: dialogAlert,
74
142
  dialogConfirm: dialogConfirm
75
143
  };
76
144
 
@@ -135,6 +203,24 @@ function addTemplates(options, _nuxt) {
135
203
  .animate-shake {
136
204
  animation: shake 0.5s ease-in-out;
137
205
  }
206
+
207
+ @keyframes alert-bounce {
208
+ 0% {
209
+ opacity: 0;
210
+ transform: scale(0.95);
211
+ }
212
+ 50% {
213
+ transform: scale(1.02);
214
+ }
215
+ 100% {
216
+ opacity: 1;
217
+ transform: scale(1);
218
+ }
219
+ }
220
+
221
+ .animate-alert-bounce {
222
+ animation: alert-bounce 0.2s cubic-bezier(0.34, 1.56, 0.64, 1);
223
+ }
138
224
  `;
139
225
  }
140
226
  });
@@ -0,0 +1,23 @@
1
+ import type { AppConfig } from "@nuxt/schema";
2
+ import theme from "#build/ui-elements/dialog-alert";
3
+ import type { ComponentConfig } from "../types/tv.js";
4
+ type DialogAlert = ComponentConfig<typeof theme, AppConfig, "dialogAlert">;
5
+ interface DialogAlertProps {
6
+ title?: string;
7
+ description?: string;
8
+ icon?: string;
9
+ label?: string;
10
+ color?: DialogAlert["variants"]["color"];
11
+ variant?: DialogAlert["variants"]["variant"];
12
+ onDismiss?: (() => void) | (() => Promise<void>);
13
+ ui?: DialogAlert["slots"];
14
+ }
15
+ declare const _default: typeof __VLS_export;
16
+ export default _default;
17
+ declare const __VLS_export: import("vue").DefineComponent<DialogAlertProps, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {
18
+ close: (value?: any) => any;
19
+ "update:open": (value: boolean) => any;
20
+ }, string, import("vue").PublicProps, Readonly<DialogAlertProps> & Readonly<{
21
+ onClose?: ((value?: any) => any) | undefined;
22
+ "onUpdate:open"?: ((value: boolean) => any) | undefined;
23
+ }>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -0,0 +1,76 @@
1
+ <script>
2
+ import theme from "#build/ui-elements/dialog-alert";
3
+ import { computed } from "vue";
4
+ import { DialogTitle, DialogDescription } from "reka-ui";
5
+ import { tv } from "../utils/tv";
6
+ </script>
7
+
8
+ <script setup>
9
+ const {
10
+ title = "",
11
+ description = "",
12
+ icon = void 0,
13
+ label = "Ok",
14
+ color = "neutral",
15
+ variant = "solid",
16
+ onDismiss = () => {
17
+ },
18
+ ui: uiProps = {}
19
+ } = defineProps({
20
+ title: { type: String, required: false },
21
+ description: { type: String, required: false },
22
+ icon: { type: String, required: false },
23
+ label: { type: String, required: false },
24
+ color: { type: null, required: false },
25
+ variant: { type: null, required: false },
26
+ onDismiss: { type: Function, required: false },
27
+ ui: { type: null, required: false }
28
+ });
29
+ const emits = defineEmits(["update:open", "close"]);
30
+ const ui = computed(
31
+ () => tv({
32
+ extend: tv(theme)
33
+ })({
34
+ size: "sm",
35
+ color,
36
+ variant
37
+ })
38
+ );
39
+ const dismissHandler = () => {
40
+ onDismiss();
41
+ emits("close");
42
+ };
43
+ </script>
44
+
45
+ <template>
46
+ <UModal
47
+ :dismissible="false"
48
+ :close="false"
49
+ :title="title"
50
+ :description="description"
51
+ :ui="{
52
+ content: ui.content({ class: ['animate-alert-bounce', uiProps?.content] }),
53
+ header: ui.header({ class: uiProps?.header }),
54
+ body: ui.body({ class: uiProps?.body }),
55
+ footer: ui.footer({ class: uiProps?.footer })
56
+ }">
57
+ <template #header>
58
+ <div class="relative w-full flex flex-col items-center text-center gap-3">
59
+ <UIcon v-if="icon" :name="icon" data-slot="icon" :class="ui.icon({ class: uiProps?.icon })" />
60
+ <div class="w-full">
61
+ <DialogTitle v-if="title" data-slot="title" :class="ui.title({ class: uiProps?.title })">
62
+ {{ title }}
63
+ </DialogTitle>
64
+
65
+ <DialogDescription v-if="description" :class="ui.description({ class: uiProps?.description })">
66
+ {{ description }}
67
+ </DialogDescription>
68
+ </div>
69
+ </div>
70
+ </template>
71
+
72
+ <template #footer>
73
+ <UButton :label="label" size="lg" color="neutral" variant="outline" @click="dismissHandler" />
74
+ </template>
75
+ </UModal>
76
+ </template>
@@ -0,0 +1,23 @@
1
+ import type { AppConfig } from "@nuxt/schema";
2
+ import theme from "#build/ui-elements/dialog-alert";
3
+ import type { ComponentConfig } from "../types/tv.js";
4
+ type DialogAlert = ComponentConfig<typeof theme, AppConfig, "dialogAlert">;
5
+ interface DialogAlertProps {
6
+ title?: string;
7
+ description?: string;
8
+ icon?: string;
9
+ label?: string;
10
+ color?: DialogAlert["variants"]["color"];
11
+ variant?: DialogAlert["variants"]["variant"];
12
+ onDismiss?: (() => void) | (() => Promise<void>);
13
+ ui?: DialogAlert["slots"];
14
+ }
15
+ declare const _default: typeof __VLS_export;
16
+ export default _default;
17
+ declare const __VLS_export: import("vue").DefineComponent<DialogAlertProps, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {
18
+ close: (value?: any) => any;
19
+ "update:open": (value: boolean) => any;
20
+ }, string, import("vue").PublicProps, Readonly<DialogAlertProps> & Readonly<{
21
+ onClose?: ((value?: any) => any) | undefined;
22
+ "onUpdate:open"?: ((value: boolean) => any) | undefined;
23
+ }>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -20,9 +20,7 @@ export default _default;
20
20
  declare const __VLS_export: import("vue").DefineComponent<DialogConfirmProps, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {
21
21
  close: (value?: any) => any;
22
22
  "update:open": (value: boolean) => any;
23
- "after:leave": () => any;
24
23
  }, string, import("vue").PublicProps, Readonly<DialogConfirmProps> & Readonly<{
25
24
  onClose?: ((value?: any) => any) | undefined;
26
25
  "onUpdate:open"?: ((value: boolean) => any) | undefined;
27
- "onAfter:leave"?: (() => any) | undefined;
28
26
  }>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -33,7 +33,7 @@ const {
33
33
  onDismiss: { type: Function, required: false },
34
34
  ui: { type: null, required: false }
35
35
  });
36
- const emits = defineEmits(["update:open", "close", "after:leave"]);
36
+ const emits = defineEmits(["update:open", "close"]);
37
37
  const isLoading = ref(false);
38
38
  const isComplete = ref(false);
39
39
  const isError = ref(false);
@@ -111,9 +111,7 @@ const handleClose = () => {
111
111
  header: ui.header({ class: uiProps?.header }),
112
112
  body: ui.body({ class: uiProps?.body }),
113
113
  footer: ui.footer({ class: uiProps?.footer })
114
- }"
115
- @close="emits('close', $event)"
116
- @after:leave="emits('after:leave')">
114
+ }">
117
115
  <template #header>
118
116
  <div class="relative w-full flex items-start gap-3">
119
117
  <UIcon v-if="dialogIcon" :name="dialogIcon" data-slot="icon" :class="ui.icon({ class: uiProps?.icon })" />
@@ -20,9 +20,7 @@ export default _default;
20
20
  declare const __VLS_export: import("vue").DefineComponent<DialogConfirmProps, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {
21
21
  close: (value?: any) => any;
22
22
  "update:open": (value: boolean) => any;
23
- "after:leave": () => any;
24
23
  }, string, import("vue").PublicProps, Readonly<DialogConfirmProps> & Readonly<{
25
24
  onClose?: ((value?: any) => any) | undefined;
26
25
  "onUpdate:open"?: ((value: boolean) => any) | undefined;
27
- "onAfter:leave"?: (() => any) | undefined;
28
26
  }>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -14,8 +14,18 @@ export interface DialogConfirmOptions {
14
14
  onDismiss?: CallbackFn;
15
15
  ui?: any;
16
16
  }
17
+ export interface DialogAlertOptions {
18
+ title: string;
19
+ description?: string;
20
+ icon?: string;
21
+ label?: string;
22
+ color?: Color;
23
+ variant?: Variant;
24
+ onDismiss?: CallbackFn;
25
+ ui?: any;
26
+ }
17
27
  export declare const useDialog: () => {
18
28
  confirm: (options: DialogConfirmOptions) => void;
19
- confirmNavigate: (path: string, options?: Omit<DialogConfirmOptions, "title" | "description" | "onConfirm">) => void;
29
+ alert: (options: DialogAlertOptions) => void;
20
30
  };
21
31
  export {};
@@ -1,6 +1,6 @@
1
1
  import DialogConfirm from "../components/DialogConfirm.vue";
2
+ import DialogAlert from "../components/DialogAlert.vue";
2
3
  import { useOverlay } from "#imports";
3
- import { navigateTo } from "#app";
4
4
  export const useDialog = () => {
5
5
  const overlay = useOverlay();
6
6
  const confirm = (options) => {
@@ -10,15 +10,12 @@ export const useDialog = () => {
10
10
  });
11
11
  modal.open();
12
12
  };
13
- const confirmNavigate = (path, options) => {
14
- confirm({
15
- title: "Leave this page?",
16
- description: "Are you sure you want to navigate away? Unsaved changes will be lost.",
17
- ...options,
18
- onConfirm: () => {
19
- navigateTo(path);
20
- }
13
+ const alert = (options) => {
14
+ const modal = overlay.create(DialogAlert, {
15
+ destroyOnClose: true,
16
+ props: options
21
17
  });
18
+ modal.open();
22
19
  };
23
- return { confirm, confirmNavigate };
20
+ return { confirm, alert };
24
21
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "nuxt-ui-elements",
3
- "version": "0.1.20",
3
+ "version": "0.1.22",
4
4
  "description": "A collection of beautiful, animated UI components for Nuxt applications",
5
5
  "license": "MIT",
6
6
  "repository": "https://github.com/genu/nuxt-ui-elements.git",