三.js:分层和解决z-fighting更有效:使用polygonOffsetFactor或禁用depthWrite的透明度?
Posted
技术标签:
【中文标题】三.js:分层和解决z-fighting更有效:使用polygonOffsetFactor或禁用depthWrite的透明度?【英文标题】:three.js: What is more efficient to layer and resolve z-fighting: using polygonOffsetFactor or transparency with depthWrite disabled? 【发布时间】:2018-08-12 07:00:00 【问题描述】:我正在使用 THREE.js 开发一个图表软件。一些绘制的矩形在同一平面上,所以会出现 z-fighting,尤其是但不限于,当我移动相机时。
我找到了两种适合我的解决方案。
第一:
polygonOffset: true,
polygonOffsetUnits: 1,
polygonOffsetFactor: -rectCount
其中 rectCount 是绘制的矩形总数(因此每个下一个具有较小的 polygonOffsetFactor,因此绘制在前一个矩形的“顶部”)。
第二:
transparent: true,
depthWrite: false
renderOrder = rectCount
.
我知道不透明物体和透明物体是按三分开排序的,所以如果我使用第二种方法,我也必须设置
transparent: true
opacity: 1
我想在上述矩形上绘制的所有其他对象。
第二个解决方案感觉更干净,TBH,更有效(而使用 polygonOffsetFactor 偶尔仍然会出现 z-fighting),但我担心为场景中的许多对象启用透明度(即使不透明度设置为 1)会对渲染效率有不利影响。假设我希望它足够轻巧,也可以在移动设备上运行。
我不知道 THREE 的内部结构,但我希望在考虑任何透明魔法之前先检查不透明度。
问题:我可以安全使用
transparent: true,
opacity: 1
在许多对象上,它不会严重影响渲染/CPU/GPU 周期?或者对于这种用例,使用 polygonOffsetFactor 被认为更有效?谢谢!
【问题讨论】:
请注意,this OpenGL polygonOffset 文档点 13.020 提到使用 polygonoffset 时有两个通道 - 这是可能答案的一些提示。 【参考方案1】:刚刚看到这个贴花示例,可能会有所帮助。 https://github.com/mrdoob/three.js/blob/master/examples/webgl_decals.html
const decalMaterial = new THREE.MeshPhongMaterial(
specular: 0x444444,
map: decalDiffuse,
normalMap: decalNormal,
normalScale: new THREE.Vector2( 1, 1 ),
shininess: 30,
transparent: true,
depthTest: true,
depthWrite: false,
polygonOffset: true,
polygonOffsetFactor: - 4,
wireframe: false
);
【讨论】:
【参考方案2】:深度写入错误对于所有距离都更可靠。如果由于其他原因最终需要更高的深度排序精度,请考虑在渲染器构造函数中设置 logarithmicDepthBuffer:true。
【讨论】:
决定重写我的评论。谢谢你的指点:)。我使用的是小距离和小相机变焦值(0.3 ~ 3),所以虽然我很高兴了解另一种类型的 depthBuffer,但我假设它可能对小距离没有帮助。如果我理解正确,您确认depthWrite: false
比 polygonOffset 更可靠——我也相信是这种情况。对于任何对 logDepthBuffer 感兴趣的人,这里有一个 demo :)以上是关于三.js:分层和解决z-fighting更有效:使用polygonOffsetFactor或禁用depthWrite的透明度?的主要内容,如果未能解决你的问题,请参考以下文章