@macrulez/vue-form-schema 0.1.7 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (105) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +461 -180
  3. package/dist/MaskEngine-BEXwX4BK.js +144 -0
  4. package/dist/MaskEngine-CPr-fSPy.cjs +1 -0
  5. package/dist/ValidationEngine-BC4U1ef1.js +135 -0
  6. package/dist/ValidationEngine-Diz-qTFs.cjs +1 -0
  7. package/dist/_plugin-vue_export-helper-BHFhmbuH.cjs +1 -0
  8. package/dist/_plugin-vue_export-helper-CHgC5LLL.js +9 -0
  9. package/dist/core/ConditionEvaluator.d.ts.map +1 -1
  10. package/dist/core/MaskEngine.d.ts.map +1 -1
  11. package/dist/core/ValidationEngine.d.ts +13 -0
  12. package/dist/core/ValidationEngine.d.ts.map +1 -1
  13. package/dist/core/formRegistry.d.ts +33 -0
  14. package/dist/core/formRegistry.d.ts.map +1 -0
  15. package/dist/core/inferTypes.d.ts.map +1 -1
  16. package/dist/core/schemaUtils.d.ts +38 -0
  17. package/dist/core/schemaUtils.d.ts.map +1 -1
  18. package/dist/core/serverErrors.d.ts +69 -0
  19. package/dist/core/serverErrors.d.ts.map +1 -0
  20. package/dist/core/types.d.ts +22 -2
  21. package/dist/core/types.d.ts.map +1 -1
  22. package/dist/core/useForm.d.ts +4 -1
  23. package/dist/core/useForm.d.ts.map +1 -1
  24. package/dist/core/useMultiStepForm.d.ts.map +1 -1
  25. package/dist/devtools/index.d.ts +26 -0
  26. package/dist/devtools/index.d.ts.map +1 -0
  27. package/dist/devtools.cjs +1 -0
  28. package/dist/devtools.d.ts +6 -0
  29. package/dist/devtools.js +93 -0
  30. package/dist/formRegistry-Bv1eaWQ-.js +31 -0
  31. package/dist/formRegistry-DaDmXyYY.cjs +1 -0
  32. package/dist/index.cjs +1 -1
  33. package/dist/index.d.ts +5 -3
  34. package/dist/index.d.ts.map +1 -1
  35. package/dist/index.js +392 -359
  36. package/dist/openapi.cjs +1 -0
  37. package/dist/openapi.d.ts +202 -0
  38. package/dist/openapi.js +118 -0
  39. package/dist/parsers/json.d.ts.map +1 -1
  40. package/dist/parsers/openapi.d.ts +139 -0
  41. package/dist/parsers/openapi.d.ts.map +1 -0
  42. package/dist/parsers/valibot.d.ts +13 -4
  43. package/dist/parsers/valibot.d.ts.map +1 -1
  44. package/dist/parsers/yup.d.ts +10 -4
  45. package/dist/parsers/yup.d.ts.map +1 -1
  46. package/dist/parsers/zod.d.ts +18 -4
  47. package/dist/parsers/zod.d.ts.map +1 -1
  48. package/dist/schemaUtils-Cc7CwGXB.cjs +1 -0
  49. package/dist/schemaUtils-Cvlsk24U.js +337 -0
  50. package/dist/style.css +1 -0
  51. package/dist/ui/index.d.ts +1 -0
  52. package/dist/ui/index.d.ts.map +1 -1
  53. package/dist/ui/naive/index.d.ts +11 -0
  54. package/dist/ui/naive/index.d.ts.map +1 -0
  55. package/dist/ui/primevue/index.d.ts +11 -0
  56. package/dist/ui/primevue/index.d.ts.map +1 -0
  57. package/dist/ui/shadcn/index.d.ts +11 -0
  58. package/dist/ui/shadcn/index.d.ts.map +1 -0
  59. package/dist/ui/tailwind/index.d.ts +11 -0
  60. package/dist/ui/tailwind/index.d.ts.map +1 -0
  61. package/dist/ui-naive.cjs +1 -0
  62. package/dist/ui-naive.d.ts +411 -0
  63. package/dist/ui-naive.js +667 -0
  64. package/dist/ui-primevue.cjs +1 -0
  65. package/dist/ui-primevue.d.ts +411 -0
  66. package/dist/ui-primevue.js +651 -0
  67. package/dist/ui-shadcn.cjs +1 -0
  68. package/dist/ui-shadcn.d.ts +411 -0
  69. package/dist/ui-shadcn.js +650 -0
  70. package/dist/ui-tailwind.cjs +1 -0
  71. package/dist/ui-tailwind.d.ts +411 -0
  72. package/dist/ui-tailwind.js +669 -0
  73. package/dist/ui.cjs +1 -1
  74. package/dist/ui.d.ts +61 -10
  75. package/dist/ui.js +434 -299
  76. package/dist/valibot.cjs +1 -1
  77. package/dist/valibot.d.ts +35 -4
  78. package/dist/valibot.js +47 -20
  79. package/dist/yup.cjs +1 -1
  80. package/dist/yup.d.ts +33 -5
  81. package/dist/yup.js +16 -15
  82. package/dist/zod.cjs +1 -1
  83. package/dist/zod.d.ts +41 -5
  84. package/dist/zod.js +58 -28
  85. package/package.json +99 -25
  86. package/dist/MaskEngine-BqJQYybS.js +0 -233
  87. package/dist/MaskEngine-BwAs2Zb0.cjs +0 -1
  88. package/dist/__tests__/ConditionEvaluator.test.d.ts +0 -2
  89. package/dist/__tests__/ConditionEvaluator.test.d.ts.map +0 -1
  90. package/dist/__tests__/MaskEngine.test.d.ts +0 -2
  91. package/dist/__tests__/MaskEngine.test.d.ts.map +0 -1
  92. package/dist/__tests__/ValidationEngine.test.d.ts +0 -2
  93. package/dist/__tests__/ValidationEngine.test.d.ts.map +0 -1
  94. package/dist/__tests__/parsers.test.d.ts +0 -2
  95. package/dist/__tests__/parsers.test.d.ts.map +0 -1
  96. package/dist/__tests__/phase3.test.d.ts +0 -2
  97. package/dist/__tests__/phase3.test.d.ts.map +0 -1
  98. package/dist/__tests__/phase4.test.d.ts +0 -2
  99. package/dist/__tests__/phase4.test.d.ts.map +0 -1
  100. package/dist/__tests__/useFieldArray.test.d.ts +0 -2
  101. package/dist/__tests__/useFieldArray.test.d.ts.map +0 -1
  102. package/dist/__tests__/useForm.test.d.ts +0 -2
  103. package/dist/__tests__/useForm.test.d.ts.map +0 -1
  104. package/dist/__tests__/useMultiStepForm.test.d.ts +0 -2
  105. package/dist/__tests__/useMultiStepForm.test.d.ts.map +0 -1
