资讯动态

vgpu渲染捆绑(Render Bundle)完全指南:一次录制无限回放,大幅降低渲染开销

发布时间:2026/10/4 18:19:18 来源:尧图企业网站定制
vgpu渲染捆绑Render Bundle完全指南一次录制无限回放大幅降低渲染开销【免费下载链接】vgpuModular cross-runtime WebGPU library for shaders, 3D scenes, GPU tensors, neural networks, and math viz项目地址: https://gitcode.com/gh_mirrors/vgpu/vgpuvgpu 是一个模块化的跨运行时 WebGPU 库用于着色器、3D 场景、GPU 张量与神经网络。本文带你快速入门 vgpu 的渲染捆绑Render Bundle把一组绘制命令一次性录制之后每帧只需回放即可跳过重复的命令编码从而大幅降低渲染开销。 为什么需要渲染捆绑在典型的 WebGPU 渲染循环里每一帧都要重新编码所有流水线、绑定组和绘制调用——哪怕场景完全没有变化。当绘制数量多起来时这部分纯 CPU 开销很容易成为帧率瓶颈。vgpu 的渲染捆绑正是为此设计的调用bundle(gpu, { target }, cb)把一组绘制命令一次性录制为Bundle之后在每帧里用pass.bundles(scene)回放成本几乎为零。⚡ 核心机制冻结什么不冻结什么理解 bundle 的关键在于分清它冻住与放行的内容冻结录制时确定放行每次回放仍生效目标渲染签名颜色格式、深度格式、采样数uniform 数据set()更新照常流入绑定组身份bind group identity目标尺寸窗口缩放后无需重录绘制命令序列indirect draw 参数缓冲GPU 每次回放重读一句话记忆录制不变的部分set()会动的部分。 快速上手三步录制你的第一个渲染捆绑const scene bundle(gpu, { target: canvasTarget }, (b) { b.draw(ocean); b.draw(boat); }); // 编码只发生这一次无需等待帧 frameLoop(gpu, (frame) { ocean.set({ params: { time: time.time } }); // uniform 依然动画 frame.pass(canvasTarget, (pass) pass.bundles(scene)); // 回放不重编码 });录制可以在帧外进行比如加载阶段vgpu 只读取 surface 已配置的渲染签名不会获取画布纹理、不会调整画布尺寸更不会提交任何 GPU 工作。真正产生绘制的是回放它始终发生在frame()或frameLoop()内部。⏱️ 性能进阶预编译管线让录制零卡顿bundle(gpu)在调用时立刻编码如果某个绘制对应的管线还没缓存它会同步编译——这是 vgpu 中唯一会阻塞等待管线创建的地方。解决方案是先预热对每个绘制的目标签名执行await effect.compile(signature)再录制。此时录制过程不再创建任何管线完全无感。target选项还接受纯签名对象如{ colors: [format] }让你能在真实画布 surface 创建之前就完成预热与录制。 静态回放 动态绘制混排同一个 pass 里回放与实时编码可以并肩工作frame.pass(canvasTarget, (pass) { pass.bundles(scene); // 静态部分回放 pass.draw(cursor); // 动态部分新鲜编码叠加其上 });注意两个必须留在动态侧的例外使用了blendConstant或带ref的stencil的绘制无法录制bundle 编码器无法设置这类 pass 级状态需要用pass.draw()实时编码。 窗口缩放无需重新录制bundle 是按渲染签名而非尺寸匹配回放目标的所以画布 resize 之后同一个 bundle 继续有效——千万不要仅仅因为目标变大/变小就重录。但采样关系是另一回事如果 bundle 采样的纹理被替换了例如跟随画布缩放的离屏目标被 resize原 bundle 会失效回放时抛出VGPU-R3-BUNDLE-STALE。此时按固定顺序替换即可录制新 bundle切换引用对新 bundle 成功后再dispose()旧 bundle。顺序很重要——如果录制失败旧 bundle 仍在位场景不会闪断。 如何释放不再需要的 bundle不做任何事也可以bundle 的存活不依赖它录制的绘制与资源失去最后一个引用后会被垃圾回收dispose()当你想在明确时点释放替换 bundle、视图销毁时调用。它同步且幂等只会解除 vgpu 的注册与引用绝不销毁被借用的绘制、几何、纹理和缓冲区。dispose()之后读取bundle.gpu或回放会抛出VGPU-BUNDLE-DISPOSED在pass.bundles(a, b)中只要有一个条目已 dispose整个列表都不会回放。⚖️ 什么时候不需要捆绑录制本身不是免费的每帧只有几个绘制时编码开销微乎其微。vgpu 的性能阶梯是effect.draw(target)—— 单个 pass 直接绘制frame(gpu)—— 把多个 pass 批量进一次 submitbundle(gpu)—— 跳过那些从不变化的重编码。绘制多、循环热bundle 才开始回本。 实战示例batch-rendering 批量渲染官方示例把 cube、pyramid、octahedron、icosahedron 四种几何体打包进一个顶点缓冲4096 个实例只录制成一个bundle每帧回放时仅用set()更新相机矩阵const recorded bundle(gpu, { target: colorTarget, label: batch-rendering-primitives }, (b) { for (const drawable of draws) b.draw(drawable); }); // 每帧p.bundles(scene.bundle)完整实现可见 scene-pipeline.ts。 延伸资料概念详解concepts-render-bundles.docs.mdBundle API 参考bundle.docs.md可运行入门示例example.ts录制 → 回放 → 验证 uniform 更新帧循环概念concepts-frames.docs.md【免费下载链接】vgpuModular cross-runtime WebGPU library for shaders, 3D scenes, GPU tensors, neural networks, and math viz项目地址: https://gitcode.com/gh_mirrors/vgpu/vgpu创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