深度缓冲详解(DepthBuffer)

2023-11-18

参考出处:
1. OpenGL 深度缓冲区 Z缓冲区 介绍
2. 什么是深度缓冲(Depth Buffer)

1. 深度缓冲概念

深度缓冲区与帧缓冲区相对应,用于记录上面每个像素的深度值,通过深度缓冲区,我们可以进行深度测试,从而确定像素的遮挡关系,保证渲染正确。

2. 何为深度

深度其实就是该象素点在3d世界中距离摄象机的距离(绘制坐标),深度缓存中存储着每个象素点(绘制在屏幕上的)的深度值!深度值(Z值)越大,则离摄像机越远。

3. 为什么需要深度?

在不使用深度测试的时候,如果我们先绘制一个距离较近的物体,再绘制距离较远的物体,则距离远的物体因为后绘制,会把距离近的物体覆盖掉,这样的效果并不是我们所希望的。而有了深度缓冲以后,绘制物体的顺序就不那么重要了,都能按照远近(Z值)正常显示,这很关键。

4. 深度缓冲原理

深度缓冲区原理就是把一个距离观察平面(近裁剪面)的深度值(或距离)与窗口中的每个像素相关联。
首先,使用glClear(GL_DEPTH_BUFFER_BIT),把所有像素的深度值设置为最大值(一般是远裁剪面)。然后,在场景中以任意次序绘制所有物体。硬件或者软件所执行的图形计算把每一个绘制表面转换为窗口上一些像素的集合,此时并不考虑是否被其他物体遮挡。其次,OpenGL会计算这些表面和观察平面的距离。如果启用了深度缓冲区,在绘制每个像素之前,OpenGL会把它的深度值和已经存储在这个像素的深度值进行比较。新像素深度值<原先像素深度值,则新像素值会取代原先的;反之,新像素值被遮挡,他颜色值和深度将被丢弃。为了启动深度缓冲区,必须先启动它,即glEnable(GL_DEPTH_TEST)。每次绘制场景之前,需要先清除深度缓冲区,即glClear(GL_DEPTH_BUFFER_BIT),然后以任意次序绘制场景中的物体。

5. 深度测试

在默认情况是将需要绘制的新像素的z值与深度缓冲区中对应位置的z值进行比较,如果比深度缓存中的值小,那么用新像素的颜色值更新帧缓存中对应像素的颜色值。
但是可以使用glDepthFunc(func)来对这种默认测试方式进行修改。其中参数func的值可以为GL_NEVER(没有处理)、GL_ALWAYS(处理所有)、GL_LESS(小于)、GL_LEQUAL(小于等于)、GL_EQUAL(等于)、GL_GEQUAL(大于等于)、GL_GREATER(大于)或GL_NOTEQUAL(不等于),其中默认值是GL_LESS。
一般来将,使用glDepthFunc(GL_LEQUAL);来表达一般物体之间的遮挡关系。

6. 所带来的弊端

启用了深度测试,那么这就不适用于同时绘制不透明物体。当需要绘制半透明物体时,需注意,在绘制半透明物体时前,还需要利用glDepthMask(GL_FALSE)将深度缓冲区设置为只读形式,否则可能出现画面错误。为什么呢,因为画透明物体时,将使用混色,这时就不能继续使用深度模式,而是利用混色函数来进行混合。这一来,就可以使用混合函数绘制半透明物体了。

7. 深入

像素的深度值是由视矩阵和投影矩阵决定的。在近裁平面上的像素深度值为0,在远裁平面上的像素的深度值为1。场景中的每个对象都需进行绘制,通常最靠近相机的像素会被保留,这些对象阻挡了在它们后面的对象的可见性。
深度缓冲通常还包含stencil bits – 所以深度缓冲又被叫做depth-stencil缓冲。深度缓冲总是32 bits,但可以用不同的方式组合,类似于纹理格式。常用的深度格式是Depth32,这种格式中32 bits都用来存储深度信息。另一个常用格式是DepthFormat.Depth24Stencil8,这种格式中24 bits用于深度计算而8 bits用于模版缓冲(stencil buffer)。

8. 补充内容

颜色缓冲区(COLOR_BUFFER)就是帧缓冲区(FRAME_BUFFER),你需要渲染的场景最终每一个像素都要写入该缓冲区,然后由它在渲染到屏幕上显示.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

