Appearance
事件系统
引擎到应用方向的状态通知统一走事件总线,经 viewer.on() / once() 订阅。事件名与 payload 类型由 ViewerEvents 接口定义,TypeScript 下 handler 参数自动获得正确类型。
on / off / once
ts
// on:订阅,返回退订函数(推荐的清理方式)
const unsubscribe = viewer.on("camera-changed", (e) => {
console.log(e.position, e.target);
});
unsubscribe();
// off:显式退订,需传入与订阅时相同的 handler 引用
const handler = (e: { fps: number; frameMs: number }) => console.log(e.fps);
viewer.on("render", handler);
viewer.off("render", handler);
// once:只触发一次,触发后自动退订;同样返回退订函数
viewer.once("model-loaded", () => console.log("全部几何已就绪"));dispose 后的行为:viewer.dispose() 之后再调 on / once 会抛 ViewerError(Disposed);off 静默返回。已注册的订阅在 dispose 时全部释放,无需手动清理。
模型加载事件时序
model.load() 一次成功加载触发的事件顺序:
text
load(source) 调用
│
├─▶ "model-loading" load 开始,payload 带原始 source
│
├─▶ "model-skeleton-ready" 结构树骨架 + 索引就绪
│ │ ★ load() 的 Promise 在此 resolve,模型已可交互
│ │
│ ├─▶ "model-geom-progress" ┐ 几何分块后台流式到达,
│ ├─▶ "model-geom-progress" ├ 每块更新 ready/total
│ └─▶ ... ┘
│
└─▶ "model-loaded" 全部几何分块到达再次 load() 或 unload() 时先触发 "model-disposed"(卸载当前模型),再开始新的时序。加载失败不走事件——load() 的 Promise 直接 reject ViewerError(见模型数据)。
全事件参考
事实源是 ViewerEvents 接口(API 参考中可查每个 payload 的完整类型)。
模型生命周期
| 事件 | 触发时机 | payload 要点 |
|---|---|---|
model-loading | model.load() 开始 | source:原始 ModelSource |
model-skeleton-ready | 骨架(结构树 + 索引)就绪,load() 的 Promise 在此 resolve | boundingBox / nodeCount / meshCount |
model-geom-progress | 几何分块流式加载进度 | ready 已到达数 / total 总数 |
model-loaded | 全部几何分块加载完成 | 空对象 |
model-error | 预留,当前无发射点——加载错误经 load() 的 Promise reject 抛出 | error: ViewerError |
model-disposed | 当前模型被卸载(显式 unload() 或再次 load() 替换) | 空对象 |
model-bounds-changed | 场景有效包围球变化(如爆炸偏移外扩) | boundingSphere |
visibility-changed | 节点可见性实际变化(hide / show / isolate / reset) | hiddenCount:当前隐藏叶子总数 |
选中与悬停
| 事件 | 触发时机 | payload 要点 |
|---|---|---|
selection-changed | 选中集变化 | added / removed 本次增删项,current 完整选中集 |
hover-changed | hover 对象变化 | item:当前 hover 项,移出模型时为 null |
渲染与相机
| 事件 | 触发时机 | payload 要点 |
|---|---|---|
lod-changed | 某网格本帧实际显示的 LOD 级切换(由流式加载与屏幕误差驱动) | meshId / fromLod / toLod |
camera-changed | 相机位姿变化(交互期间约 30Hz 节流) | position / target / up |
render | 渲染心跳,约每秒一次 | fps 区间平均帧率 / frameMs 最近一帧渲染耗时 |
剖切
| 事件 | 触发时机 | payload 要点 |
|---|---|---|
section-changed | 剖切状态变化(平面增删改 / 激活集变化) | activeSectionId(多 section 激活时取最近激活者)/ planeCount |
section-activated | 某 section 被激活(开始参与裁剪) | sectionId |
section-deactivated | 某 section 被反激活(退出裁剪) | sectionId |
section-plane-drag-start | 开始用 gizmo 拖拽某剖切平面 | sectionId / planeId / plane |
section-plane-drag | gizmo 拖拽中,平面每次更新都触发 | 同上,plane 为当前平面 |
section-plane-drag-end | gizmo 拖拽结束 | 同上 |