import { render } from "@testing-library/react"; import type * as React from "react"; import { vi } from "vitest"; import { defineToolcraft } from "../../schema/define-toolcraft"; import type { ToolcraftProductSceneBoundsProvider } from "../../scene"; import type { ToolcraftInitialState } from "../../state/types"; import { ToolcraftRoot } from "../app-shell/toolcraft-root"; import { useToolcraft } from "../app-shell/use-toolcraft"; import { CanvasShell } from "./canvas-shell"; import { ToolcraftProductSceneBoundsBoundary } from "./product-scene-surface"; export function createSchema() { return defineToolcraft({ canvas: { enabled: true, size: { width: 300, height: 200, unit: "px" }, upload: true, }, panels: {}, persistence: { storage: "none" }, }); } export function createIntrinsicMediaSchema() { return defineToolcraft({ canvas: { enabled: true, sizing: { mode: "intrinsic-media" }, upload: true, }, panels: {}, persistence: { storage: "none" }, }); } export function createBackgroundSchema() { return defineToolcraft({ canvas: { enabled: true, size: { width: 300, height: 200, unit: "px" }, sizing: { mode: "editable-output" }, upload: true, }, panels: { controls: { sections: [ { controls: { includeBackground: { defaultValue: true, target: "export.includeBackground", type: "switch", }, background: { defaultValue: "#D4CECA", target: "appearance.background", type: "color", }, }, title: "Background", }, ], title: "Controls", }, }, persistence: { storage: "none" }, }); } export function createUploadDefaultSchema() { return defineToolcraft({ canvas: { enabled: true, upload: true, }, panels: {}, persistence: { storage: "none" }, }); } export function CanvasStateProbe() { const { state } = useToolcraft(); const firstImage = state.mediaAssets.find( (asset) => asset.assetKind === "image", ); return ( <> {state.canvas.offset.x},{state.canvas.offset.y} {state.canvas.zoom} {state.mediaAssets.length} {firstImage?.size?.width ?? 0},{firstImage?.size?.height ?? 0} {state.mediaAssets.map((asset) => asset.sourceTarget ?? "none").join(",")} {state.mediaAssets.map((asset) => asset.assetKind).join(",")} ); } export function mockCanvasRect(canvas: HTMLElement): void { vi.spyOn(canvas, "getBoundingClientRect").mockReturnValue({ bottom: 600, height: 600, left: 0, right: 800, toJSON: () => ({}), top: 0, width: 800, x: 0, y: 0, }); } type RenderCanvasShellOptions = { afterCanvas?: React.ReactNode; children?: React.ReactNode; frameProps?: React.HTMLAttributes; infiniteCanvasContent?: React.ReactNode; initialState?: ToolcraftInitialState; productSceneBoundsProvider?: ToolcraftProductSceneBoundsProvider; schema?: ReturnType; }; export function renderCanvasShell({ afterCanvas, children, frameProps, infiniteCanvasContent, initialState, productSceneBoundsProvider, schema = createSchema(), }: RenderCanvasShellOptions = {}) { const { style, ...restFrameProps } = frameProps ?? {}; return render(
{children} {afterCanvas}
, ); }