49 lines
2.5 KiB
TypeScript
49 lines
2.5 KiB
TypeScript
import { afterEach, describe, expect, it, vi } from "vitest";
|
|
import { connectAuthoritativeDualScreen } from "./authoritativeDualScreenRuntime";
|
|
import { useUiLayoutStore } from "../game/uiLayoutStore";
|
|
import { useDpsMeterStore } from "../game/dpsMeterStore";
|
|
import { emptyDpsMeter } from "../game/dpsMeter";
|
|
import type { DualScreenMessage } from "./dualScreenSync";
|
|
|
|
describe("dedicated companion DPS synchronization", () => {
|
|
afterEach(() => {
|
|
useUiLayoutStore.getState().finish(false);
|
|
useDpsMeterStore.setState(emptyDpsMeter(), true);
|
|
vi.unstubAllGlobals();
|
|
vi.useRealTimers();
|
|
});
|
|
|
|
it("publishes meter ticks and layout drafts, then unsubscribes on disconnect", () => {
|
|
vi.useFakeTimers(); vi.setSystemTime(1_000);
|
|
vi.stubGlobal("window", { setTimeout, clearTimeout, location: { search: "?display=top" } });
|
|
const postMessage = vi.fn<(message: DualScreenMessage) => void>();
|
|
const channel = { postMessage, onmessage: null } as unknown as BroadcastChannel;
|
|
const disconnect = connectAuthoritativeDualScreen(channel, { data: { type: "companion-ready" } } as MessageEvent<DualScreenMessage>);
|
|
try {
|
|
useUiLayoutStore.getState().begin();
|
|
useUiLayoutStore.getState().updateDraft((layout) => ({ ...layout, dpsMeterDisplay: "companion", elements: {
|
|
...layout.elements, dps: { visible: false, position: { x: .4, y: .6 }, width: 300 },
|
|
} }));
|
|
vi.advanceTimersByTime(100);
|
|
let latest = postMessage.mock.lastCall?.[0];
|
|
expect(latest?.type).toBe("app-state");
|
|
if (latest?.type !== "app-state") throw new Error("Missing companion snapshot");
|
|
expect(latest.snapshot.game.dpsMeter).toMatchObject({ display: "companion", layout: {
|
|
visible: false, position: { x: .4, y: .6 }, width: 300,
|
|
} });
|
|
|
|
useDpsMeterStore.setState({ startedAt: 1_000, endedAt: null, updatedAt: 3_000, elapsedMs: 2_000,
|
|
damage: { test: { id: "test", name: "Test", color: "#fff", total: 200 } } }, true);
|
|
vi.advanceTimersByTime(100);
|
|
latest = postMessage.mock.lastCall?.[0];
|
|
if (latest?.type !== "app-state") throw new Error("Missing DPS snapshot");
|
|
expect(latest.snapshot.game.dpsMeter.values).toMatchObject({ totalDamage: 200, totalDps: 100, durationSeconds: 2 });
|
|
} finally { disconnect(); }
|
|
postMessage.mockClear();
|
|
useUiLayoutStore.getState().finish(false);
|
|
useDpsMeterStore.setState(emptyDpsMeter(), true);
|
|
vi.advanceTimersByTime(100);
|
|
expect(postMessage).not.toHaveBeenCalled();
|
|
});
|
|
});
|