# SVG 导入

> 示例：
> - `vjcad/example/insert/svg/01importsvg.js` — IMPORTSVG 命令
> - `vjcad/example/insert/svg/02importsvgapi.js` — `parseSvgToWebcad` API
> - `vjcad/example/insert/svg/03insertimage.js` — INSERTIMAGE 命令（图片转矢量入口）
> 文档：`vjcad/doc/insert/index.md`

## 1. 命令方式（最简单）

```js
await Engine.editor.executerWithOp('IMPORTSVG');
Engine.zoomExtents();
```

`IMPORTSVG` 弹出对话框，支持：

- 选择本地 SVG 文件 / 直接粘贴 SVG 字符串
- 显示设置：`显示线宽` / `启用填充` / `线宽缩放比例`
- 颜色处理：白/黑色 → `0=原样` / `1=反色` / `2=过滤`
- 插入选项：`允许缩放` / `允许旋转`
- SVG 原始效果 vs WebCAD 效果实时对比预览

## 2. API 方式（可批量 / 服务端预设 / 程序生成 SVG）

完整流程见 `vjcad/example/insert/svg/02importsvgapi.js`。骨架：

```js
const wasmService = getWebCadCoreService();
// 无需手动 initWasm：parseSvgToWebcad 内部会 await this.initWasm()

const webcadData = await wasmService.parseSvgToWebcad(
    svgContent,
    /* whiteColorProcessing */ 0, // 0=原样 / 1=反色 / 2=过滤
    /* blackColorProcessing */ 0,
    /* enableFill */          0, // 0=否 / 1=是
    /* displayLineWeight */   1,
    /* lineWeightScale */     1.0
);

if (!webcadData) throw new Error('SVG 解析失败');   // 失败返回 null（不抛错），详情见控制台
const parsed = JSON.parse(webcadData);
const entities = parsed.entities ?? [];
```

随后用 **临时 CadDocument** 把 `entities` 装进 `*Model` 块、再合并到当前文档：

```js
const docData = {
    appName: "WebCAD SVG Import",
    docVer: 0.3,
    dbBlocks: {
        "*Model": {
            blockId: "*Model", name: "*Model", isLayout: false,
            basePoint: [0, 0], lookPt: [0, 0],
            twistAngle: 0, zoom: 1, UCSXANG: 0, UCSORG: [0, 0],
            items: entities,
        },
    },
    dbLayers: [{ name: "0", layerId: "0", layerOn: true, color: 7,
                 lineType: "Continuous", lineWeight: -3, plottable: true }],
    dbTextStyles: [],
    dbLayouts: [{ layoutId: 0, name: "Model", spaceName: "*Model" }],
};

const symbolDoc = new CadDocument();
await symbolDoc.fromDb(docData);

const basePt = new Point2D(
    parsed.bounds ? (parsed.bounds[0] + parsed.bounds[2]) / 2 : 0,
    parsed.bounds ? (parsed.bounds[1] + parsed.bounds[3]) / 2 : 0
);
const insertPoint = new Point2D(0, 0);

const modelBlock = symbolDoc.blocks.itemByName("*Model");
for (const entity of modelBlock.items) {
    if (!entity.isAlive) continue;
    const cloned = entity.clone();
    cloned.move(basePt, insertPoint);  // 把基点对齐到插入点
    Engine.addEntities(cloned);
}
regen();
Engine.zoomExtents();
```

> 完整代码：`vjcad/example/insert/svg/02importsvgapi.js`

## 3. parseSvgToWebcad 参数

| 参数 | 取值 | 说明 |
|---|---|---|
| `svgContent` | string | 完整 SVG 文本 |
| `whiteColorProcessing` | 0 / 1 / 2 | 白色：0=原样 / 1=反色 / 2=过滤 |
| `blackColorProcessing` | 0 / 1 / 2 | 黑色：同上 |
| `enableFill` | 0 / 1 | 是否将填充区域转为 Hatch |
| `displayLineWeight` | 0 / 1 | 是否保留线宽 |
| `lineWeightScale` | number | 线宽缩放（1.0 = 原值） |

返回 JSON 字符串：

```json
{
    "entities": [ /* webcad 实体数组 */ ],
    "bounds":   [minX, minY, maxX, maxY]
}
```

## 4. 支持的 SVG 元素

`<rect>` / `<circle>` / `<ellipse>` / `<line>` / `<polyline>` / `<polygon>` / `<path>`（包含 `M L H V Q T C S A Z`）/ `<text>`（基础）/ `<g>`（嵌套）。

> 颜色 `stroke`、`fill`、`stroke-width` 均会被解析。

## 红旗

- 不需要先 `await initWasm()`（`parseSvgToWebcad` 内部自动初始化）；WASM 加载或解析失败时返回 `null` 而非抛错，必须判空再 `JSON.parse`
- 当 `parsed.bounds` 缺失时，把 `basePoint` 退化为 `[0, 0]`
- 大 SVG（>10MB）建议在 webworker 里转，主线程会卡顿
- `parseSvgToWebcad` 是 **同步语义但内部异步**，外面必须 `await`
- 千万别把 SVG 里的 `transform="..."` 留空：`parseSvgToWebcad` 已经把变换应用到坐标，导入后再 `move/rotate` 是叠加而非覆盖

## 参考（官方文档 MCP）

- 示例：
- `vjcad/example/insert/svg/01importsvg.js` — IMPORTSVG 命令
- `vjcad/example/insert/svg/02importsvgapi.js` — `parseSvgToWebcad` API
- `vjcad/example/insert/svg/03insertimage.js` — INSERTIMAGE 命令（图片转矢量入口）
- 文档：`vjcad/doc/insert/index.md`
