swapchain , context 和 device 的区别与联系

除此篇随笔外, 还有另外一篇转载: http://www.cnblogs.com/Wilson-Loo/articles/2797613.html

一些概念, 特别是 IT 领域的, 尤其需要弄明白其本质、工作特点、机制后, 才能更好地去使用; 才不会在编码过程中 思考于为什么要这样调用呢, 为什么一定是 device_>createBuffer() 而不能是 context_->createBuffer() 呢?!此番会将经历浪费在无谓的思考上, 不能专注于当下的整个项目工作; 但有思考还好啦, 说明还是有改善、进修的契机; 可怕的是 仅仅是照着 Tutorials教程 一个个单词的抄着, 或者 copy + C/V, 待整本书抄完了, 就好像学会了似的。

以前在 还没有看 《effective c++》 系列书籍 的时候, 看别人代码是总是不明白为什么要 在 函数参数列表的括号 右边使用 冒号, 然后又应用各种古怪的表示( 呃, 构造函数的 初始化参数列表); 没看《设计模式》前, 总是纳闷代码间 为什么要那样组织, 像helloword 那样不是很清爽的吗!

后来才明白其中的原委, 机制, 处于什么考量, 渐渐的自己的编写的代码方式 也随着改变, 看别人代码时 也很容易“入眼”, 更多的时间花在了有用的书本 正确观点的 阅读学习上, 而不会纠结于 “这本书的纸张颜色为什么不是 黄色的呢?”! 这些自杀式自我思考。

 

回到正题, 经我 这两个星期来的学习, 对 context, device 和 swapchain 的区别 和联系 有了如下的认识, 加深了自己的认知。

context :设备上下文, 用来渲染 指令的。 作为 操作相关处理的“接口”而非对象, 正如下图:

device 作为 “实际对象”, 管理存储各种数据(当然也负责与 hardwar的沟通), 而 context 更多的是 “提供操作的接口”, 通常用来告知 device 进行如何绘图 how to draw, 正如

 http://msdn.microsoft.com/zh-cn/library/windows/desktop/hh404598(v=vs.85).aspx

所说: The device context interface represents a device context; it is used to render commands. 通过 ID3D11DeviceContext 接口的函数可知:

Methods
The ID3D11DeviceContext1 interface has these methods.
------------------------------------------------------
Method()                    // Description
ClearView()                    // Sets all the elements in a resource view to one value.
CopySubresourceRegion1()    // Copies a region from a source resource to a destination resource.
CSGetConstantBuffers1()        // Gets the constant buffers that the compute-shader stage uses.
CSSetConstantBuffers1()        // Sets the constant buffers that the compute-shader stage uses.
DiscardResource()            // Discards a resource from the device context.
DiscardView()                // Discards a resource view from the device context.
DiscardView1()                // Discards the specified elements in a resource view from the device context.
DSGetConstantBuffers1()        // Gets the constant buffers that the domain-shader stage uses.
DSSetConstantBuffers1()        // Sets the constant buffers that the domain-shader stage uses.
GSGetConstantBuffers1()        // Gets the constant buffers that the geometry shader pipeline stage uses.
GSSetConstantBuffers1()        // Sets the constant buffers that the geometry shader pipeline stage uses.
HSGetConstantBuffers1()        // Gets the constant buffers that the hull-shader stage uses.
HSSetConstantBuffers1()        // Sets the constant buffers that the hull-shader stage of the pipeline uses.
PSGetConstantBuffers1()        // Gets the constant buffers that the pixel shader pipeline stage uses.
PSSetConstantBuffers1()        // Sets the constant buffers that the pixel shader pipeline stage uses.
SwapDeviceContextState()    // Activates the given context state object and changes the current device behavior to Direct3D 11, Direct3D 10.1, or Direct3D 10.
UpdateSubresource1()        // The CPU copies data from memory to a subresource created in non-mappable memory.
VSGetConstantBuffers1()        // Gets the constant buffers that the vertex shader pipeline stage uses.
VSSetConstantBuffers1()        // Sets the constant buffers that the vertex shader pipeline stage uses.
 

