#Directx12基本的Graphics概念和Direct3D类型(-)

来源:互联网 发布:同志交友软件 编辑:程序博客网 时间:2024/06/17 23:18

COM

  • Component Object Model(COM)是一种支持DirectX进行独立编程以及向前兼容的技术,在使用时常常将一个COM对象当做一个接口一样使用,大多数COM对象隐藏了具体的实现细节,因此也可以当做一种C++类来使用。然而与一般的C++类不同的是,我们不使用C++关键字New来获得一个COM对象,因为COM对象是一种特殊的引用计数对象,我们可以通过一些方法以及一些其他的COM接口获得一个COM对象。当使用完COM对象后,同样不需要使用delete关键字删除引用对象,而是调用COM对象的Release()方法,这个方法是COM的共同基类IUnknow接口的方法。调用Release()方法后将减少当前COM对象的引用计数,当引用计数减少到0时,COM对象会自动的释放自身占用的内存资源。

-为了方便管理COM对象的生命周期,WIndows系统运行环境库(WRL)在头文件**#include <wrl.h>**提供了Microsoft::WRL::ComPtr 类.ComPtr对象是一个智能指针对象,当超出作用域时会自动调用Release()方法释放底层的COM对象,在使用COM对象时,常常用到以下三个方法:

-GET():(用于需要一个指向COM接口一级指针的地方)
返回一个指向底层COM接口的指针,常常被用在传递COM接口指针的参数中,例如

        ComPtr<ID3D12RootSignature> mRootSignature;    mRootSignature->SetGraphicsRootSignature(mRootSignature.Get())

-GetAddressOf() :(用于需要一个指向COM接口二级指针的地方)

返回一个指向底层COM接口的指针的地址,常常用在需要返回一个COM接口指针的参数总。例如:

ComPtr<ID3D12CommandAllocator>  mDirectCmdListAlloc;ThrowIfFailed(m3d3Device->CreateCommandAllocator(D3D12_COMMAND_LIST_TYPE_DIRECT,mDirectCmdListAlloc.GetAddressOd()));

-Reset():
减小COM对象的引用计数,相当于设置ComPtr实例为nullptr

纹理格式(Textures Formats)

2D纹理是存储了数据元素的矩阵。2D纹理的一个用途是存储的2D图像数据,其中,在纹理存储每个元件的像素的颜色。然而数据元素并不一定是像素颜色;例如,在一个先进的技术称为法线贴图,每个元素在纹理存储3D矢量,而不是一个彩色。因此,通常在纹理转给你存储图像数据信息。一个1D纹理是像数据元素的一维阵列,二维纹理是表示类似于二维的数组,并且3D纹理是像数据元素的一个三维阵列。纹理其实不仅仅是数据的阵列;他们可以有mipmap级别和GPU可以做他们的特殊操作,如应用过滤器和多重采样。此外,纹理不能存储任意类型的数据元素;它只能存储某些类型的数据元素格式。如下常用的纹理格式

  • DXGI_FORMAT_R32G32B32_FLOAT : 每个元素包含3个32位的浮点数据组件
  • DXGI_FORMAT_R16G16B16A16_UNORM ;每个元素包含4个16bit数据映射到[0,1]的组件

  • DXGI_FORMAT_R32G32_UINT: 每个元素包含2个32位的无符号数据组件

  • DXGI_FORMAT_R8G8B8A8_UNORM:每个元素包含四个8bit数据映射到[0,1]

  • DXGI_FORMAT_R8G8B8A8_SNORM:每个元素包含四个8bit数据映射到[-1,1]

  • DXGI_FORMAT_R8G8B8A8_SINT:每个元素包含四个8bit数据映射到[-128,127]

  • DXGI_FORMAT_R8G8B8A8_UINT:每个元素包含四个8bit数据映射到[0,255]

  • DXGI_FORMAT_R16G16B16A16_TYPELESS:无格式类型,每个元素含有4个16bit的数据组件,但是每个数据可以是整型或者浮点型,需要在使用时指定

