共计 1832 个字符,预计需要花费 5 分钟才能阅读完成。
问题背景
当 3D 模型包含大量 Mesh 时,会导致几个关键性能问题:

- Draw Call 压力 :每个 Mesh 通常需要单独的 Draw Call,数量过多时会造成 CPU 瓶颈
- 内存带宽瓶颈 :高精度顶点数据会显著增加显存占用和传输开销
- 加载时间延长 :未压缩的模型文件体积庞大,影响用户体验
以一个包含 50 万三角形的建筑模型为例,原始 glTF 文件可能达到 200MB,在移动设备上加载需要 10 秒以上,且运行时帧率可能低于 30FPS。
主流压缩方案对比
1. Draco 压缩算法
Draco 采用熵编码技术,核心原理包括:
- 顶点位置预测编码(预测残差比原始坐标更易压缩)
- 拓扑结构索引重整(将相邻三角形组织为更紧凑的表示形式)
- 属性量化(将浮点数转换为低比特整数)
典型压缩率可达原始大小的 30%-50%,但解码需要额外 WASM 模块。
2. Meshopt 优化方案
Meshopt 专注于运行时性能优化:
- 顶点缓存优化(重新排序三角形以提高 GPU 缓存命中率)
- 顶点数据量化(类似 Draco 但更轻量级)
- 索引压缩(使用变长编码减少索引数据体积)
相比 Draco,Meshopt 压缩率稍低(约 60% 原大小),但解码速度更快且无需额外库。
3. LOD 技术对比
| 类型 | 生成方式 | 适用场景 |
|---|---|---|
| 传统 LOD | 美术预先制作多个版本 | 静态大场景 |
| 程序化 LOD | 运行时自动简化 | 动态加载场景 |
| 混合 LOD | 预生成 + 运行时调整 | 开放世界游戏 |
实战指南
使用 glTF-Transform 处理模型
import {NodeIO, Mesh, PropertyType} from '@gltf-transform/core';
import {quantize, draco} from '@gltf-transform/functions';
// 初始化 IO 处理器
const io = new NodeIO()
.registerExtensions([draco.DracoMeshCompression])
.registerDependencies({'draco3d.decoder': await new DracoDecoderModule(),
});
// 加载原始模型
const document = await io.read('model.glb');
// 执行压缩
await document.transform(
// 顶点属性量化(位置 16 位,UV/ 法线 12 位)quantize({
pattern: /POSITION|TEXCOORD|NORMAL/,
bits: {POSITION: 16, TEXCOORD: 12, NORMAL: 12},
}),
// Draco 压缩(压缩级别 6)draco({method: 'edgebreaker', encodeSpeed: 5, decodeSpeed: 5})
);
// 保存压缩后模型
await io.write('model-compressed.glb', document);
Three.js 加载注意事项
-
必须提前加载 Draco 解码器
import {DRACOLoader} from 'three/examples/jsm/loaders/DRACOLoader'; const dracoLoader = new DRACOLoader(); dracoLoader.setDecoderPath('/draco/'); const loader = new GLTFLoader(); loader.setDRACOLoader(dracoLoader); -
处理 WebGL 上下文丢失
renderer.context.canvas.addEventListener('webglcontextlost', () => { // 需要重新创建解码器实例 dracoLoader.dispose();});
关键避坑点
法线贴图兼容性
- 量化后的法线可能产生锯齿,建议:
- 保持法线 12bit 以上精度
- 或在着色器中使用 octahedral 编码
骨骼动画权重处理
- 四舍五入误差可能导致权重和≠1.0
- 解决方案:
// 在着色器中归一化 vec4 weights = normalize(vertexWeights);
性能对比数据
| 指标 | 原始模型 | 压缩后 | 提升 |
|---|---|---|---|
| 文件大小 | 186MB | 62MB | 66%↓ |
| 内存占用 | 420MB | 150MB | 64%↓ |
| 加载时间 | 8.2s | 2.7s | 67%↓ |
| 平均 FPS | 31 | 58 | 87%↑ |
进阶思考
可以结合以下策略进一步优化:
- 渐进式加载 :先加载低精度版本,再后台加载高清细节
- 流式传输 :将模型分块并按需加载
- 视锥裁剪 :只加载可见区域的 Mesh
这些技术与压缩方案协同使用,可打造极致性能的 3D 应用。
正文完
发表至: 未分类
近三天内