深度缓冲详解(DepthBuffer) 的相关文章

  • 计算边界球体半径时遇到一些问题

    我已经设法用两种方法计算边界球体半径 但没有一种方法能够准确地满足我的要求 我不需要 像素 完美边界球 但我想要比我目前拥有的更好的东西 我正在使用 Wavefront obj 模型并计算这些模型的边界球半径 我提取当前模型尺寸 我使用 N
  • 将 CVPixelBuffer 渲染到 NSView (macOS)

    我有一个CVPixelBuffer我正在尝试在屏幕上有效地绘制 转变为低效率的方式NSImage可以工作 但速度非常慢 丢掉了大约 40 的帧数 因此 我尝试使用将其渲染在屏幕上CIContext s drawImage inRect fr
  • 静态链接库时出现 glew 链接器错误

    我正在尝试在 Visual Studio 2012 中构建一个 opengl 项目 我想静态包含 glew 库 因此我从源代码构建它并将生成的 glew32sd lib 复制到我的 lib 目录 我将此 lib 路径提供给 Visual S
  • 交错顶点提交如何提高性能?

    我已经阅读并看到了其他问题 这些问题通常都指向将顶点位置和颜色等交错到一个数组中的建议 因为这可以最大限度地减少从 cpu 发送到 gpu 的数据 我不清楚的是 即使使用交错数组 您仍然必须对位置和颜色指针进行单独的 GL 调用 OpenG
  • (定义一个宏)方便OpenGL命令调试?

    有时插入条件打印和检查需要很长时间glGetError 使用二分搜索的形式来缩小范围 其中第一个函数调用是 OpenGL 首先报告错误 我认为如果有一种方法可以构建一个宏 我可以包装所有可能失败的 GL 调用 并有条件地调用 那就太酷了gl
  • OpenGL 的每个组件 alpha 通道?

    是否可以使用 OpenGL 对每个组件使用一个 alpha 通道 一个用于红色 一个用于绿色 一个用于蓝色 进行混合 如果没有 有哪些可能的解决方法 这不是直接支持的东西 不过 您自己实现起来相当容易 使用 3 通道 alpha 纹理渲染三
  • gluPerspective 与 gluOrtho2D

    我查看了 MSDN 上关于这两个函数的文档 但是 我不太明白这两个功能之间的区别 一个是用于设置 3D 相机视图 另一个是用于设置 2D 相机视图 如果能得到解答就太好了 预先感谢您的评论 正交投影基本上是没有透视的 3D 投影 本质上 这
  • 我的绘图存在坐标/glortho 问题

    I have made a bit of a change to my code in the last couple of hours as everything was messy with my grid so I made it i
  • 如何将点光源转换为卵形/椭圆形?

    我希望通过具有不同 x 和 y 值的 vec2 半径将当前的圆形光变成椭圆形 有没有办法根据我当前在片段着色器中的代码来做到这一点 uniform struct Light vec4 colour vec3 position vec2 ra
  • 简单的线框格式?

    我正在寻找一种用于线框模型的简单文件格式 我知道 VRML u3D 等 但这些对于我的需求来说似乎很重要 我的标准是 必须有明确的规格 要么是开放的 要么是非常完善 记录的 我只需要 想要 简单的模型 顶点和边 我不想处理面孔或物体 如果格
  • OpenGL 着色器不与着色器程序链接

    我正在尝试使用 GLFW GLEW 添加着色器 我收到一个错误 指出着色器已加载 但它们没有有效的对象代码 这是我用于加载着色器的代码 class SHADER public void LoadShaders const char vert
  • 阻止 OpenGL.framework 在 Cocoa 应用程序中加载

    我的应用程序链接到这些框架 Cocoa Framework AppKit Framework CoreData Framework Foundation Framework 请注意 OpenGL Framework 是NOT已链接 但是 设
  • SDL 鼠标位置调整大小后裁剪

    我在 SDL 中的鼠标位置上遇到了一些奇怪的行为 如果我将窗口大小调整得更大 则任一鼠标事件的 x y 位置似乎都限制为原始窗口的宽度和高度 如果我缺少一些函数调用来告诉 SDL 鼠标区域的大小已增加 应用程序的相关部分 void Resi
  • 当 OpenGL 中同时绑定 1D 和 2D 纹理时,正确的行为是什么?

    假设你有这样的东西 glBindTexture GL TEXTURE 2D my2dTex glBindTexture GL TEXTURE 1D my1dTex glBegin 正确的 OpenGL 行为是什么 要绘制一维纹理 二维纹理还
  • 为什么拥有单独的投影矩阵但结合模型和视图矩阵会有好处?

    当您学习 3D 编程时 您会被告知用 3 个变换矩阵来思考是最简单的 模型矩阵 该矩阵对于每个模型都是独立的 它根据需要旋转和缩放对象 最后将其移动到 3D 世界中的最终位置 模型矩阵将模型坐标转换为世界坐标 视图矩阵 对于大量对象 如果不
  • GL_CULL_FACE使所有对象消失

    我正在尝试在 openGL3 3 中创建一些简单的多边形 我有两种类型的对象 具有以下属性 对象 1 10 个顶点 按顺序在下面列出 存储在GL ARRAY BUFFER并使用GL TRIANGLE FAN v x y z w v 0 0
  • Visual Studio 2010 中的 SOIL 设置

    我无法得到SOIL http www lonesock net soil html正确使用 Visual Studio 2010 我远非 VS 专家 但据我所知 只需执行以下步骤即可使环境正常运行 属性 gt gt C C gt 常规 gt
  • 三角形纹理映射OpenGL

    我正在开发一个使用 Marching Cubes 算法并将数据更改为 3D 模型的项目 现在我想在 OpenGL 中为我的 3D 模型使用纹理映射 我首先尝试了一个简单的示例 它将图片映射到三角形上 这是我的代码 int DrawGLSce
  • OpenGL:仅获取模板缓冲区而没有深度缓冲区?

    我想获取一个模板缓冲区 但如果可能的话 不要承受附加深度缓冲区的开销 因为我不会使用它 我发现的大多数资源表明 虽然模板缓冲区是可选的 例如 排除它以利于获得更高的深度缓冲区精度 但我还没有看到任何请求并成功获取仅 8 位模板缓冲区的代码
  • 使用 GLSL 直接在着色器中从位置计算平移矩阵

    我正在开发 C OpengL 程序以及 GLSL 顶点和片段着色器 我正在创建同一对象的多个实例 我只需要改变实例之间的对象位置 这是我所做的 我正在使用一个统一变量 它是一个变换矩阵数组 每个矩阵代表一个对象实例 MVP 也是一个变换矩阵

