import { InputValidator } from "./utils/validate/InputValidator.mjs";
import { FieldBuilder } from "./utils/builders/FieldBuilder.mjs";
import InputsValidator from "./utils/validate/InputsValidator.mjs";
import { FieldsBuilder } from "./utils/builders/FieldsBuilder.mjs";
import { JSXElementConstructor } from "react";
import { TextFieldProps } from "@mui/material/TextField";
import { OutlinedInputProps } from "@mui/material/OutlinedInput";

//#region src/types.d.ts
type NameField = PropertyKey;
type GetArrayValues<T> = T[keyof T][];
type Simplify<T> = T extends Record<string, any> ? { [K in keyof T]: T[K] } : T;
type GetFieldsValue<Fields extends readonly {
  name: NameField;
  value: any;
}[]> = Simplify<{ [F in Fields[number] as F['name']]: F['value'] }>;
type GetFields<FieldsObject> = { [Field in keyof FieldsObject]: FieldsObject extends Record<string, FieldType> ? FieldsObject[Field] : never };
interface Message {
  ns?: string;
  message: string;
  /**
   * @description Properties to be passed to translate
   */
  props?: any;
}
interface EventField<V, Name extends NameField> {
  name: Name;
  value: V;
}
interface EventChangeValue<V = GenericValue, Name = string> {
  name: Name;
  value: V;
}
type OnChangeFieldEvent<Field extends FieldType> = EventField<Field['value'], Field['name']> & {
  field: FieldBuilder<Field>;
};
type OnChangeField<Field extends FieldType> = (e: OnChangeFieldEvent<Field>, nativeEvent?: React.ChangeEvent<HTMLInputElement | HTMLTextAreaElement>) => void | (() => void);
type OnSetValue<Field extends FieldType> = (e: {
  lastValue: Field['value'];
  newValue: Field['value'];
  field: FieldBuilder<Field>;
}) => void;
type GenericValue = any;
type GlobalProps = {
  [key: string]: any;
};
type transPosition = string | boolean;
type ActiveStep = number;
interface InitialState {
  ns?: string;
}
type ValidateInputsValidator<Fields extends FieldBuilder<any>[]> = ValidationsFields<Fields>['validate'];
type FieldsToObject<Fields extends {
  name: NameField;
  value: any;
}[]> = { [F in Fields[number] as F['name']]: F };
type FieldsProps<Fields extends FieldBuilder<any>[]> = {
  fields: [...Fields];
} & ValidationsFields<Fields> & InitialState;
type GenericFieldsBuilder = FieldsBuilder<FieldBuilder<any>[]>;
interface AllPropsValidationFunction<V = any> {
  field: FieldBuilder<any>;
  validate: boolean;
  value: V;
}
type ValidationFunction<V = any> = (all: AllPropsValidationFunction<V>) => FieldError | Promise<FieldError>;
/**
 * @description
 * Defines the map of errors returned from failed validation checks.
 *
 * @publicApi
 */
