查看 webxr 耗时需利用 performance api 结合 requestanimationframe 的回调机制,在每一帧渲染前后记录时间戳并计算差值。具体做法是在 onxrframe 中通过 frame.getviewerpose() 获取姿态数据,并在调用 renderer.render() 前后分别使用 performance.now() 打点,从而分离出渲染管线与逻辑处理的耗时。

如何分离 WebXR 渲染帧的各阶段耗时
要精确分析性能瓶颈,必须将一帧的时间拆解为“应用逻辑”、“视图投影计算”和“GPU 提交”三个部分。核心在于捕获 XRFrame 对象后,立即记录开始时间,在处理完所有场景图更新后记录中间时间,最后在 renderer.render() 执行完毕后记录结束时间。这样得到的差值分别对应 CPU 侧的逻辑开销和 GPU 侧的绘制调用开销。

const session = await navigator.xr.requestSession('immersive-vr');
const frameTimeRef = { start: 0, logicEnd: 0, renderEnd: 0 };
session.requestAnimationFrame((time, frame) => {
// 1. 记录帧起始时间
frameTimeRef.start = performance.now();
// 2. 处理 XR 逻辑(如获取姿态、更新模型)
const pose = frame.getViewerPose(referenceSpace);
updateScene(pose);
// 3. 记录逻辑结束时间
frameTimeRef.logicEnd = performance.now();
// 4. 执行渲染
renderer.render(scene, camera);
// 5. 记录渲染结束时间
frameTimeRef.renderEnd = performance.now();
console.log(`Logic: ${(frameTimeRef.logicEnd - frameTimeRef.start).toFixed(2)}ms`);
console.log(`Render: ${(frameTimeRef.renderEnd - frameTimeRef.logicEnd).toFixed(2)}ms`);
session.requestAnimationFrame(arguments.callee);
});
上述代码展示了如何在单帧内通过三个时间点切分耗时。运行该程序后,控制台会输出类似 “Logic: 2.50ms” 和 “Render: 8.20ms” 的数据。开发者应重点关注 Logic 耗时是否超过 1-2ms,以及 Render 耗时是否导致帧率低于 90fps。若 Logic 耗时过高,需优化 updateScene 中的矩阵运算或场景遍历;若 Render 耗时过高,则需减少 Draw Call 或降低几何复杂度。
如何监控 WebXR 会话期间的平均帧率与掉帧情况
单次帧的耗时波动可能具有偶然性,因此需要建立长周期的监控机制来统计平均帧率(FPS)和检测掉帧。实现方法是维护一个固定大小的环形缓冲区或使用滑动窗口算法,持续收集每帧的总耗时(即当前帧 start 与上一帧 start 之间的时间差),并据此计算瞬时 FPS。当瞬时 FPS 显著低于目标值(如 72fps 或 90fps)时,标记为掉帧事件。

requestAnimationFrame
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