随机推荐

  • 如何使用vscode开发uniapp并运行

    如何使用vscode开发uniapp并运行 1 必须先下载HBuilderX然后导入你需要开发的uni项目 2 然后在vscode中再次打开你的uni项目 3 去vscode插件市场安装一个uni helper这个插件 4 即可在vscod
  • java 利用ganymed-ssh2 远程执行linux shell 命令

    早期的ganymed ssh2包也可以实现远程调研linux shell 命令 但是这个包最新版本是2014年之后 就没有更新了 发现linux 操作系统安装 open ssh 8 5及更高级版本 就一直提示连接失败 可以使用jsch 最新
  • linux内存利用率计算方式

    一 查看内存的方式 root vmware free h root vmware cat proc meminfo 需要使用的指标有 MemTotal MemFree Buffers Cached MemTotal 总内存大小 MemFre
  • 计算半圆弧的周长及半圆的面积

    3 计算半圆弧的周长及半圆的面积 编程并输出半径r 5 3的半圆弧长 提示 半圆弧长不应该加直径的长度 及该半圆弧与直经围成的半圆的面积 的取值为3 14159 要求半径r和必须利用宏常量表示 include
  • MacOS怎么查看进程占用内存是多少

    一 背景 在Linux下可以使用 free 命令来方便的查看内存占用情况 如 free g free m等 但MacOS下没有这个命令 既然如此 那么MacOS里是否有类似的工具呢 而我们又该如何查看整个PC的内存占用情况 及指定进程的内存
  • 慢慢欣赏linux pud_offset解析

    typedef struct pudval t pud pud t gt typedef u64 pudval t dir表示L0页表索引的指针 指向PUD页表的基地址 define pud offset dir addr pud t va
  • 《计算机工程》期刊 从投稿到录用过程

    本人 18级双一流院校全日制研究生在读 专业 地理学 研究方向 激光雷达数据处理与三维点云语义分割 文章投计算机工程期刊从投稿到可刊总周期 两个月之内 审稿费100元 可加急 发表情况 预计十月发表 期刊选择 论文修改完成之后 自己有上网了
  • 教你利用IBM的开发手册

    在IBM AIX下做开发的不少人一直都不知道IBM其实已经提供了详尽的开发文档及手册供开发人员使用 很多人仍然使用很原始的方式 例如在GOOGLE中搜索 或者买本手册型的书放在边上 更有甚者直接记在脑子里 这算是相当聪明的了 但是 有许多与
  • 山石发声

    技术变化快 投入不可控 攻击侧升级 攻防不对等 人才缺口大 维护成本高 山石网科安全运营体系 让安全运营挑战迎刃而解 近年来 全球安全服务市场景气度较高 行业增速远高于安全行业的整体水平 究其原因 首先是IT基础架构的变化驱动安全服务体系的
  • java每日一题:手动触发垃圾回收(GC)

    面试官 首先 我想问一下 你能向我解释一下 手动触发Java垃圾回收 的过程吗 面试者 在Java中 垃圾回收是自动进行的 由Java虚拟机 JVM 负责管理 但是 有时候我们可能希望手动触发垃圾回收以释放一些无用的对象 这可以通过调用Sy
  • Scrapy的基本介绍、安装及工作流程

    一 Scrapy介绍 Scrapy是什么 Scrapy 是用 Python 实现的一个为了爬取网站数据 提取结构性数据而编写的应用框架 异步爬虫框架 通常我们可以很简单的通过 Scrapy 框架实现一个爬虫 抓取指定网站的内容或图片 Scr
  • 程序员搜索技巧

    1 搜索时 一定使用关键字搜索 空格 浓缩减少废话与口语 不断负反馈增添修改关键词 再不行就英文 2 精确搜索 作为整体 用 双引号 3 查找标题含有的确定关键词 intitle 英文冒号 4 站内搜索 过滤垃圾广告 定位某一网址答案 xx
  • Cobertura 统计多模块maven项目测试覆盖率

    Cobertura 统计单元测试覆盖率的机制 运行类 并在一个log文件中记录哪一行被执行 然后将源代码和log文件进行比对 1 简单的情况 单模块maven项目 项目结构 源代码 src main java se sigma calcul
  • OpenCV图像人脸检测及视频中的人脸检测(附源码)

    文章目录 一 数据和知识准备 1 下载HAAR与LBP数据 2 opencv相关知识 二 python opencv实现人脸检测 1 图像单人脸检测 2 图像多人脸检测 3 视频中人脸检测 4 摄像头人脸检测 一 数据和知识准备 1 下载H
  • java中的垃圾回收机制

    概述 JAVA中的垃圾回收机制是自动的 它是保证程序健壮的主要手段 同时也避免了回收内存带来的代码繁琐 注意 1 java中的垃圾回收机制采用的是多线程技术实现的 垃圾回收功能是一条优先级比较低的线程 2 垃圾回收机制仅仅作用于堆内存 和栈
  • Unity一些很有用的技巧

    一 性能 多线程射线检测 在使用中经常需要每帧进行射线 性能消耗比较大 那么可以使用Unity Collections RaycastCommand进行多线程的检查 将耗能操作放到子线程去 同样其他的形状检测 Unity官方文档 Rayca
  • Python每日一记196>>>pandas.core.indexing.IndexingError: Too many indexers

    以下代码出现了pandas core indexing IndexingError Too many indexers问题 import pandas as pd import numpy as np data 2018 pd read e
  • Rust组合器

    组合器 在 Rust 中 组合器更多的是用于对返回结果的类型进行变换 例如使用 ok or 将一个 Option 类型转换成 Result 类型 下面我们来看看一些常见的组合器 or 和 and 跟布尔关系的与 或很像 这两个方法会对两个表
  • JAVA 8 junit 单元测试——静态方法单元测试 Mockito.mockStatic

    静态方法的单元测试Mockito 直接上例子 方法 public ArrayList
  • 深度缓冲详解(DepthBuffer)

    参考出处 1 OpenGL 深度缓冲区 Z缓冲区 介绍 2 什么是深度缓冲 Depth Buffer 1 深度缓冲概念 深度缓冲区与帧缓冲区相对应 用于记录上面每个像素的深度值 通过深度缓冲区 我们可以进行深度测试 从而确定像素的遮挡关系