type ValidationError = string | React.ReactElement<any> | Message;
type FieldError = ValidationError | Record<string, any> | boolean | undefined | void;
type FieldErrors = undefined | void | FieldError[];
interface ValidationsProps<Field extends FieldType> {
  validate?: ValidateField<Field>;
  value: Field['value'];
  validations?: Field['validations'];
}
type ValidateField<Field extends FieldType> = boolean | ((arg: InputValidator<Field>) => boolean);
interface ValidationsFields<Fields extends FieldBuilder<any>[]> {
  validate?: boolean | ((inputsValidator: InputsValidator<Fields>) => boolean);
}
type ChildrenRender = React.ReactElement<FieldProps<any, any, any>, JSXElementConstructor<FieldProps<any, any, any>>>;
type RenderField<Field extends FieldType> = (element: {
  children: ChildrenRender;
  props: FieldProps<Field['value'], Field['name'], Field['validations']>;
}) => React.CElement<any, any>;
type ComponentField<Field extends FieldType> = React.ElementType<FieldProps<Field['value'], Field['name'], Field['validations']>>;
interface ComponentErrorsProps<Field extends FieldType<any, any, any, any>> {
  errors: any[];
  field?: FieldBuilder<Field>;
}
type ComponentErrors<Field extends FieldType<any, any, any, any>> = React.ElementType<ComponentErrorsProps<Field>>;
type TypeTextField = 'date' | 'email' | 'number' | 'password' | 'search' | 'tel' | 'text' | 'time' | 'url' | 'week' | 'datetime-local';
type TypeField = 'component' | TypeTextField;
type TextFieldPropsField = Pick<TextFieldProps, 'multiline' | 'rows' | 'autoComplete' | 'autoFocus' | 'color' | 'defaultValue' | 'disabled' | 'FormHelperTextProps' | 'fullWidth' | 'helperText' | 'id' | 'InputLabelProps' | 'inputRef' | 'label' | 'margin' | 'placeholder' | 'required' | 'select' | 'SelectProps'>;
type LabelPropsField = string | null | undefined | React.ReactElement<any> | Message;
type InputPropsField<Field extends FieldType> = ((a: {
  type: TypeField;
  changeType: (type: TypeField, callback?: () => void) => void;
  field: FieldBuilder<Field>;
}) => Partial<Field & OutlinedInputProps>) | Partial<Field & OutlinedInputProps>;
type FieldType<Name extends NameField = any, Value = any, Validations = any, Label = any> = {
  name: Name;
  value: Value;
  label: Label;
  validations: Validations;
};
type CommonValidations<V = any> = ValidationFunction<V>[];
type ValidationResult<V> = V extends Promise<infer R> ? R : V extends ((...args: any[]) => infer R) ? Awaited<R> : V;
type NormalizeArray<T> = T extends readonly (infer U)[] ? U[] : T;
type GetErrors<Validations extends CommonValidations | undefined> = Validations extends undefined ? undefined : Validations extends Array<any> ? NormalizeArray<{ [K in keyof Validations]: ValidationResult<Validations[K]> }> : never;
type PropsField<Field extends FieldType = any> = {
  readonly name: Field['name'];
  type?: TypeField;
  disabled?: boolean;
  defaultInputValue?: Field['value'];
  onChange?: OnChangeField<Field>;
  onSetValue?: OnSetValue<Field>;
  value: Field['value'];
  label?: Field['label'];
  validations?: Field['validations'];
} & InitialState & {
  validate?: ValidateField<Field>;
  render?: RenderField<Field>;
  InputProps?: InputPropsField<Field>;
  component?: ComponentField<Field>;
  fullWidth?: boolean;
  errors?: GetErrors<Field['validations']> | [];
  autoComplete?: string;
  textFieldProps?: TextFieldPropsField;
};
interface Validate<Field extends FieldType<any, any, any>> extends ValidationsProps<Field> {
  state?: boolean;
}
interface FieldProps<Value = any, Name extends NameField = any, Validations extends CommonValidations | undefined = undefined | any[]> {
  field: FieldBuilder<Simplify<FieldType<Name, Value, Validations>>>;
  onChangeField?: OnChangeField<Simplify<FieldType<Name, Value, Validations>>>;
  globalProps?: GlobalProps;
}
//#endregion
export { ActiveStep, AllPropsValidationFunction, ChildrenRender, CommonValidations, ComponentErrors, ComponentErrorsProps, ComponentField, EventChangeValue, EventField, FieldError, FieldErrors, FieldProps, FieldType, FieldsProps, FieldsToObject, GenericFieldsBuilder, GenericValue, GetArrayValues, GetErrors, GetFields, GetFieldsValue, GlobalProps, InitialState, InputPropsField, LabelPropsField, Message, NameField, OnChangeField, OnChangeFieldEvent, OnSetValue, PropsField, RenderField, Simplify, TextFieldPropsField, TypeField, TypeTextField, Validate, ValidateField, ValidateInputsValidator, ValidationError, ValidationFunction, ValidationsFields, ValidationsProps, transPosition };