@@ -0,0 +1,669 @@
1
+ import { defineComponent as V, computed as $, openBlock as l, createElementBlock as s, createTextVNode as N, toDisplayString as x, createCommentVNode as p, renderSlot as E, normalizeProps as J, guardReactiveProps as O, Fragment as w, renderList as F, ref as I, onMounted as Q, onUnmounted as W, createBlock as k, withCtx as q, createElementVNode as g, mergeProps as C, withModifiers as X, normalizeClass as Y, unref as D, resolveDynamicComponent as z, resolveComponent as Z } from "vue";
2
+ import { b as _, d as U, u as ee } from "./MaskEngine-BEXwX4BK.js";
3
+ import { g as M } from "./ValidationEngine-BC4U1ef1.js";
4
+ const te = { class: "mb-4" }, re = ["for"], le = {
5
+ key: 0,
6
+ class: "text-red-400 ml-0.5",
7
+ "aria-hidden": "true"
8
+ }, oe = ["id"], T = /* @__PURE__ */ V({
9
+ __name: "BaseField",
10
+ props: {
11
+ field: {},
12
+ error: {},
13
+ touched: { type: Boolean }
14
+ },
15
+ setup(e) {
16
+ const m = e, t = $(() => {
17
+ var d;
18
+ return !!(m.touched && ((d = m.error) != null && d.length));
19
+ }), c = $(() => `${m.field.name}-error`), a = $(() => ({
20
+ "aria-required": m.field.required ? "true" : void 0,
21
+ "aria-invalid": t.value ? "true" : "false",
22
+ "aria-describedby": t.value ? c.value : void 0
23
+ }));
24
+ return (d, n) => (l(), s("div", te, [
25
+ e.field.label ? (l(), s("label", {
26
+ key: 0,
27
+ for: e.field.name,
28
+ class: "block text-xs font-semibold uppercase tracking-wider text-gray-400 mb-1.5"
29
+ }, [
30
+ N(x(e.field.label) + " ", 1),
31
+ e.field.required ? (l(), s("span", le, "*")) : p("", !0)
32
+ ], 8, re)) : p("", !0),
33
+ E(d.$slots, "default", J(O(a.value))),
34
+ t.value ? (l(), s("ul", {
35
+ key: 1,
36
+ id: c.value,
37
+ class: "mt-1 space-y-0.5",
38
+ role: "alert",
39
+ "aria-live": "polite"
40
+ }, [
41
+ (l(!0), s(w, null, F(e.error, (i, f) => (l(), s("li", {
42
+ key: f,
43
+ class: "text-red-400 text-xs"
44
+ }, x(i), 1))), 128))
45
+ ], 8, oe)) : p("", !0)
46
+ ]));
47
+ }
48
+ }), ae = ["id", "type", "name", "value", "placeholder", "disabled", "required"], A = /* @__PURE__ */ V({
49
+ __name: "TextField",
50
+ props: {
51
+ field: {},
52
+ modelValue: {},
53
+ error: {},
54
+ touched: { type: Boolean }
55
+ },
56
+ emits: ["update:modelValue", "blur"],
57
+ setup(e, { emit: m }) {
58
+ const t = e, c = m, a = I(null);
59
+ let d = null;
60
+ const n = $(() => {
61
+ var i;
62
+ return !!(t.touched && ((i = t.error) != null && i.length));
63
+ });
64
+ return Q(() => {
65
+ a.value && t.field.mask && (d = _(a.value, t.field.mask));
66
+ }), W(() => d == null ? void 0 : d()), (i, f) => (l(), k(T, {
67
+ field: e.field,
68
+ error: e.error,
69
+ touched: e.touched
70
+ }, {
71
+ default: q((b) => [
72
+ g("input", C({
73
+ id: e.field.name,
74
+ ref_key: "inputRef",
75
+ ref: a,
76
+ type: e.field.type === "email" ? "email" : "text",
77
+ name: e.field.name,
78
+ value: e.modelValue ?? "",
79
+ placeholder: e.field.placeholder,
80
+ disabled: e.field.disabled === !0,
81
+ required: e.field.required
82
+ }, b, {
83
+ class: [
84
+ "w-full rounded-lg border bg-gray-900 px-3 py-2 text-sm text-gray-100 placeholder-gray-500 outline-none transition focus:ring-2 disabled:cursor-not-allowed disabled:opacity-50",
85
+ n.value ? "border-red-500 focus:ring-red-500" : "border-gray-700 focus:ring-indigo-500 focus:border-indigo-500"
86
+ ],
87
+ onInput: f[0] || (f[0] = (y) => c("update:modelValue", y.target.value)),
88
+ onBlur: f[1] || (f[1] = (y) => c("blur"))
89
+ }), null, 16, ae)
90
+ ]),
91
+ _: 1
92
+ }, 8, ["field", "error", "touched"]));
93
+ }
94
+ }), de = ["id", "name", "value", "placeholder", "disabled", "required"], P = /* @__PURE__ */ V({
95
+ __name: "NumberField",
96
+ props: {
97
+ field: {},
98
+ modelValue: {},
99
+ error: {},
100
+ touched: { type: Boolean }
101
+ },
102
+ emits: ["update:modelValue", "blur"],
103
+ setup(e, { emit: m }) {
104
+ const t = e, c = m, a = $(() => {
105
+ var n;
106
+ return !!(t.touched && ((n = t.error) != null && n.length));
107
+ });
108
+ function d(n) {
109
+ const i = n.target.value;
110
+ c("update:modelValue", i === "" ? null : Number(i));
111
+ }
112
+ return (n, i) => (l(), k(T, {
113
+ field: e.field,
114
+ error: e.error,
115
+ touched: e.touched
116
+ }, {
117
+ default: q((f) => [
118
+ g("input", C({
119
+ id: e.field.name,
120
+ type: "number",
121
+ name: e.field.name,
122
+ value: e.modelValue ?? "",
123
+ placeholder: e.field.placeholder,
124
+ disabled: e.field.disabled === !0,
125
+ required: e.field.required
126
+ }, f, {
127
+ class: [
128
+ "w-full rounded-lg border bg-gray-900 px-3 py-2 text-sm text-gray-100 placeholder-gray-500 outline-none transition focus:ring-2 disabled:cursor-not-allowed disabled:opacity-50",
129
+ a.value ? "border-red-500 focus:ring-red-500" : "border-gray-700 focus:ring-indigo-500 focus:border-indigo-500"
130
+ ],
131
+ onInput: d,
132
+ onBlur: i[0] || (i[0] = (b) => c("blur"))
133
+ }), null, 16, de)
134
+ ]),
135
+ _: 1
136
+ }, 8, ["field", "error", "touched"]));
137
+ }
138
+ }), ne = ["id", "name", "value", "placeholder", "disabled", "required"], L = /* @__PURE__ */ V({
139
+ __name: "TextareaField",
140
+ props: {
141
+ field: {},
142
+ modelValue: {},
143
+ error: {},
144
+ touched: { type: Boolean }
145
+ },
146
+ emits: ["update:modelValue", "blur"],
147
+ setup(e, { emit: m }) {
148
+ const t = e, c = m, a = $(() => {
149
+ var d;
150
+ return !!(t.touched && ((d = t.error) != null && d.length));
151
+ });
152
+ return (d, n) => (l(), k(T, {
153
+ field: e.field,
154
+ error: e.error,
155
+ touched: e.touched
156
+ }, {
157
+ default: q((i) => [
158
+ g("textarea", C({
159
+ id: e.field.name,
160
+ name: e.field.name,
161
+ value: e.modelValue ?? "",
162
+ placeholder: e.field.placeholder,
163
+ disabled: e.field.disabled === !0,
164
+ required: e.field.required
165
+ }, i, {
166
+ class: [
167
+ "w-full resize-y rounded-lg border bg-gray-900 px-3 py-2 text-sm text-gray-100 placeholder-gray-500 outline-none transition focus:ring-2 disabled:cursor-not-allowed disabled:opacity-50",
168
+ a.value ? "border-red-500 focus:ring-red-500" : "border-gray-700 focus:ring-indigo-500 focus:border-indigo-500"
169
+ ],
170
+ style: { "min-height": "80px" },
171
+ onInput: n[0] || (n[0] = (f) => c("update:modelValue", f.target.value)),
172
+ onBlur: n[1] || (n[1] = (f) => c("blur"))
173
+ }), null, 16, ne)
174
+ ]),
175
+ _: 1
176
+ }, 8, ["field", "error", "touched"]));
177
+ }
178
+ }), ie = {
179
+ key: 0,
180
+ class: "py-2 text-sm text-gray-400"
181
+ }, ue = ["id", "name", "disabled", "required"], se = ["selected"], ce = ["value", "selected"], j = /* @__PURE__ */ V({
182
+ __name: "SelectField",
183
+ props: {
184
+ field: {},
185
+ modelValue: {},
186
+ error: {},
187
+ touched: { type: Boolean }
188
+ },
189
+ emits: ["update:modelValue", "blur"],
190
+ setup(e, { emit: m }) {
191
+ const t = e, c = m, a = $(() => Array.isArray(t.field.options) ? t.field.options : []), d = $(() => {
192
+ var i;
193
+ return !!(t.touched && ((i = t.error) != null && i.length));
194
+ });
195
+ function n(i) {
196
+ const f = i.target, b = a.value.find((y) => String(y.value) === f.value);
197
+ c("update:modelValue", (b == null ? void 0 : b.value) ?? f.value);
198
+ }
199
+ return (i, f) => (l(), k(T, {
200
+ field: e.field,
201
+ error: e.error,
202
+ touched: e.touched
203
+ }, {
204
+ default: q((b) => [
205
+ e.field.optionsLoading ? (l(), s("div", ie, "Loading…")) : (l(), s("select", C({
206
+ key: 1,
207
+ id: e.field.name,
208
+ name: e.field.name,
209
+ disabled: e.field.disabled === !0 || e.field.optionsLoading,
210
+ required: e.field.required
211
+ }, b, {
212
+ class: [
213
+ "w-full rounded-lg border bg-gray-900 px-3 py-2 text-sm text-gray-100 outline-none transition focus:ring-2 disabled:cursor-not-allowed disabled:opacity-50",
214
+ d.value ? "border-red-500 focus:ring-red-500" : "border-gray-700 focus:ring-indigo-500 focus:border-indigo-500"
215
+ ],
216
+ onChange: n,
217
+ onBlur: f[0] || (f[0] = (y) => c("blur"))
218
+ }), [
219
+ g("option", {
220
+ value: "",
221
+ disabled: "",
222
+ selected: e.modelValue === null || e.modelValue === void 0 || e.modelValue === "",
223
+ class: "bg-gray-800"
224
+ }, x(e.field.placeholder ?? "Select an option"), 9, se),
225
+ (l(!0), s(w, null, F(a.value, (y) => (l(), s("option", {
226
+ key: String(y.value),
227
+ value: String(y.value),
228
+ selected: e.modelValue === y.value,
229
+ class: "bg-gray-800"
230
+ }, x(y.label), 9, ce))), 128))
231
+ ], 16, ue))
232
+ ]),
233
+ _: 1
234
+ }, 8, ["field", "error", "touched"]));
235
+ }
236
+ }), me = { class: "flex cursor-pointer items-center gap-2.5" }, fe = ["id", "name", "checked", "disabled", "required", "aria-checked"], be = {
237
+ key: 0,
238
+ class: "text-sm text-gray-200"
239
+ }, K = /* @__PURE__ */ V({
240
+ __name: "CheckboxField",
241
+ props: {
242
+ field: {},
243
+ modelValue: { type: [Boolean, null] },
244
+ error: {},
245
+ touched: { type: Boolean }
246
+ },
247
+ emits: ["update:modelValue", "blur"],
248
+ setup(e, { emit: m }) {
249
+ const t = m;
250
+ return (c, a) => (l(), k(T, {
251
+ field: { ...e.field, label: void 0 },
252
+ error: e.error,
253
+ touched: e.touched
254
+ }, {
255
+ default: q((d) => [
256
+ g("label", me, [
257
+ g("input", C({
258
+ id: e.field.name,
259
+ type: "checkbox",
260
+ name: e.field.name,
261
+ checked: !!e.modelValue,
262
+ disabled: e.field.disabled === !0,
263
+ required: e.field.required,
264
+ "aria-checked": e.modelValue ? "true" : "false"
265
+ }, d, {
266
+ class: "h-4 w-4 cursor-pointer rounded border-gray-600 bg-gray-900 text-indigo-500 accent-indigo-500 disabled:cursor-not-allowed disabled:opacity-50",
267
+ onChange: a[0] || (a[0] = (n) => t("update:modelValue", n.target.checked)),
268
+ onBlur: a[1] || (a[1] = (n) => t("blur"))
269
+ }), null, 16, fe),
270
+ e.field.label ? (l(), s("span", be, x(e.field.label), 1)) : p("", !0)
271
+ ])
272
+ ]),
273
+ _: 1
274
+ }, 8, ["field", "error", "touched"]));
275
+ }
276
+ }), ge = ["aria-required", "aria-invalid", "aria-describedby"], ye = {
277
+ key: 0,
278
+ class: "block text-xs font-semibold uppercase tracking-wider text-gray-400 mb-2"
279
+ }, he = {
280
+ key: 0,
281
+ class: "text-red-400 ml-0.5",
282
+ "aria-hidden": "true"
283
+ }, ve = { class: "space-y-2" }, xe = ["name", "value", "checked", "disabled", "onChange"], $e = { class: "text-sm text-gray-200" }, pe = ["id"], G = /* @__PURE__ */ V({
284
+ __name: "RadioField",
285
+ props: {
286
+ field: {},
287
+ modelValue: {},
288
+ error: {},
289
+ touched: { type: Boolean }
290
+ },
291
+ emits: ["update:modelValue", "blur"],
292
+ setup(e, { emit: m }) {
293
+ const t = e, c = m, a = $(() => {
294
+ var i;
295
+ return !!(t.touched && ((i = t.error) != null && i.length));
296
+ }), d = $(() => `${t.field.name}-error`), n = $(() => Array.isArray(t.field.options) ? t.field.options : []);
297
+ return (i, f) => (l(), s("fieldset", {
298
+ class: "mb-4",
299
+ "aria-required": e.field.required ? "true" : void 0,
300
+ "aria-invalid": a.value ? "true" : "false",
301
+ "aria-describedby": a.value ? d.value : void 0
302
+ }, [
303
+ e.field.label ? (l(), s("legend", ye, [
304
+ N(x(e.field.label) + " ", 1),
305
+ e.field.required ? (l(), s("span", he, "*")) : p("", !0)
306
+ ])) : p("", !0),
307
+ g("div", ve, [
308
+ (l(!0), s(w, null, F(n.value, (b) => (l(), s("label", {
309
+ key: String(b.value),
310
+ class: "flex cursor-pointer items-center gap-2.5"
311
+ }, [
312
+ g("input", {
313
+ type: "radio",
314
+ name: e.field.name,
315
+ value: String(b.value),
316
+ checked: e.modelValue === b.value,
317
+ disabled: e.field.disabled === !0,
318
+ class: "h-4 w-4 cursor-pointer border-gray-600 bg-gray-900 text-indigo-500 accent-indigo-500 disabled:cursor-not-allowed disabled:opacity-50",
319
+ onChange: (y) => c("update:modelValue", b.value),
320
+ onBlur: f[0] || (f[0] = (y) => c("blur"))
321
+ }, null, 40, xe),
322
+ g("span", $e, x(b.label), 1)
323
+ ]))), 128))
324
+ ]),
325
+ a.value ? (l(), s("ul", {
326
+ key: 1,
327
+ id: d.value,
328
+ class: "mt-1 space-y-0.5",
329
+ role: "alert",
330
+ "aria-live": "polite"
331
+ }, [
332
+ (l(!0), s(w, null, F(e.error, (b, y) => (l(), s("li", {
333
+ key: y,
334
+ class: "text-red-400 text-xs"
335
+ }, x(b), 1))), 128))
336
+ ], 8, pe)) : p("", !0)
337
+ ], 8, ge));
338
+ }
339
+ }), ke = ["id", "name", "value", "disabled", "required"], H = /* @__PURE__ */ V({
340
+ __name: "DateField",
341
+ props: {
342
+ field: {},
343
+ modelValue: {},
344
+ error: {},
345
+ touched: { type: Boolean }
346
+ },
347
+ emits: ["update:modelValue", "blur"],
348
+ setup(e, { emit: m }) {
349
+ const t = e, c = m, a = $(() => {
350
+ var d;
351
+ return !!(t.touched && ((d = t.error) != null && d.length));
352
+ });
353
+ return (d, n) => (l(), k(T, {
354
+ field: e.field,
355
+ error: e.error,
356
+ touched: e.touched
357
+ }, {
358
+ default: q((i) => [
359
+ g("input", C({
360
+ id: e.field.name,
361
+ type: "date",
362
+ name: e.field.name,
363
+ value: e.modelValue ?? "",
364
+ disabled: e.field.disabled === !0,
365
+ required: e.field.required
366
+ }, i, {
367
+ class: [
368
+ "w-full rounded-lg border bg-gray-900 px-3 py-2 text-sm text-gray-100 outline-none transition focus:ring-2 disabled:cursor-not-allowed disabled:opacity-50",
369
+ a.value ? "border-red-500 focus:ring-red-500" : "border-gray-700 focus:ring-indigo-500 focus:border-indigo-500"
370
+ ],
371
+ onInput: n[0] || (n[0] = (f) => c("update:modelValue", f.target.value)),
372
+ onBlur: n[1] || (n[1] = (f) => c("blur"))
373
+ }), null, 16, ke)
374
+ ]),
375
+ _: 1
376
+ }, 8, ["field", "error", "touched"]));
377
+ }
378
+ }), Ve = ["id", "name", "accept", "multiple", "disabled", "required"], we = { class: "pointer-events-none space-y-1" }, Fe = { class: "text-sm text-gray-300" }, Be = {
379
+ key: 0,
380
+ class: "text-xs text-gray-500"
381
+ }, qe = {
382
+ key: 0,
383
+ class: "mt-2 space-y-1"
384
+ }, Ce = { class: "truncate text-gray-200" }, Te = { class: "ml-2 shrink-0 text-xs text-gray-500" }, Se = ["aria-label", "onClick"], Re = /* @__PURE__ */ V({
385
+ __name: "FileField",
386
+ props: {
387
+ field: {},
388
+ modelValue: {},
389
+ error: {},
390
+ touched: { type: Boolean }
391
+ },
392
+ emits: ["update:modelValue", "blur"],
393
+ setup(e, { emit: m }) {
394
+ const t = e, c = m, a = I(!1), d = I(null), n = $(() => t.modelValue ? Array.isArray(t.modelValue) ? t.modelValue : [t.modelValue] : []), i = $(() => t.field.multiple ?? !1);
395
+ function f(o) {
396
+ if (!o || o.length === 0) {
397
+ c("update:modelValue", null);
398
+ return;
399
+ }
400
+ c("update:modelValue", i.value ? Array.from(o) : o[0]);
401
+ }
402
+ function b(o) {
403
+ f(o.target.files), c("blur");
404
+ }
405
+ function y(o) {
406
+ var r;
407
+ a.value = !1, o.preventDefault(), f(((r = o.dataTransfer) == null ? void 0 : r.files) ?? null), c("blur");
408
+ }
409
+ function S(o) {
410
+ const r = n.value.filter((h, v) => v !== o);
411
+ r.length === 0 ? (c("update:modelValue", null), d.value && (d.value.value = "")) : c("update:modelValue", i.value ? r : r[0]);
412
+ }
413
+ function R(o) {
414
+ return o < 1024 ? `${o} B` : o < 1024 * 1024 ? `${(o / 1024).toFixed(1)} KB` : `${(o / (1024 * 1024)).toFixed(1)} MB`;
415
+ }
416
+ return (o, r) => (l(), k(T, {
417
+ field: e.field,
418
+ error: e.error,
419
+ touched: e.touched
420
+ }, {
421
+ default: q((h) => {
422
+ var v;
423
+ return [
424
+ g("div", {
425
+ class: Y([
426
+ "relative rounded-lg border-2 border-dashed p-6 text-center transition",
427
+ a.value ? "border-indigo-500 bg-indigo-500/10" : e.touched && ((v = e.error) != null && v.length) ? "border-red-500 bg-red-500/5" : "border-gray-700 bg-gray-900 hover:border-gray-500"
428
+ ]),
429
+ onDragover: r[0] || (r[0] = X((u) => a.value = !0, ["prevent"])),
430
+ onDragleave: r[1] || (r[1] = (u) => a.value = !1),
431
+ onDrop: y
432
+ }, [
433
+ g("input", C({
434
+ id: e.field.name,
435
+ ref_key: "inputRef",
436
+ ref: d,
437
+ type: "file",
438
+ name: e.field.name,
439
+ accept: e.field.accept,
440
+ multiple: i.value,
441
+ disabled: e.field.disabled === !0,
442
+ required: e.field.required
443
+ }, h, {
444
+ class: "absolute inset-0 h-full w-full cursor-pointer opacity-0 disabled:cursor-not-allowed",
445
+ onChange: b
446
+ }), null, 16, Ve),
447
+ g("div", we, [
448
+ r[2] || (r[2] = g("div", { class: "text-2xl" }, "📁", -1)),
449
+ g("p", Fe, x(a.value ? "Drop files here" : "Click to upload or drag & drop"), 1),
450
+ e.field.accept ? (l(), s("p", Be, x(e.field.accept), 1)) : p("", !0)
451
+ ])
452
+ ], 34),
453
+ n.value.length ? (l(), s("ul", qe, [
454
+ (l(!0), s(w, null, F(n.value, (u, B) => (l(), s("li", {
455
+ key: `${u.name}-${B}`,
456
+ class: "flex items-center justify-between rounded-lg border border-gray-700 bg-gray-900 px-3 py-2 text-sm"
457
+ }, [
458
+ g("span", Ce, x(u.name), 1),
459
+ g("span", Te, x(R(u.size)), 1),
460
+ g("button", {
461
+ type: "button",
462
+ "aria-label": `Remove ${u.name}`,
463
+ class: "ml-2 shrink-0 text-gray-500 hover:text-red-400 transition",
464
+ onClick: (Pe) => S(B)
465
+ }, " × ", 8, Se)
466
+ ]))), 128))
467
+ ])) : p("", !0)
468
+ ];
469
+ }),
470
+ _: 1
471
+ }, 8, ["field", "error", "touched"]));
472
+ }
473
+ }), Ae = { class: "mb-4" }, De = {
474
+ key: 0,
475
+ class: "block text-xs font-semibold uppercase tracking-wider text-gray-400 mb-2"
476
+ }, Ee = { class: "flex-1 space-y-0" }, Ie = ["onClick"], Ne = /* @__PURE__ */ V({
477
+ __name: "ArrayField",
478
+ props: {
479
+ field: {},
480
+ form: {},
481
+ components: {}
482
+ },
483
+ setup(e) {
484
+ const m = e, t = U(), c = {
485
+ text: A,
486
+ email: A,
487
+ number: P,
488
+ textarea: L,
489
+ select: j,
490
+ checkbox: K,
491
+ radio: G,
492
+ date: H
493
+ };
494
+ function a(o) {
495
+ var r;
496
+ return o.component ? o.component : ((r = m.components) == null ? void 0 : r[o.type]) ?? t[o.type] ?? c[o.type] ?? null;
497
+ }
498
+ const { rows: d, append: n, remove: i } = ee(m.form, m.field.name);
499
+ function f(o) {
500
+ return M(m.form.values.value, o.name);
501
+ }
502
+ function b(o, r) {
503
+ m.form.setField(o.name, r);
504
+ }
505
+ function y(o) {
506
+ var h;
507
+ const r = m.form;
508
+ (h = r.touchField) == null || h.call(r, o.name);
509
+ }
510
+ function S(o) {
511
+ return m.form.errors.value[o.name] ?? [];
512
+ }
513
+ function R(o) {
514
+ return m.form.touched.value[o.name] ?? !1;
515
+ }
516
+ return (o, r) => (l(), s("div", Ae, [
517
+ e.field.label ? (l(), s("div", De, x(e.field.label), 1)) : p("", !0),
518
+ (l(!0), s(w, null, F(D(d), (h) => (l(), s("div", {
519
+ key: h.key,
520
+ class: "mb-2 flex items-start gap-2 rounded-lg border border-gray-700 bg-gray-900 p-3"
521
+ }, [
522
+ g("div", Ee, [
523
+ (l(!0), s(w, null, F(h.fields, (v) => (l(), s(w, {
524
+ key: v.name
525
+ }, [
526
+ a(v) ? (l(), k(z(a(v)), {
527
+ key: 0,
528
+ field: v,
529
+ "model-value": f(v),
530
+ error: S(v),
531
+ touched: R(v),
532
+ "onUpdate:modelValue": (u) => b(v, u),
533
+ onBlur: (u) => y(v)
534
+ }, null, 40, ["field", "model-value", "error", "touched", "onUpdate:modelValue", "onBlur"])) : p("", !0)
535
+ ], 64))), 128))
536
+ ]),
537
+ g("button", {
538
+ type: "button",
539
+ class: "mt-7 shrink-0 rounded px-2 py-1 text-xs text-gray-500 hover:bg-red-500/10 hover:text-red-400 transition",
540
+ onClick: (v) => D(i)(h.index)
541
+ }, " Remove ", 8, Ie)
542
+ ]))), 128)),
543
+ g("button", {
544
+ type: "button",
545
+ class: "mt-1 rounded-lg border border-dashed border-gray-600 px-4 py-2 text-sm text-gray-400 hover:border-indigo-500 hover:text-indigo-400 transition",
546
+ onClick: r[0] || (r[0] = (h) => D(n)())
547
+ }, " + Add row ")
548
+ ]));
549
+ }
550
+ }), ze = {
551
+ key: 1,
552
+ class: "mb-4 rounded-lg border border-gray-700 p-4"
553
+ }, Ue = {
554
+ key: 0,
555
+ class: "px-1 text-xs font-semibold uppercase tracking-wider text-gray-400"
556
+ }, Me = ["disabled"], Ge = /* @__PURE__ */ V({
557
+ __name: "TailwindFormRenderer",
558
+ props: {
559
+ form: {},
560
+ components: {},
561
+ submitLabel: {},
562
+ fields: {}
563
+ },
564
+ emits: ["submit"],
565
+ setup(e, { emit: m }) {
566
+ const t = e, c = U(), a = m, d = {
567
+ text: A,
568
+ email: A,
569
+ number: P,
570
+ textarea: L,
571
+ select: j,
572
+ checkbox: K,
573
+ radio: G,
574
+ date: H,
575
+ file: Re
576
+ };
577
+ function n(r) {
578
+ var h;
579
+ return r.component ? r.component : ((h = t.components) == null ? void 0 : h[r.type]) ?? c[r.type] ?? d[r.type] ?? null;
580
+ }
581
+ function i(r) {
582
+ return M(t.form.values.value, r.name);
583
+ }
584
+ function f(r, h) {
585
+ t.form.setField(r.name, h);
586
+ }
587
+ function b(r) {
588
+ var v;
589
+ const h = t.form;
590
+ (v = h.touchField) == null || v.call(h, r.name);
591
+ }
592
+ function y(r) {
593
+ return t.form.errors.value[r.name] ?? [];
594
+ }
595
+ function S(r) {
596
+ return t.form.touched.value[r.name] ?? !1;
597
+ }
598
+ const R = $(
599
+ () => (t.fields ?? t.form.fields.value).filter((r) => r.visible !== !1)
600
+ );
601
+ async function o(r) {
602
+ r.preventDefault(), await t.form.submit(), a("submit");
603
+ }
604
+ return (r, h) => {
605
+ const v = Z("TailwindFormRenderer", !0);
606
+ return l(), s("form", {
607
+ novalidate: "",
608
+ onSubmit: o
609
+ }, [
610
+ (l(!0), s(w, null, F(R.value, (u) => (l(), s(w, {
611
+ key: u.name
612
+ }, [
613
+ r.$slots[`field-${u.name}`] ? E(r.$slots, `field-${u.name}`, {
614
+ key: 0,
615
+ field: u,
616
+ value: i(u),
617
+ error: y(u),
618
+ touched: S(u),
619
+ setValue: (B) => f(u, B),
620
+ touch: () => b(u)
621
+ }) : u.type === "group" ? (l(), s("fieldset", ze, [
622
+ u.label ? (l(), s("legend", Ue, x(u.label), 1)) : p("", !0),
623
+ u.fields ? (l(), k(v, {
624
+ key: 1,
625
+ form: e.form,
626
+ fields: u.fields,
627
+ components: e.components
628
+ }, null, 8, ["form", "fields", "components"])) : p("", !0)
629
+ ])) : u.type === "array" ? (l(), k(Ne, {
630
+ key: 2,
631
+ field: u,
632
+ form: e.form,
633
+ components: e.components
634
+ }, null, 8, ["field", "form", "components"])) : n(u) ? (l(), k(z(n(u)), {
635
+ key: 3,
636
+ field: u,
637
+ "model-value": i(u),
638
+ error: y(u),
639
+ touched: S(u),
640
+ "onUpdate:modelValue": (B) => f(u, B),
641
+ onBlur: (B) => b(u)
642
+ }, null, 40, ["field", "model-value", "error", "touched", "onUpdate:modelValue", "onBlur"])) : p("", !0)
643
+ ], 64))), 128)),
644
+ E(r.$slots, "submit", {
645
+ isSubmitting: e.form.isSubmitting.value,
646
+ isValid: e.form.isValid.value
647
+ }, () => [
648
+ g("button", {
649
+ type: "submit",
650
+ disabled: e.form.isSubmitting.value,
651
+ class: "mt-2 rounded-lg bg-indigo-600 px-5 py-2 text-sm font-medium text-white transition hover:bg-indigo-500 disabled:cursor-not-allowed disabled:opacity-40"
652
+ }, x(e.submitLabel ?? "Submit"), 9, Me)
653
+ ])
654
+ ], 32);
655
+ };
656
+ }
657
+ });
658
+ export {
659
+ Ge as TailwindFormRenderer,
660
+ Ne as TwArrayField,
661
+ K as TwCheckboxField,
662
+ H as TwDateField,
663
+ Re as TwFileField,
664
+ P as TwNumberField,
665
+ G as TwRadioField,
666
+ j as TwSelectField,
667
+ A as TwTextField,
668
+ L as TwTextareaField
669
+ };