交换链(The Swap Chain)

  • 为了避免绘制时屏幕闪烁而采取的一种计数,绘制时先将图形绘制在backbuffer,绘制完成后,然后交换frontbuffer和backbuffer,如此循环以便于达到理想的效果

在Direct3D中,IDXGISwapChain接口代表着交换链,这个接口提供了常用的两个方法:

  • IDXGISwapChain::ResizeBuffers() //重置缓冲区
  • IDXGISwapChain::Present()

深度缓冲区(Depth Buffering)

深度缓冲区中包含了特定的像素点的深度信息而不是图像信息,其中的数据值是[0,1],每一个数据对应一个特定分辨率的像素点的信息。在开始渲染之前,深度缓冲区会被默认的颜色和默认的深度值初始化(通常是深度值最大值1.0)

这里写图片描述
上图示例了不同3D空间中的位置信息,需要获取最终显示那个图形的像素信息

通过每个图形的对应像素点的位置投影与默认的深度值比较可以得到最终的深入值以及最终显示的哪一个图像的像素信息,具体比较过程如下:

这里写图片描述

  • 由此我们可以得到一个结论,在渲染时只需要逐一的将要需要的像素深度值与比较前的深度值比较,如果要比较的深度值小于存储的深度值则更新深度值和颜色值,这样就能控制物体的正常的渲染顺序。

由于深度缓冲区也是一种纹理,因此其中的数据必须是确定的数据格式,常用的格式有:

  • DXGI_FORMAT_D32_FLOAT_S8X24_UINT:32位的浮点深度缓冲区,其中8bit被保留用于映射到[0,255]的模板缓冲区

资源描述符(Resources and Descriptors)

  • 在GPU执行渲染时,GPU会将数据写到资源中也会从资源从读取数据,因此在执行一个绘制命令时必须将资源绑定或者链接到渲染管线上,这些资源将会在渲染时被引用到。然而,GPU资源并不是直接绑定的,而是通过描述符对象(descriptor object)来引用的。描述对象结构是一种轻量级结构,通过它GPU能获得准确的资源数据和渲染所需的信息,所以,我们通过定义一个资源描述符对象来讲资源绑定到渲染管线中以便于被引用到。

  • 为什么不直接绑定资源到GPU,而要使用间接的资源描述对象了?答案在于,资源在内存中是一种通用的数据,它会在渲染管线的不同的阶段被引用到,例如一个纹理既可以是一个渲染对象也可能在某个阶段是作为shader的输入数据,甚至我们可能只是引用一个资源的一部分,而资源本身没有状态信息表示其作用,甚至资源本身可以是无类型的资源(typeless),此时,GPU甚至不知道数据的类型……

  • 这也是为什么引入资源描述对象的原因,它可以唯一的描述资源以供GPU使用,并且描述了这个资源将如何被使用。对于无类型的资源,必须在定义资源描述时确定类型。(注:在以前的老版本中,使用view而不是descriptors 描述资源)

  • 资源必须有确定的类型。常用的资源类型有:

  • CBV/SRV/UAV : constans buffers/shader resource/ unordered access view resource
    -RTV : render target 渲染对象
    -DSV :depth/stencil resource 深度和模板缓存资源

descriptor heap

_ 资源描述符头对象是一个资源描述对象的数组,它是应用程序中使用的资源的一个备份。对于每一种类型的资源描述都需要定义一个独立的资源描述头对象,当然也可以给同一个资源创建多个不同的资源描述头对象,例如对于一个纹理贴图资源,可以创建两个资源描述对象,一个用与RTV,另一个用在SRV。

-资源描述对象应该在创建的初始化,这是因为有一些类型检查和校验程序在运行。

………2016/10/5 12:05

0 0
原创粉丝点击