import { describe, expect, it } from "vitest";
import {
  defineToolcraft,
  fireEvent,
  renderControlsPanel,
  renderControlsPanelWithSchema,
  screen
} from "../testing/controls-panel-test-utils";

describe("ControlsPanel runtime setup controls", () => {
  it("commits canvas size controls to runtime state on blur or Enter", () => {
    renderControlsPanel();

    const canvasSizeGroup = screen.getByText("Canvas width").closest(
      '[data-control-layout="inline"][data-control-layout-columns="2"]',
    );

    expect(canvasSizeGroup).toBeTruthy();
    expect(canvasSizeGroup?.textContent).toContain("Canvas width");
    expect(canvasSizeGroup?.textContent).toContain("Canvas height");

    const widthInput = screen.getByDisplayValue("320") as HTMLInputElement;

    fireEvent.change(widthInput, { target: { value: "640" } });
    expect(screen.getByTestId("canvas-size").textContent).toBe("320,180");
    expect(widthInput.value).toBe("640");

    fireEvent.blur(widthInput);
    expect(screen.getByTestId("canvas-size").textContent).toBe("640,180");

    const heightInput = screen.getByDisplayValue("180") as HTMLInputElement;

    fireEvent.change(heightInput, { target: { value: "360" } });
    expect(screen.getByTestId("canvas-size").textContent).toBe("640,180");

    fireEvent.keyDown(heightInput, { code: "Enter", key: "Enter" });
    expect(screen.getByTestId("canvas-size").textContent).toBe("640,360");

    fireEvent.click(screen.getByRole("button", { name: "Reset controls" }));

    expect(screen.getByTestId("canvas-size").textContent).toBe("320,180");
  });

  it("renders editable-output aspect ratio controls with the current canvas preset", () => {
    const schema = defineToolcraft({
      canvas: {
        enabled: true,
        size: { height: 1080, unit: "px", width: 1440 },
        sizing: { mode: "editable-output" },
      },
      panels: {
        controls: {
          sections: [],
          title: "Controls",
        },
      },
    });
    const { container } = renderControlsPanelWithSchema(schema);

    expect(screen.getByTestId("canvas-size").textContent).toBe("1440,1080");

    const aspectRatioControl = container.querySelector<HTMLElement>(
      '[data-slot="canvas-aspect-ratio-control"]',
    );

    expect(screen.getByText("Aspect ratio")).toBeTruthy();
    expect(aspectRatioControl?.textContent).toContain("4:3");
    const values = JSON.parse(screen.getByTestId("values-json").textContent ?? "{}");

    expect(values["canvas.aspectRatio"]).toEqual({
      height: 3,
      mode: "preset",
      value: "4:3",
      width: 4,
    });
    expect(values["canvas.size.width"]).toBe(1440);
    expect(values["canvas.size.height"]).toBe(1080);
  });

  it("switches editable-output aspect ratio to custom after manual size edits", () => {
    const schema = defineToolcraft({
      canvas: {
        enabled: true,
        size: { height: 1080, unit: "px", width: 1920 },
        sizing: { mode: "editable-output" },
      },
      panels: {
        controls: {
          sections: [],
          title: "Controls",
        },
      },
    });

    renderControlsPanelWithSchema(schema);

    const widthInput = screen.getByDisplayValue("1920") as HTMLInputElement;

    fireEvent.change(widthInput, { target: { value: "1600" } });
    fireEvent.blur(widthInput);

    expect(screen.getByTestId("canvas-size").textContent).toBe("1600,1080");
    expect(screen.getAllByText("Custom").length).toBeGreaterThan(0);
    expect(screen.queryByDisplayValue("40")).toBeNull();
    expect(screen.queryByDisplayValue("27")).toBeNull();
    expect(JSON.parse(screen.getByTestId("values-json").textContent ?? "{}")).toMatchObject({
      "canvas.aspectRatio": {
        height: 27,
        mode: "custom",
        value: "40:27",
        width: 40,
      },
      "canvas.size.height": 1080,
      "canvas.size.width": 1600,
    });
  });

  it("renders raster render scale as the last technical setup control", () => {
    const schema = defineToolcraft({
      canvas: {
        enabled: true,
        renderScale: true,
        size: { height: 1080, unit: "px", width: 1920 },
        sizing: { mode: "editable-output" },
      },
      panels: {
        controls: {
          sections: [],
          title: "Controls",
        },
      },
    });
    renderControlsPanelWithSchema(schema);

    const values = JSON.parse(screen.getByTestId("values-json").textContent ?? "{}");

    expect(screen.getByText("Resolution scale")).toBeTruthy();
    expect(screen.getByText("2")).toBeTruthy();
    expect(values["canvas.renderScale"]).toBe(2);
  });

  it("renders timeline extended mode as runtime panel state instead of product values", () => {
    const schema = defineToolcraft({
      canvas: {
        enabled: true,
        renderScale: true,
        size: { height: 1080, unit: "px", width: 1920 },
        sizing: { mode: "editable-output" },
      },
      panels: {
        controls: {
          sections: [],
          title: "Controls",
        },
        timeline: { mode: "playback" },
      },
    });

    renderControlsPanelWithSchema(schema, undefined, {
      timeline: { currentTimeSeconds: 2, expanded: true, isPlaying: true },
    });

    const timelineField = screen.getByText("Timeline").closest('[role="group"]');
    const setupSection = timelineField?.closest("section");
    const timelineSwitch = timelineField?.querySelector<HTMLElement>('[role="switch"]');

    expect((setupSection?.textContent ?? "").indexOf("Resolution scale")).toBeLessThan(
      (setupSection?.textContent ?? "").indexOf("Timeline"),
    );
    expect(screen.queryByRole("button", { name: "Timeline help" })).toBeNull();
    expect(
      screen.queryByRole("button", { name: "Infinity canvas help" }),
    ).toBeNull();
    expect(timelineSwitch?.getAttribute("aria-checked")).toBe("false");
    expect(screen.getByTestId("timeline-panel-extended").textContent).toBe("undefined");
    expect(screen.getByTestId("timeline-panel-hidden").textContent).toBe("undefined");
    expect(screen.getByTestId("timeline-expanded").textContent).toBe("true");

    fireEvent.click(timelineSwitch as HTMLElement);

    expect(timelineSwitch?.getAttribute("aria-checked")).toBe("true");
    expect(screen.getByTestId("timeline-panel-extended").textContent).toBe("true");
    expect(screen.getByTestId("timeline-panel-hidden").textContent).toBe("undefined");
    expect(screen.getByTestId("timeline-expanded").textContent).toBe("true");
    expect(JSON.parse(screen.getByTestId("values-json").textContent ?? "{}")).not.toHaveProperty(
      "panels.timeline.extended",
    );

    fireEvent.click(screen.getByRole("button", { name: "Reset controls" }));

    expect(timelineSwitch?.getAttribute("aria-checked")).toBe("true");
    expect(screen.getByTestId("timeline-panel-extended").textContent).toBe("true");
  });
});
