import { describe, expect, it } from "vitest"; import { applySourcePatches } from "../../src/document/source-patcher"; import { parseSvgSource } from "../../src/document/source-parser"; import { composeTransformList, parseTransformList, } from "../../src/domain/affine"; import { bakeElementTransform } from "../../src/domain/bake-transform"; function bake(source: string, id: string) { const parsed = parseSvgSource(source, 1); expect(parsed.semantic).not.toBeNull(); const semantic = parsed.semantic!; const node = [...semantic.nodes.values()].find( (candidate) => candidate.id === id, )!; const matrix = composeTransformList( parseTransformList(node.attributes.transform ?? ""), ); const result = bakeElementTransform( source, node, matrix, semantic.preferences, ); return { result, source: applySourcePatches(source, result.patches) }; } describe("element transform baking", () => { it("retains lines, polygons, and safe rectangles as native elements", () => { const line = bake( '', "shape", ); expect(line.source).toContain( '', "shape", ); expect(polygon.source).toContain('points="0,0 4,0 4,6"'); const rectangle = bake( '', "shape", ); expect(rectangle.result.convertedToPath).toBe(false); expect(rectangle.source).toContain( ' { const baked = bake( '', "shape", ); expect(baked.result).toMatchObject({ outputElement: "path", convertedToPath: true, }); expect(baked.source).toContain(' { const circle = bake( '', "shape", ); expect(circle.result.outputElement).toBe("circle"); expect(circle.source).toContain('r="6"'); const ellipse = bake( '', "shape", ); expect(ellipse.result.outputElement).toBe("ellipse"); expect(ellipse.source).toContain(' { const baked = bake( '', "shape", ); expect(baked.source).toContain(' { const source = 'Text'; expect(() => bake(source, "shape")).toThrow(/not deterministic/u); }); it("refuses non-SVG numeric spellings instead of coercing geometry", () => { const source = ''; expect(() => bake(source, "shape")).toThrow(/finite width/u); }); });