唯杰地图 logo唯杰地图
VJMAP
EN

trouble / 常见坑总览

vjcad/references/trouble/overview.md 3.6 KB81 行
原文

这个目录是"红旗"的集中清单。开发遇到莫名错误时优先来这里翻一遍。

vjcad 是一个完整的 CAD 引擎,开发中会遇到一些 跨模块的"看起来无关但其实根因相同" 的问题。本目录把它们按"症状"分组:

症状 主页
启动时画布黑屏 / 实体没进图(Engine 未就绪) / cadView.onLoad 卡住 init-pitfalls.md
切页面 / 卸载组件后内存涨 / 事件回调被反复触发 event-leak.md
EntityAdded 事件触发了好多次 / PolylineEnt 加点时机怪 command-event-timing.md
文档 / 示例 / 源码命名不一致 / 接口签名对不上 source-conflicts.md

通用排查方法

1. 看引擎是否初始化完毕

console.log('cadView:', cadView);
console.log('Engine:', Engine);
console.log('pcanvas:', Engine.pcanvas);       // onLoad 前为 null
console.log('mounted:', !!document.getElementById('map'));

Engine 是静态类,永远不是 undefined;Engine.currentDoc 在 onLoad 前也不是 undefined(懒建的孤儿文档),判断是否就绪看 Engine.pcanvas 是否非 null,否则去 init-pitfalls。

2. 看事件是否被绑了多次

const events = CadEventManager.getInstance();
console.log('监听数:', events.listenerCount(CadEvents.EntityAdded));   // CadEventManager 上没有 _listeners 字段

用公开的 listenerCount(event);如果某个事件在你 console.log 时已经 > 1,可能是 useEffect / 路由切换时没有 off。

3. 看命令是否被注册多次

console.log('已注册:', CommandRegistry.items.map(i => i.name));

items 是 CommandDefinition[] 静态数组;regist 只 push 不去重,执行时 CommandRegistry.item(name) 取第一个同名定义(先注册者胜出),后注册的不生效;要替换须先 CommandRegistry.unregist(name)(每次只删第一个匹配,重复注册过的要循环到返回 false)。

4. 关键的"先 await 再用"

调用 必须先
Engine.xxx await cadView.onLoad()
cadOverlay.addTo(map) await map.onLoad()
extractTables() 等同步 WASM 调用 WASM 已初始化(await cadView.onLoad() 已完成);parseSvgToWebcad 等 async 方法内部会自动 await this.initWasm(),无需手动调
Engine.editor.executerWithOp(cmd) CommandRegistry.regist(cmdDef)
Engine.patternManager.registerPattern Engine 已加载

5. 善用 writeMessage

vjcad 在底部命令行打字(HTML)一直是最快的"事件 / 状态"调试通道:

writeMessage('<br/>当前实体数: ' + Engine.currentSpace.items.length);  // BlockDefinition 字段是 items/aliveItems,无 .entities

6. 仅 dev 时打开详细日志

if (import.meta.env.DEV) {
    // 没有 CadEvents.AnyEvent 通配——要全量监听就自己枚举所有值
    const handlers = {};
    for (const t of Object.values(CadEvents)) {
        handlers[t] = args => console.log('[CAD]', t, args);
        Engine.eventManager.on(t, handlers[t]);
    }
}

生产环境务必关掉这类全量监听。

参考(官方文档 MCP)

  • 子页面分别引用了 vjcad/doc/event/*.md、vjcad/doc/guide/*.md,请按子页面查看
  • 通用调试通道(writeMessage、Engine.eventManager.on(CadEvents.XXX, ...))见 vjcad/doc/event/event-usage.md