import { Field, Label, Switch as HeadlessSwitch } from '@headlessui/react'
import { type ReactNode } from 'react'
import {
  Controller,
  get,
  type FieldError,
  type FieldValues,
  type Path,
  type RegisterOptions,
} from 'react-hook-form'
import { useRemixFormContext } from 'remix-hook-form'
import { twMerge } from 'tailwind-merge'

type TSwitchProperties<T extends FieldValues> = {
  id: string
  label?: ReactNode
  name: Path<T>
  rules?: RegisterOptions
  containerClassName?: string
  labelClassName?: string
  className?: string
  inputClassName?: string
}

export const Switch = <TFormValues extends Record<string, unknown>>(
  properties: TSwitchProperties<TFormValues>,
) => {
  const {
    id,
    label,
    name,
    rules,
    containerClassName,
    labelClassName,
    className,
    inputClassName,
  } = properties

  const {
    control,
    formState: { errors },
  } = useRemixFormContext()

  const error: FieldError = get(errors, name)

  return (
    <Field
      className={twMerge('relative', containerClassName)}
      id={id}
    >
      <Label className={twMerge('mb-1 block text-gray-700', labelClassName)}>
        {label} {error && <span className="text-red-500">{error.message}</span>}
      </Label>
      <Controller
        name={name}
        control={control}
        rules={rules}
        render={({ field }) => (
          <div className={twMerge('flex items-center', className)}>
            <HeadlessSwitch
              checked={field.value}
              onChange={(checked) => {
                field.onChange(checked)
              }}
              className={twMerge(
                'group relative flex h-7 w-14 cursor-pointer rounded-full bg-[#2E2F7C]/10 p-1 shadow transition-colors duration-200 ease-in-out focus:outline-none data-[checked]:bg-[#2E2F7C]/90 data-[focus]:outline-1 data-[focus]:outline-white',
                inputClassName,
              )}
            >
              <span
                aria-hidden="true"
                className="pointer-events-none inline-block size-5 translate-x-0 rounded-full bg-white ring-0 shadow-lg transition duration-200 ease-in-out group-data-[checked]:translate-x-7"
              />
            </HeadlessSwitch>
          </div>
        )}
      />
    </Field>
  )
}
