• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            3d Game Walkman

            3d圖形渲染,網絡引擎 — tonykee's Blog
            隨筆 - 45, 文章 - 0, 評論 - 309, 引用 - 0
            數據加載中……

            Early ZBuffer [轉]

            看到這篇文章寫的還不錯,順手轉過來了^_^
              
               一、最近在優化客戶端性能的時候,看到了Early ZBuffer。在VSPS中間GPU會對進行Z-buffer預判機制,對無效像素進行剔除,ATI、NVIDIA都有自己的Z-buffer預判機制。其實Doom3的時候已經開始使用預填充ZBuffer了,因為Doom3的PS需要處理陰影、NormalMap、LightMap及其他貼圖處理,PS指令非常多,所以無效像素的剔除對性能影響是很大的,越早將無效像素剔除,顯卡便能獲得更多的時間對有效像素進行渲染。

             

                二、Early-Z技術介紹(這段摘自http://tech.sina.com.cn/h/2008-06-17/09302262913.shtml

              當代的GPU都會采用Z-buffer去記錄哪些像素是可見,而哪些像素是被遮擋而不可見。一個3D Frame最終要轉換成為2D圖像才能表示在屏幕上面,來自GPU連續的頂點流(vertices)會構建這個frame,從這個頂點流獲取相應的2D坐 標去生成多邊形。多邊形的連續產生會覆蓋原來的區域,因而Z-buffer的信息就是告訴ROP,哪些像素是可見哪些是不可見的。提前進行的Early- Z對比可以節省大量資源,因為同一個區域被多個多邊形覆蓋的次數輕而易舉地達到原來的四倍甚至更高





            目前甚少方法可以利用Z-buffer信息去挑選或者排出被遮擋像素的渲染,Z-Cull就是這樣的一個方法。Z-comparision通常 會發生在ROP的后期。問題就產生,意味著pixel要通過完整的ROP管線才能被發現是否可見。一些復雜的包含數千步驟的shader程序,即使是被遮 擋的pixel也全部通過流水線,這顯然浪費了GPU的性能。Early-Z移去不可見像素在它們進入流水線之前,這樣顯然會提高性能,NVIDIA認為 這個操作提升22%附近的性能。

             

                三、具體實現:場景渲染兩遍:
                void Render()
                {
                    DrawZPass();    
                    DrawColorPass();    
                }
                
                // 關閉ColorBuffer寫入,以最簡單的渲染狀態繪制場景
                void DrawZPass()
                {
                    // Disable color writes
                    pD3DDevice->SetRenderState( D3DRS_COLORWRITEENABLE, 0x00000000);

                    // Ensure alpha off
                    pD3DDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, false );
                    pD3DDevice->SetRenderState( D3DRS_ALPHATESTENABLE, false );

                    // Ensure z-enabled
                    pD3DDevice->SetRenderState( D3DRS_ZENABLE, true );
                    pD3DDevice->SetRenderState( D3DRS_ZWRITEENABLE, true );

                    DrawScene();

                    pD3DDevice->SetRenderState( D3DRS_COLORWRITEENABLE, 0x0000000F );
                }

                // 正常渲染
                void DrawColorPass()
                {
                    pD3DDevice->SetRenderState( D3DRS_DEPTHBIAS, F2DW(-0.001f) );    
                    DrawScene()
                }

                1.DrawZPass:應該跳過AlphaBlend、AlphaTest的實體。
                2.DrawColorPass:對于那些預寫入ZBuffer的實體,在這個Pass中只需開啟ZBufferTest、并且可以關閉ZBufferWrite。
                3.使用了EarlyZBuffer,就不用再排序了。

                4.在第二遍渲染的時候,因為浮點的誤差,會有ZFighting現象,所以應允許一定的誤差。

                5.Early ZBuffer不一定適用所有場景,比如有大量實體的室外場景,因為DrawZPass畢竟也要繪制所有的實體,如果調用太多DP,性能反而會有所下降。


                 四、另外一個性能優化提示:先畫UI;最后繪制天空盒。這也于ZBuffer有關,因為天空盒總是顯示在最后,而天空盒總是被前面的實體遮擋了大部分區域。

            不過最后繪制天空盒時候,大家會問如何避免被FarPlane裁剪,有一個技巧可以解決,在SkyShader的VS輸出投影后的位置時,這樣設置:

                 Out.position = mul(mvp, vertex).xyww。// 不是Out.position = mul(mvp, vertex);

                這樣天空盒投影后的總是映射到FarPlane,這樣就完美了,哈哈。這個方法時我在ATI的《Depth In Depth》文檔中看到的。UI也是,游戲里的UI區域如果預先寫入ZBuffer,也可以避免大量的無效PS處理。


                 五、最后希望大家可以仔細看看《Depth In Depth》,里邊有很多優化提示。

            posted on 2009-12-01 14:20 李侃 閱讀(2543) 評論(0)  編輯 收藏 引用 所屬分類: 前臺客戶端

            久久久久久久亚洲Av无码| 久久久国产精品网站| 亚洲人AV永久一区二区三区久久| 久久精品一本到99热免费| 波多野结衣中文字幕久久| 久久综合综合久久狠狠狠97色88| 国产高潮国产高潮久久久| 国产精品美女久久久久av爽| 亚洲日本va午夜中文字幕久久| 国内精品人妻无码久久久影院导航| 久久久久久久亚洲Av无码| 国产精品热久久无码av| 亚洲va国产va天堂va久久| 国产精品久久自在自线观看| 91精品久久久久久无码| 一本久久综合亚洲鲁鲁五月天亚洲欧美一区二区 | 亚洲精品乱码久久久久久中文字幕| 97久久天天综合色天天综合色hd| 久久精品国产一区二区三区不卡| 欧美牲交A欧牲交aⅴ久久| 久久精品亚洲乱码伦伦中文| 国产激情久久久久影院| 久久久久久毛片免费播放| 久久婷婷五月综合色高清 | 欧美黑人激情性久久| 色婷婷久久综合中文久久一本| 91久久香蕉国产熟女线看| 97久久超碰国产精品旧版| 国产精品久久久久久吹潮| 色偷偷久久一区二区三区| av无码久久久久不卡免费网站| 中文字幕久久波多野结衣av| 国产精品久久久久国产A级| 91精品国产高清91久久久久久| 国产精品久久国产精麻豆99网站| 99久久免费国产特黄| 热re99久久精品国产99热| 国产精品成人精品久久久| 色播久久人人爽人人爽人人片aV | 浪潮AV色综合久久天堂| 久久久久亚洲精品天堂久久久久久|