// @vitest-environment jsdom // // Rendering integration of the shared SegmentedToggle. Labels are plain props (no i18n); the active // paint is CSS (`.pill[aria-pressed]`), so we assert the aria-pressed contract, not styling. import { describe, it, expect, vi, afterEach } from "vitest"; import { render, screen, fireEvent, cleanup } from "@testing-library/react"; import SegmentedToggle from "./SegmentedToggle"; const OPTS = [ { value: "or", label: "Any" }, { value: "and", label: "All" }, ] as const; afterEach(cleanup); describe("SegmentedToggle", () => { it("renders one button per option with the given labels", () => { render(); expect(screen.getAllByRole("button").map((b) => b.textContent)).toEqual(["Any", "All"]); }); it("marks exactly the active option aria-pressed", () => { render(); expect(screen.getByRole("button", { name: "Any" }).getAttribute("aria-pressed")).toBe("false"); expect(screen.getByRole("button", { name: "All" }).getAttribute("aria-pressed")).toBe("true"); }); it("clicking an option fires onChange with its value", () => { const onChange = vi.fn(); render(); fireEvent.click(screen.getByRole("button", { name: "All" })); expect(onChange).toHaveBeenCalledWith("and"); }); it("exposes the group aria-label", () => { render(); expect(screen.getByRole("group", { name: "Match mode" })).toBeTruthy(); }); it("renders the caption when label is set", () => { render( , ); // caption text plus the two option labels expect(screen.getByText("Match")).toBeTruthy(); expect(screen.getAllByRole("button")).toHaveLength(2); }); it("renders per-option icons and tooltips (scope-bar shape)", () => { render( , title: "Your subs" }, { value: "all", label: "Library", icon: }, ]} value="my" onChange={vi.fn()} />, ); expect(screen.getByTestId("ic-my")).toBeTruthy(); expect(screen.getByRole("button", { name: "Mine" }).getAttribute("title")).toBe("Your subs"); }); });