import FormField from '@/shared/components/form/form-field';
import { IClient } from '@/shared/types/client';
import { AddressData, FormFieldType, ModeType } from '@/shared/types/common';
import { FormikContextType, FormikErrors, FormikTouched } from 'formik';
import { useEffect, useState } from 'react';

const getFieldError = (
  fieldName: keyof IClient,
  touched: FormikTouched<IClient>,
  errors: FormikErrors<IClient>
): string | undefined => {
  if (!touched[fieldName] || !errors[fieldName]) return undefined;

  if (fieldName === 'mapAdresse') {
    return (errors.mapAdresse as any)?.formattedAddress;
  }

  return String(errors[fieldName]);
};
export const RenderField = ({
  field,
  formik,
  client,
  mode,
}: {
  field: FormFieldType<IClient>;
  formik: FormikContextType<IClient>;
  client: IClient;
  mode: ModeType;
}) => {
  const [value, setValue] = useState<any>(undefined);

  useEffect(() => {
    let newValue;
    if (field.name === 'civility') {
      newValue = formik.values[field.name];
    } else if (field.name === 'clientType') {
      newValue =
        mode === 'view' || mode === 'edit' || mode === 'copy'
          ? String(formik.values[field.name]?.id || '')
          : formik.values[field.name] || '';
    } else if (field.name === 'agencyName') {
      newValue =
        mode === 'view' || mode === 'edit' || mode === 'copy'
          ? String(formik.values['agency_id'] || '')
          : formik.values[field.name] || '';
    } else if (field.name === 'mapAdresse') {
      const formikMapAdresse = formik.values['mapAdresse'];
      if (formikMapAdresse) {
        newValue = formikMapAdresse;
        formik.setFieldValue('mapAdresse', newValue);
      } else if (client.addresses && client.addresses.length > 0) {
        const addressData: AddressData = {
          address: client.addresses[0].additionalAddress || '',
          lat: client.addresses[0].latitude || 0,
          lng: client.addresses[0].longitude || 0,
          formattedAddress: client.addresses[0].additionalAddress || '',
          city: client.addresses[0].city || '',
          postalCode: client.addresses[0].zipCode || '',
          country: client.addresses[0].country || '',
        };
        formik.setFieldValue('mapAdresse', addressData);
        newValue = addressData;
      }
    } else if (field.name === 'password') {
      newValue = mode === 'view' ? '**********' : formik.values[field.name];
    } else {
      newValue = formik.values[field.name];
    }
    setValue(newValue);
  }, [formik.values, mode, client.addresses, field.name]);

  const handleChange = (name: string, newValue: any) => {
    setValue(newValue);
    if (name === 'agencyName') {
      if (mode === 'edit' || mode === 'copy') {
        formik.setFieldValue(name, newValue);
        formik.setFieldValue('agency_id', newValue);
      } else {
        formik.setFieldValue(name, newValue);
      }
    } else if (name === 'clientType') {
      if (mode === 'edit' || mode === 'copy') {
        formik.setFieldValue(name, { id: newValue });
      } else {
        formik.setFieldValue(name, newValue);
      }
    } else {
      formik.setFieldValue(name, newValue);
    }
  };

  const editableFieldsInCopyMode = ['firstName', 'lastName', 'email', 'password', 'civility', 'landlinePhone', 'phoneNumber'];

  const fieldIsReadOnly =
    mode === 'view' ||
    (mode === 'copy' && !editableFieldsInCopyMode.includes(field.name)) ||
    (mode === 'edit' && field.name === 'email');
  

  return (
    <FormField
      field={field}
      value={value}
      onChange={handleChange}
      error={getFieldError(field.name as keyof IClient, formik.touched, formik.errors)}
      isReadOnly={fieldIsReadOnly}
      onBlur={formik.handleBlur}
    />
  );
};
