import React, { useEffect, useRef, useState } from 'react';
import { Form } from '@unform/web';
import 'jest-styled-components';
import { FormHandles } from '@unform/core';
import { fireEvent, render, screen } from '@testing-library/react';
import { UnformInput } from '.';

it('snapshot - with null', () => {
   const onSubmit = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();

      return (
         <Form ref={formRef} onSubmit={(v) => onSubmit(v)}>
            <UnformInput name="default" />
            <button
               data-testid="submit"
               title="submit"
               onClick={() => {
                  formRef.current.submitForm();
               }}
            />
         </Form>
      );
   }

   render(<Component />);

   fireEvent.click(screen.getByTestId('submit'));

   expect(onSubmit).toHaveBeenCalled();
   expect(onSubmit).toHaveBeenCalledWith({ default: null });
});

it('snapshot - with initial value', () => {
   const onSubmit = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();

      return (
         <Form ref={formRef} onSubmit={(v) => onSubmit(v)} initialData={{ default: 100.2212 }}>
            <UnformInput name="default" />
            <button
               data-testid="submit"
               title="submit"
               onClick={() => {
                  formRef.current.submitForm();
               }}
            />
         </Form>
      );
   }

   render(<Component />);

   fireEvent.click(screen.getByTestId('submit'));

   expect(onSubmit).toHaveBeenCalled();
   expect(onSubmit).toHaveBeenCalledWith({ default: 100.2212 });
});

it('snapshot - with initial value should call onChange', () => {
   const onChange = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();

      return (
         <Form ref={formRef} onSubmit={(v) => {}} initialData={{ default: 100.2212 }}>
            <UnformInput name="default" onChange={onChange} />
         </Form>
      );
   }

   render(<Component />);

   expect(onChange).toHaveBeenCalled();
   expect(onChange).toHaveBeenCalledWith(100.2212);
});

it('snapshot - with value', () => {
   const onSubmit = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();
      const [value, setValue] = useState(10);

      useEffect(() => {
         setValue(123);
      }, []);

      return (
         <Form ref={formRef} onSubmit={(v) => onSubmit(v)}>
            <UnformInput name="default" value={value} />
            <button
               data-testid="submit"
               title="submit"
               onClick={() => {
                  setValue(123);
                  formRef.current.submitForm();
               }}
            />
         </Form>
      );
   }

   render(<Component />);

   fireEvent.click(screen.getByTestId('submit'));

   expect(onSubmit).toHaveBeenCalled();
   expect(onSubmit).toHaveBeenCalledWith({ default: 123 });
});

it('snapshot - set value should call onChange', () => {
   const onChange = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();
      const [value, setValue] = useState(10);

      useEffect(() => {
         formRef.current.setFieldValue('default', 1);
      }, []);

      return (
         <Form ref={formRef} onSubmit={(v) => {}}>
            <UnformInput name="default" value={value} onChange={onChange} />
         </Form>
      );
   }

   render(<Component />);

   expect(onChange).toHaveBeenCalled();
   expect(onChange).toHaveBeenCalledWith(1);
});

it('snapshot - clear form should call onChange', () => {
   const onChange = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();
      const [value, setValue] = useState(10);

      useEffect(() => {
         formRef.current.reset();
      }, []);

      return (
         <Form ref={formRef} onSubmit={(v) => {}} initialData={{ default: 1 }}>
            <UnformInput name="default" value={value} onChange={onChange} />
         </Form>
      );
   }

   render(<Component />);

   expect(onChange).toHaveBeenCalled();
   expect(onChange).toHaveBeenCalledWith(1);
   expect(onChange).toHaveBeenCalledWith(null);
});

it('snapshot - with ref', () => {
   const onSubmit = jest.fn();

   function Component() {
      const formRef = useRef<FormHandles>();
      const inputRef = useRef<any>();

      return (
         <Form ref={formRef} onSubmit={(v) => onSubmit(v)}>
            <UnformInput name="default" ref={inputRef} />
            <button
               data-testid="submit"
               title="submit"
               onClick={() => {
                  inputRef.current.value = 123;
                  formRef.current.submitForm();
               }}
            />
         </Form>
      );
   }

   render(<Component />);

   fireEvent.click(screen.getByTestId('submit'));

   expect(onSubmit).toHaveBeenCalled();
   expect(onSubmit).toHaveBeenCalledWith({ default: 123 });
});
