shadcn-zod-formkit 1.15.0 → 1.16.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.
package/dist/index.d.mts CHANGED
@@ -73,13 +73,15 @@ declare enum InputTypes {
73
73
  REPEATER = "repeater",
74
74
  MULTI_SELECT = "multi_select",
75
75
  COMBOBOX = "COMBO_BOX",
76
- SORTABLE_LIST = "sortable_list"
76
+ SORTABLE_LIST = "sortable_list",
77
+ REPEATER_TABS = "repeater_tabs"
77
78
  }
78
79
  declare const inputFieldComp: InputTypes[];
79
80
 
80
81
  interface FieldProps<T = Record<string, any>> {
81
82
  name: keyof T;
82
83
  label: string;
84
+ tabLabelField?: string;
83
85
  childrenPosition?: 'up' | 'down';
84
86
  children?: ReactNode | ((item: any, index: number) => ReactNode);
85
87
  defaultValue?: any;
@@ -193,6 +195,8 @@ interface FormResp<T> {
193
195
  data: T;
194
196
  }
195
197
  interface Props$4<T extends Record<string, any>> {
198
+ showIcon?: boolean;
199
+ showFormHeader?: boolean;
196
200
  formTitle: string;
197
201
  formSubTitle?: string;
198
202
  readOnly?: boolean;
@@ -208,7 +212,7 @@ interface Props$4<T extends Record<string, any>> {
208
212
  children?: ReactNode;
209
213
  childrenHeader?: ReactNode;
210
214
  }
211
- declare const DynamicForm: <T extends Record<string, any>>({ formTitle, formSubTitle, fields, readOnly, record, onSubmit, extraValidations, children, childrenHeader, withErrorsAlert, errorAlertPosition, withCard, submitBtnClass, submitBtnLabel, }: Props$4<T>) => react_jsx_runtime.JSX.Element;
215
+ declare const DynamicForm: <T extends Record<string, any>>({ formTitle, formSubTitle, fields, readOnly, record, onSubmit, extraValidations, children, childrenHeader, showIcon, showFormHeader, withErrorsAlert, errorAlertPosition, withCard, submitBtnClass, submitBtnLabel, }: Props$4<T>) => react_jsx_runtime.JSX.Element;
212
216
 
213
217
  declare const DynamicFormExample: () => react_jsx_runtime.JSX.Element;
214
218
  declare const mockFields: Array<FieldProps | FieldProps[]>;
package/dist/index.d.ts CHANGED
@@ -73,13 +73,15 @@ declare enum InputTypes {
73
73
  REPEATER = "repeater",
74
74
  MULTI_SELECT = "multi_select",
75
75
  COMBOBOX = "COMBO_BOX",
76
- SORTABLE_LIST = "sortable_list"
76
+ SORTABLE_LIST = "sortable_list",
77
+ REPEATER_TABS = "repeater_tabs"
77
78
  }
78
79
  declare const inputFieldComp: InputTypes[];
79
80
 
80
81
  interface FieldProps<T = Record<string, any>> {
81
82
  name: keyof T;
82
83
  label: string;
84
+ tabLabelField?: string;
83
85
  childrenPosition?: 'up' | 'down';
84
86
  children?: ReactNode | ((item: any, index: number) => ReactNode);
85
87
  defaultValue?: any;
@@ -193,6 +195,8 @@ interface FormResp<T> {
193
195
  data: T;
194
196
  }
195
197
  interface Props$4<T extends Record<string, any>> {
198
+ showIcon?: boolean;
199
+ showFormHeader?: boolean;
196
200
  formTitle: string;
197
201
  formSubTitle?: string;
198
202
  readOnly?: boolean;
@@ -208,7 +212,7 @@ interface Props$4<T extends Record<string, any>> {
208
212
  children?: ReactNode;
209
213
  childrenHeader?: ReactNode;
210
214
  }
211
- declare const DynamicForm: <T extends Record<string, any>>({ formTitle, formSubTitle, fields, readOnly, record, onSubmit, extraValidations, children, childrenHeader, withErrorsAlert, errorAlertPosition, withCard, submitBtnClass, submitBtnLabel, }: Props$4<T>) => react_jsx_runtime.JSX.Element;
215
+ declare const DynamicForm: <T extends Record<string, any>>({ formTitle, formSubTitle, fields, readOnly, record, onSubmit, extraValidations, children, childrenHeader, showIcon, showFormHeader, withErrorsAlert, errorAlertPosition, withCard, submitBtnClass, submitBtnLabel, }: Props$4<T>) => react_jsx_runtime.JSX.Element;
212
216
 
213
217
  declare const DynamicFormExample: () => react_jsx_runtime.JSX.Element;
214
218
  declare const mockFields: Array<FieldProps | FieldProps[]>;
package/dist/index.mjs CHANGED
@@ -1,4 +1,4 @@
1
- import { ChevronDownIcon, ChevronLeftIcon, ChevronRightIcon, CheckIcon, XIcon, MinusIcon, GripVerticalIcon, ChevronUpIcon, CalendarIcon, EyeOff, Eye, Pencil, Loader2, Save, Plus, MessageCircleWarning, Info, CircleCheck, CircleX, ChevronsUpDown, Check, Trash2, Upload, GripVertical, SearchIcon, CircleIcon } from 'lucide-react';
1
+ import { ChevronDownIcon, ChevronLeftIcon, ChevronRightIcon, CheckIcon, XIcon, MinusIcon, GripVerticalIcon, ChevronUpIcon, CalendarIcon, EyeOff, Eye, Pencil, Loader2, Save, Plus, MessageCircleWarning, Info, CircleCheck, CircleX, Trash2, ChevronsUpDown, Check, Upload, GripVertical, SearchIcon, CircleIcon } from 'lucide-react';
2
2
  import { InfoCircledIcon } from '@radix-ui/react-icons';
3
3
  import { cva } from 'class-variance-authority';
4
4
  import { twMerge } from 'tailwind-merge';
@@ -26,6 +26,7 @@ import { Toaster as Toaster$1 } from 'sonner';
26
26
  import * as SwitchPrimitive from '@radix-ui/react-switch';
27
27
  import * as TooltipPrimitive from '@radix-ui/react-tooltip';
28
28
  import { Command as Command$1 } from 'cmdk';
29
+ import * as TabsPrimitive from '@radix-ui/react-tabs';
29
30
  import * as SliderPrimitive from '@radix-ui/react-slider';
30
31
  import { useSensors, useSensor, PointerSensor, KeyboardSensor, DndContext, closestCenter } from '@dnd-kit/core';
31
32
  import { sortableKeyboardCoordinates, SortableContext, verticalListSortingStrategy, arrayMove, useSortable } from '@dnd-kit/sortable';
@@ -236,9 +237,11 @@ var InputTypes = /* @__PURE__ */ ((InputTypes2) => {
236
237
  InputTypes2["MULTI_SELECT"] = "multi_select";
237
238
  InputTypes2["COMBOBOX"] = "COMBO_BOX";
238
239
  InputTypes2["SORTABLE_LIST"] = "sortable_list";
240
+ InputTypes2["REPEATER_TABS"] = "repeater_tabs";
239
241
  return InputTypes2;
240
242
  })(InputTypes || {});
241
243
  var inputFieldComp = [
244
+ "repeater_tabs" /* REPEATER_TABS */,
242
245
  "sortable_list" /* SORTABLE_LIST */,
243
246
  "COMBO_BOX" /* COMBOBOX */,
244
247
  "multi_select" /* MULTI_SELECT */,
@@ -4583,6 +4586,161 @@ var FieldRepeater = ({ form, input, isSubmitting }) => {
4583
4586
  }
4584
4587
  );
4585
4588
  };
4589
+ function Tabs({
4590
+ className,
4591
+ ...props
4592
+ }) {
4593
+ return /* @__PURE__ */ jsx(
4594
+ TabsPrimitive.Root,
4595
+ {
4596
+ "data-slot": "tabs",
4597
+ className: cn("flex flex-col gap-2", className),
4598
+ ...props
4599
+ }
4600
+ );
4601
+ }
4602
+ function TabsList({
4603
+ className,
4604
+ ...props
4605
+ }) {
4606
+ return /* @__PURE__ */ jsx(
4607
+ TabsPrimitive.List,
4608
+ {
4609
+ "data-slot": "tabs-list",
4610
+ className: cn(
4611
+ "bg-muted text-muted-foreground inline-flex h-9 w-fit items-center justify-center rounded-lg p-[3px]",
4612
+ className
4613
+ ),
4614
+ ...props
4615
+ }
4616
+ );
4617
+ }
4618
+ function TabsTrigger({
4619
+ className,
4620
+ ...props
4621
+ }) {
4622
+ return /* @__PURE__ */ jsx(
4623
+ TabsPrimitive.Trigger,
4624
+ {
4625
+ "data-slot": "tabs-trigger",
4626
+ className: cn(
4627
+ "data-[state=active]:bg-background dark:data-[state=active]:text-foreground focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:outline-ring dark:data-[state=active]:border-input dark:data-[state=active]:bg-input/30 text-foreground dark:text-muted-foreground inline-flex h-[calc(100%-1px)] flex-1 items-center justify-center gap-1.5 rounded-md border border-transparent px-2 py-1 text-sm font-medium whitespace-nowrap transition-[color,box-shadow] focus-visible:ring-[3px] focus-visible:outline-1 disabled:pointer-events-none disabled:opacity-50 data-[state=active]:shadow-sm [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
4628
+ className
4629
+ ),
4630
+ ...props
4631
+ }
4632
+ );
4633
+ }
4634
+ function TabsContent({
4635
+ className,
4636
+ ...props
4637
+ }) {
4638
+ return /* @__PURE__ */ jsx(
4639
+ TabsPrimitive.Content,
4640
+ {
4641
+ "data-slot": "tabs-content",
4642
+ className: cn("flex-1 outline-none", className),
4643
+ ...props
4644
+ }
4645
+ );
4646
+ }
4647
+ var RepeaterTabsInput = class extends BaseInput {
4648
+ render() {
4649
+ const { input, form, isSubmitting } = this;
4650
+ return /* @__PURE__ */ jsx(FieldRepeaterTabs, { form, input, isSubmitting });
4651
+ }
4652
+ };
4653
+ var FieldRepeaterTabs = ({ form, input, isSubmitting }) => {
4654
+ const { control } = form;
4655
+ const { fields, append, remove } = useFieldArray({
4656
+ control,
4657
+ name: input.name
4658
+ });
4659
+ const [activeTab, setActiveTab] = useState(fields[0]?.id ?? "");
4660
+ const canAdd = !input.maxItems || fields.length < input.maxItems;
4661
+ const canRemove = fields.length > (input.minItems ?? 0);
4662
+ const handleAdd = () => {
4663
+ const newItem = { id: `tab-${Date.now()}` };
4664
+ append(newItem);
4665
+ setActiveTab(newItem.id);
4666
+ };
4667
+ const handleRemove = (index) => {
4668
+ const removedId = fields[index].id;
4669
+ remove(index);
4670
+ if (activeTab === removedId && fields.length > 1) {
4671
+ const nextTab = fields[index - 1] ?? fields[0];
4672
+ if (nextTab) setActiveTab(nextTab.id);
4673
+ }
4674
+ };
4675
+ return /* @__PURE__ */ jsx(
4676
+ FormField,
4677
+ {
4678
+ control,
4679
+ name: input.name,
4680
+ render: () => /* @__PURE__ */ jsxs(FormItem, { className: input.className, children: [
4681
+ input.label && /* @__PURE__ */ jsx(FormLabel, { children: /* @__PURE__ */ jsx("b", { children: input.label }) }),
4682
+ /* @__PURE__ */ jsx(FormControl, { children: /* @__PURE__ */ jsx("div", { className: "space-y-3", children: /* @__PURE__ */ jsxs(Tabs, { value: activeTab, onValueChange: setActiveTab, className: "w-full", children: [
4683
+ /* @__PURE__ */ jsxs(TabsList, { className: "flex w-full justify-start overflow-x-auto", children: [
4684
+ fields.map((item, index) => /* @__PURE__ */ jsxs("div", { className: "flex items-center", children: [
4685
+ /* @__PURE__ */ jsx(TabsTrigger, { value: item.id, className: "flex items-center gap-1", children: input.tabLabelField ? form.watch(`${input.name}.${index}.${input.tabLabelField}`) || `Item ${index + 1}` : `Item ${index + 1}` }),
4686
+ canRemove && /* @__PURE__ */ jsx(
4687
+ Button,
4688
+ {
4689
+ type: "button",
4690
+ size: "icon",
4691
+ variant: "ghost",
4692
+ onClick: () => handleRemove(index),
4693
+ children: /* @__PURE__ */ jsx(Trash2, { size: 14 })
4694
+ }
4695
+ )
4696
+ ] }, item.id)),
4697
+ canAdd && /* @__PURE__ */ jsxs(
4698
+ Button,
4699
+ {
4700
+ type: "button",
4701
+ variant: "secondary",
4702
+ size: "sm",
4703
+ onClick: handleAdd,
4704
+ disabled: isSubmitting,
4705
+ className: "ml-2",
4706
+ children: [
4707
+ /* @__PURE__ */ jsx(Plus, { size: 14, className: "mr-1" }),
4708
+ " Agregar"
4709
+ ]
4710
+ }
4711
+ )
4712
+ ] }),
4713
+ fields.map((item, index) => /* @__PURE__ */ jsx(TabsContent, { value: item.id, className: "mt-4", children: input.repeaterFields?.map((fieldGroup, groupIndex) => {
4714
+ const group = Array.isArray(fieldGroup) ? fieldGroup : [fieldGroup];
4715
+ const cols = group.length;
4716
+ return /* @__PURE__ */ jsx("div", { className: `grid gap-3 grid-cols-${cols}`, children: group.map((subField) => /* @__PURE__ */ jsx(
4717
+ FormField,
4718
+ {
4719
+ control,
4720
+ name: `${input.name}.${index}.${subField.name}`,
4721
+ render: ({ field, fieldState }) => /* @__PURE__ */ jsxs(FormItem, { className: "flex-1", children: [
4722
+ /* @__PURE__ */ jsx(FormLabel, { children: subField.label }),
4723
+ /* @__PURE__ */ jsx(FormControl, { children: /* @__PURE__ */ jsx(
4724
+ Input,
4725
+ {
4726
+ placeholder: subField.placeHolder,
4727
+ disabled: subField.disabled || isSubmitting,
4728
+ ...field
4729
+ }
4730
+ ) }),
4731
+ /* @__PURE__ */ jsx(FormMessage, { children: fieldState.error?.message })
4732
+ ] })
4733
+ },
4734
+ `${input.name}.${index}.${subField.name}`
4735
+ )) }, groupIndex);
4736
+ }) }, item.id))
4737
+ ] }) }) }),
4738
+ input.description && /* @__PURE__ */ jsx(FormDescription, { children: input.description }),
4739
+ /* @__PURE__ */ jsx(FormMessage, {})
4740
+ ] })
4741
+ }
4742
+ );
4743
+ };
4586
4744
  var SelectInput = class extends BaseInput {
4587
4745
  render() {
4588
4746
  const { input, form, isSubmitting } = this;
@@ -5262,6 +5420,7 @@ var inputMap = {
5262
5420
  ["multi_select" /* MULTI_SELECT */]: MultiSelectInput,
5263
5421
  ["COMBO_BOX" /* COMBOBOX */]: ComboboxInput,
5264
5422
  ["sortable_list" /* SORTABLE_LIST */]: SortableListInput,
5423
+ ["repeater_tabs" /* REPEATER_TABS */]: RepeaterTabsInput,
5265
5424
  //ToDos: ============================================================
5266
5425
  ["slider" /* SLIDER */]: SliderInput,
5267
5426
  //ToDo: // PENDIENTE ... VISUALMENTE NO SE VE BIEN.!!!
@@ -5426,6 +5585,8 @@ var DynamicForm = ({
5426
5585
  extraValidations,
5427
5586
  children,
5428
5587
  childrenHeader,
5588
+ showIcon = true,
5589
+ showFormHeader = true,
5429
5590
  withErrorsAlert = true,
5430
5591
  errorAlertPosition = "up",
5431
5592
  withCard = false,
@@ -5455,9 +5616,9 @@ var DynamicForm = ({
5455
5616
  }
5456
5617
  };
5457
5618
  const formContent = /* @__PURE__ */ jsxs("div", { children: [
5458
- /* @__PURE__ */ jsxs(CardTitle, { className: "flex flex-row items-center gap-2 p-2 border-b", children: [
5619
+ showFormHeader && /* @__PURE__ */ jsxs(CardTitle, { className: "flex flex-row items-center gap-2 p-2 border-b", children: [
5459
5620
  /* @__PURE__ */ jsxs("div", { className: "flex flex-row items-center gap-2 w-full", children: [
5460
- /* @__PURE__ */ jsx(Pencil, { className: "h-5 w-5" }),
5621
+ showIcon && /* @__PURE__ */ jsx(Pencil, { className: "h-5 w-5" }),
5461
5622
  /* @__PURE__ */ jsxs("div", { className: "flex flex-col", children: [
5462
5623
  /* @__PURE__ */ jsxs(CardTitle, { className: "text-xl", children: [
5463
5624
  formTitle,