码农知识堂 - 1000bd
  •   Python
  •   PHP
  •   JS/TS
  •   JAVA
  •   C/C++
  •   C#
  •   GO
  •   Kotlin
  •   Swift
  • JavaScript WebGL 绘制顺序


    引子

    在 JavaScript WebGL 三维相关概念中尝试一些效果的时候,又碰到了新问题,就去查了资料,自己尝试后总结下。

    • Origin
    • My GitHub

    绘制顺序

    之前二维绘制顺序并没有产生明显的不好效果,现在绘制三维影响就比较大了。

    先看看二维相同一套顶点不同顺序的效果:

    • 二维面顺序示例 1
    • 二维面顺序示例 2

    面的颜色始终保持一致,但顺序变了,发现 WebGL 默认情况下会按照缓冲区中顺序绘制,也就是后绘制的图形会覆盖先绘制的图形。这个就像一层一层贴纸一样,比较符合一般认知,所以在二维绘制时并没发现明显不对劲的地方。

    关于三维绘制顺序先思考一下:三维的顶点坐标有三个分量,第三个分量是在 z 轴上表示深度信息,默认垂直屏幕向内为负方向,那么 z 值越大表示离屏幕越近,既然都有区分的依据,直接按照这个顺序绘制应该就可以了。实际试试:

    • 三维面顺序示例 1
    • 三维面顺序示例 2

    发现示例 2 中 z 分量的设置并没有效果,还是跟二维绘制面顺序一样。查资料说要开启隐藏面消除功能:

    gl.enable(gl.DEPTH_TEST)
    
    • 1

    再来看看示例 2 开启 DEPTH_TEST,发现还是没有效果,找到网上的一些示例并进行对比,发现还需要投影,才能看到效果,见示例 2 开启 DEPTH_TEST 且产生正确投影。

    深度冲突

    开启隐藏面消除功能之后,在绘制两个很靠近的面时,可能会出现显示异常的情况,这个现象称为深度冲突(Z fighting)。这里有两类这个现象的示例:

    • drawArrays 执行一次绘制,里面包含了两个面示例1
    • drawArrays 执行两次绘制,单独绘制的两个面示例2

    示例 1 的情况是一次绘制多个面,通过调整 z 分量比较容易解决。

    示例 2 的情况是多次绘制多个面,不确定性相对更强,这个时候可以借助 多边形偏移(polygon offset) 来解决。在两次绘制之间指定偏移:

      // 代码省略
      gl.enable(gl.POLYGON_OFFSET_FILL);
      gl.drawArrays(gl.TRIANGLES, 0, 3); // 开启多边形偏移
      gl.polygonOffset(1, 1); // 指定偏移
      gl.drawArrays(gl.TRIANGLES, 3, 3);
    
    • 1
    • 2
    • 3
    • 4
    • 5

    这是示例。

    polygonOffset(factor, units) 指定加到每个顶点绘制 z 值上的偏移量,两个参数都是比例因子,最终值的计算公式是 factor × DZ + r × units ,其中 DZ 是顶点所在表面相对于观察者视线的角度, r 是设备能够解析偏移量的最小值。这个方法对于渲染隐藏线图像、将贴花应用于表面以及渲染具有高亮显示边缘立体图形很有用。

    参考资料

    • polygonOffset mdn
    • WebGL编程指南在线版
  • 相关阅读:
    influxdb2的使用
    利用SpringBoot+rabbitmq 实现邮件异步发送,保证100%投递成功
    数字电路与逻辑设计之 设计电路 之无反变量
    (最新版2022版)剑指offer之树和二叉树题解
    数据压缩STC稀疏三元压缩算法复现
    竞赛 深度学习卫星遥感图像检测与识别 -opencv python 目标检测
    STC15单片机-串口打印printf重定向
    React中封装echarts图表组件以及自适应窗口变化
    80. 删除有序数组中的重复项 II
    MySQL 索引
  • 原文地址:https://blog.csdn.net/u011194386/article/details/126220716
  • 最新文章
  • 【JVM】编译执行与解释执行的区别是什么?JVM 使用哪种方式?
    用 Hashids 优雅解决 C 端自增 ID 暴露问题
    V8引擎 精品漫游指南--Ignition篇(上) 指令 栈帧 槽位 调用约定 内存布局 基础内容
    LLVM Pass快速入门(四):代码插桩
    milkup:桌面端 markdown AI续写和即时渲染
    基于项目工程构建SBOM(软件物料清单)的研究
    鸿蒙应用开发UI基础第二节:鸿蒙应用程序框架核心解析与实操
    .NET 中如何快速实现 List 集合去重?
    扣子Coze实战:从0到1打造抖音+小红书热点监控智能体
    浅谈数据访问层
  • 热门文章
  • 十款代码表白小特效 一个比一个浪漫 赶紧收藏起来吧!!!
    奉劝各位学弟学妹们,该打造你的技术影响力了!
    五年了,我在 CSDN 的两个一百万。
    Java俄罗斯方块,老程序员花了一个周末,连接中学年代!
    面试官都震惊,你这网络基础可以啊!
    你真的会用百度吗?我不信 — 那些不为人知的搜索引擎语法
    心情不好的时候,用 Python 画棵樱花树送给自己吧
    通宵一晚做出来的一款类似CS的第一人称射击游戏Demo!原来做游戏也不是很难,连憨憨学妹都学会了!
    13 万字 C 语言从入门到精通保姆级教程2021 年版
    10行代码集2000张美女图,Python爬虫120例,再上征途
小工具 小游戏
Copyright © 2022 侵权请联系2656653265@qq.com    京ICP备2022015340号-1

京公网安备 11010502049817号