这些函数都几乎是 用来 操作(已存在的数据相关的)数据, 而不会创建数据、对象。例如前面我们已经使用到的 

d3dContext_->OMSetRenderTargets( 1, &backBufferTarget_, 0 );
d3dContext_->RSSetViewports( 1, &viewport);
d3dContext_->ClearRenderTargetView( backBufferTarget_, clearColor);

//还有后面用到的:
d3dContext_->IASetInputLayout( inputLayout);
d3dContext_->IASetVertexBuffer( 0, &vertexBuffer_, &stride, &offset);
d3dContext_->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);

d3dContext_->VSSetShader( solidColorVS, 0, 0);
d3dContext_->PSSetShader( solidColorPS, 0, 0);

d3dContext_->Draw( 3, 0); 

 

第二,device 就是一个虚拟适配器, 和硬件交互, 用力创建资源:

http://msdn.microsoft.com/zh-cn/library/windows/desktop/ff476379(v=vs.85).aspx

The device interface represents a virtual adapter; it is used to create resources.

// 前面使用到的:
d3dDevice_->CreateRenderTargetView( backBufferTexture, 0, &backBufferTarget_);
d3dDevice_->CreateBuffer( &vertexDesc, &resourceData, &vertexBuffer);
d3dDevice_->CreateVertexShader( vsBuffer->GetBufferPointer(), vsBuffer->GetBufferSize(), 0, &solidColorVS);
d3dDevice_->CreatePixelShader( psBuffer->GetBufferPointer(), psBuffer->GetBufferSize(), 0, &solidColorPS);d3dDevice_->CreateInputLayout( vertexLayout, totalLayoutElements, vsBuffer->GetBufferPointer(), vsBuffer->GetBufferSize(), &inputLayout);

// 后面使用的:
d3dDevice_->CreateSampleState( &colorMapDesc, &colormapSampler_);
d3dDevice_->CreateBlendState( &blendDesc, &alphaBlendState_ );

 第三, swapchain 实现了一个或多个的 surface 用来存储 输出到输出设备output device 之前的各种 “渲染数据”, 做得数据后台加速:

http://msdn.microsoft.com/zh-cn/library/windows/desktop/bb174569(v=vs.85).aspx

An IDXGISwapChain interface implements one or more surfaces for storing renderd data before presenting it to an output.

Methods
The IDXGISwapChain interface has these methods.
---------------------------------------
Method    Description
GetBuffer()                // Accesses one of the swap-chain's back buffers.
GetContainingOutput()    // Get the output (the display monitor) that contains the majority of the client area of the target window.
GetDesc()                // Get a description of the swap chain.
                        //     Note Starting with Direct3D 11.1, we recommend not to use GetDesc anymore to get a description of the swap chain. Instead, use IDXGISwapChain1::GetDesc1.
GetFrameStatistics()    // Gets performance statistics about the last render frame.
GetFullscreenState()    // Get the state associated with full-screen mode.
GetLastPresentCount()    // Gets the number of times that IDXGISwapChain::Present or IDXGISwapChain1::Present1 has been called.
Present()                // Presents a rendered image to the user.
                        //     Note  Starting with Direct3D 11.1, we recommend not to use Present anymore to present a rendered image. Instead, use IDXGISwapChain1::Present1. For more info, see Remarks.
ResizeBuffers()            // Changes the swap chain's back buffer size, format, and number of buffers. This should be called when the application window is resized.
ResizeTarget()            // Resizes the output target.

 大部分 函数都是 与 buffer的状态相关, 不像 device的 createXXX() 创建对象, 也不像context 的 SetYYY() 设置较大功能。

另外, 从本随笔开头的图可看出, context 大部分的 “动词”, device 是 “名词”的创建/管理, 而swapchain 就是缓冲加速器。

-- the end.

posted @ 2012-12-01 15:06  Wilson-Loo  阅读(2712)  评论(1编辑  收藏  举报