import { describe, it, expect, afterEach } from "vitest";
import { render, cleanup } from "@testing-library/react";
import { PublicPageRenderer } from "@/features/editor/components/PublicPageRenderer";
import type { Block } from "@/features/editor/state/editorStore";

// PublicPageRenderer 버튼 스타일 TDD
// - fillColorCustom / strokeColorCustom / textColorCustom
// - widthMode=fixed + widthPx, paddingX/paddingY
// - borderRadius 토큰에 따른 둥글기

describe("PublicPageRenderer - 버튼 블록 스타일", () => {
  afterEach(() => {
    cleanup();
  });

  it("버튼 색상 커스텀 값은 배경/외곽선/텍스트 색상 스타일에 반영되어야 한다", () => {
    const blocks: Block[] = [
      {
        id: "btn_colors",
        type: "button",
        props: {
          label: "컬러 버튼",
          href: "#",
          align: "center",
          fillColorCustom: "#123456",
          strokeColorCustom: "#ff0000",
          textColorCustom: "#00ff00",
        } as any,
      },
    ];

    const { container } = render(<PublicPageRenderer blocks={blocks} />);

    const link = container.querySelector("a") as HTMLAnchorElement | null;
    expect(link).not.toBeNull();

    const wrapper = link!.parentElement as HTMLElement | null;
    expect(wrapper).not.toBeNull();
    // 정렬/버튼 베이스는 pb-* 토큰 클래스로 렌더된다.
    expect(wrapper!.className).toContain("pb-text-center");
    expect(link!.className).toContain("pb-btn-base");
    expect(link!.className).toContain("pb-btn-size-md");
    expect(link!.className).toContain("pb-btn-variant-solid-primary");
    expect(link!.className).toContain("pb-btn-radius-md");
    // 배경색: #123456 → rgb(18, 52, 86)
    expect(link!.style.backgroundColor).toBe("rgb(18, 52, 86)");
    // 외곽선 색상: #ff0000 → rgb(255, 0, 0)
    expect(link!.style.borderColor).toBe("rgb(255, 0, 0)");
    // strokeColorCustom 이 있을 때 border-width/style 도 설정되어야 한다.
    expect(link!.style.borderWidth).toBe("1px");
    expect(link!.style.borderStyle).toBe("solid");
    // 텍스트 색상: #00ff00 → rgb(0, 255, 0)
    expect(link!.style.color).toBe("rgb(0, 255, 0)");
  });

  it("widthMode=fixed 인 버튼은 widthPx/paddingX/paddingY 가 em 단위 스타일로 반영되어야 한다", () => {
    const blocks: Block[] = [
      {
        id: "btn_layout",
        type: "button",
        props: {
          label: "레이아웃 버튼",
          href: "#",
          align: "left",
          widthMode: "fixed",
          widthPx: 320,
          paddingX: 16,
          paddingY: 8,
        } as any,
      },
    ];

    const { container } = render(<PublicPageRenderer blocks={blocks} />);

    const link = container.querySelector("a") as HTMLAnchorElement | null;
    expect(link).not.toBeNull();
    // width: 320px / 16 = 20em
    expect(link!.style.width).toBe("20em");
    // padding-inline: 16px / 16 = 1em
    expect(link!.style.paddingInline).toBe("1em");
    // padding-block: 8px / 16 = 0.5em
    expect(link!.style.paddingBlock).toBe("0.5em");
  });

  it("borderRadius 토큰은 em 단위 둥글기로 반영되어야 한다", () => {
    const blocks: Block[] = [
      {
        id: "btn_radius",
        type: "button",
        props: {
          label: "둥근 버튼",
          href: "#",
          borderRadius: "lg",
        } as any,
      },
    ];

    const { container } = render(<PublicPageRenderer blocks={blocks} />);

    const link = container.querySelector("a") as HTMLAnchorElement | null;
    expect(link).not.toBeNull();
    // lg → 12px → 12 / 16 = 0.75em
    expect(link!.style.borderRadius).toBe("0.75em");
  });

  it("버튼에 imageSrc 가 있으면 이미지와 텍스트를 함께 렌더링해야 한다 (좌측 배치)", () => {
    const blocks: Block[] = [
      {
        id: "btn_img_left",
        type: "button",
        props: {
          label: "이미지 버튼",
          href: "#",
          imageSrc: "https://example.com/icon.png",
          imageAlt: "아이콘",
          imagePlacement: "left",
        } as any,
      },
    ];

    const { container } = render(<PublicPageRenderer blocks={blocks} />);

    const link = container.querySelector("a") as HTMLAnchorElement | null;
    expect(link).not.toBeNull();

    const img = link!.querySelector("img") as HTMLImageElement | null;
    expect(img).not.toBeNull();
    expect(img!.src).toContain("https://example.com/icon.png");
    expect(img!.alt).toBe("아이콘");

    const labelNode = Array.from(link!.querySelectorAll("span")).find((el) =>
      el.textContent?.includes("이미지 버튼"),
    );
    expect(labelNode).toBeTruthy();
  });

  it("imagePlacement 가 top 인 경우 이미지가 텍스트 위쪽에 렌더링되어야 한다", () => {
    const blocks: Block[] = [
      {
        id: "btn_img_top",
        type: "button",
        props: {
          label: "위쪽 이미지 버튼",
          href: "#",
          imageSrc: "https://example.com/icon-top.png",
          imageAlt: "위쪽 아이콘",
          imagePlacement: "top",
        } as any,
      },
    ];

    const { container } = render(<PublicPageRenderer blocks={blocks} />);

    const link = container.querySelector("a") as HTMLAnchorElement | null;
    expect(link).not.toBeNull();

    const wrapper = link!.querySelector("span") as HTMLSpanElement | null;
    expect(wrapper).not.toBeNull();
    expect(wrapper!.className).toContain("flex-col");

    const firstChild = wrapper!.firstElementChild as HTMLElement | null;
    expect(firstChild?.tagName.toLowerCase()).toBe("img");
  });
});
