import * as React from "react";
import { render, screen, fireEvent, cleanup } from "@testing-library/react";
import { EditorMode } from "@sc/modules/v2/Editor/types";
import reactToCSS from "react-style-object-to-css";
import { styleClean } from "@sc/utils";

import TextAreaField from "./TextAreaField";
import { styleData } from "../../FormBuilder.stories";
import { IconTypes } from "@sc/plugins/webcomponents/v2/Icon";

const testId = "FormBuilder-FormFields-TextAreaField";
const props = {
  styles: styleData,
  attributeContainerDataSettings: { hide: false },
};

describe("<TextAreaField /> Rendering Tests", () => {
  afterEach(cleanup);
  it(`Should render in the dom`, () => {
    render(<TextAreaField {...props} />);
    expect(screen.queryByTestId(testId)).toBeTruthy();
  });

  it(`Should render an EDITOR or LIVE version of the component based on the value of the mode prop`, () => {
    const testIdLive = "FormBuilder-FormFields-TextAreaField-LIVE";
    const testIdEditor = "FormBuilder-FormFields-TextAreaField-EDITOR";

    const { rerender } = render(
      <TextAreaField {...props} mode={EditorMode.LIVE} />
    );
    expect(screen.queryByTestId(testIdLive)).toBeTruthy();

    rerender(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(testIdEditor)).toBeTruthy();
  });

  it(`Should render a regular textarea input field when the mode is live`, () => {
    const testIdLive = "FormBuilder-FormFields-TextAreaField-LIVE";
    render(<TextAreaField {...props} mode={EditorMode.LIVE} />);
    expect(
      screen.queryByTestId(testIdLive).querySelector("textarea")
    ).toBeTruthy();
  });

  it(`Should render the AttributeContainer component when the mode is edit`, () => {
    const attrTestId = "FormBuilder-AttributeContainer";
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(attrTestId)).toBeTruthy();
  });

  it(`Should see that the <Label /> component has been rendered in the dom`, () => {
    const labelTestId = "FormBuilder-Attributes-Label";
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(labelTestId)).toBeTruthy();
  });

  it(`Should see that the <IconSelector /> component has been rendered in the dom`, () => {
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId("Properties-IconSelector-input")).toBeTruthy();
  });

  it(`Should see that the <Description /> component has been rendered in the dom`, () => {
    const descriptionTestId = "FormBuilder-Attributes-Description";
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(descriptionTestId)).toBeTruthy();
  });

  it(`Should see that the <Column /> component has been rendered in the dom`, () => {
    const columnsTestId = "FormBuilder-Attributes-Columns";
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(columnsTestId)).toBeTruthy();
  });

  it(`Should see that the <Required /> component has been rendered in the dom`, () => {
    const requiredTestId = "FormBuilder-Attributes-Required";
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(requiredTestId)).toBeTruthy();
  });

  it(`Should only see that the <InitialValue /> component has been rendered if the "hide" value is false`, () => {
    const initialValueTestId = "FormBuilder-Attributes-InitialValue";
    render(<TextAreaField {...props} mode={EditorMode.EDITOR} />);
    expect(screen.queryByTestId(initialValueTestId)).toBeTruthy();
  });

  it(`Should render an inputStyle, iconStyle, descriptionStyle, containerStyle, and labelStyle when specified`, () => {
    const label = "Label Check";
    const description = "Description Check";

    const { container } = render(
      <TextAreaField
        {...props}
        icon={IconTypes.Email}
        label={label}
        description={description}
      />
    );

    expect(container.firstChild).toMatchSnapshot();

    // // inputStyle
    // expect(
    //   styleClean(
    //     screen
    //       .getByTestId(testId)
    //       .querySelector("textarea")
    //       .getAttribute("style")
    //   )
    // ).toContain(
    //   styleClean(
    //     reactToCSS({ ...styleData.inputStyle, padding: "15px 15px 15px 40px" })
    //   )
    // );

    // // iconStyle
    // expect(
    //   styleClean(screen.getByTestId("WC-ICON-LIVE").getAttribute("style"))
    // ).toContain(styleClean(reactToCSS(styleData.iconStyle)));

    // // descriptionStyle
    // expect(
    //   styleClean(screen.getByText(description).getAttribute("style"))
    // ).toContain(styleClean(reactToCSS(styleData.descriptionStyle)));

    // // containerStyle
    // expect(
    //   styleClean(screen.getByTestId(testId).getAttribute("style"))
    // ).toContain(styleClean(reactToCSS(styleData.containerStyle)));

    // // labelStyle
    // expect(styleClean(screen.getByText(label).getAttribute("style"))).toContain(
    //   styleClean(reactToCSS(styleData.labelStyle))
    // );
  });

  test.skip(`Should only see that the <Validation /> component has been rendered if the "hide" value is false`, () => {});
});

describe("<TextAreaField /> Events Tests", () => {
  afterEach(cleanup);
  it(`Should trigger the onChange event (via handleChange()) if the AttributeContainer's onChange event is called`, () => {
    const onChange = jest.fn();
    render(<TextAreaField {...props} onChange={onChange} />);
    fireEvent.change(screen.getByTestId(testId).querySelector("textarea"), {
      target: { value: "test" },
    });
    expect(onChange).toBeCalled();
  });

  it(`Should trigger the onBlur event if the AttributeContainer's onBlur event is called`, () => {
    const onBlur = jest.fn();
    render(<TextAreaField {...props} onBlur={onBlur} />);
    fireEvent.blur(screen.getByTestId(testId).querySelector("textarea"), {
      target: { value: "test" },
    });
    expect(onBlur).toBeCalled();
  });
});

describe("<TextAreaField /> Actions Tests", () => {
  afterEach(cleanup);
  test.skip(`handleChange should convert the incoming payload to LiveFormFieldProps`, () => {});
});
