zoukankan      html  css  js  c++  java
  • directX学习系列8 颜色融合(转)

      1, Multipass(多通道) 
      将一个任务划分成几个阶段,由多个pass处理不同阶段,后续pass总是处理前一个pass的结果。例如复杂的光照方程可以分成几个pass来计算。 
      用不同的纹理通过多个pass来多次渲染一个图元,这样可以实现许多很酷的特效。例如LightMap,它就是用不同的纹理来表示复杂的光、影效果。 
      2, Multitexture(多纹理) 
      很显然,pass越多,效率越低。为了降低pass的数量,有些硬件加速卡支持在一个pass中渲染两个或更多的纹理,这种技术就叫做multitexture。D3D在一个pass中最多支持8个纹理的混合。 
      3, Pipeline(管道) 
      可以将管道想像成一条流水线,它完成某项任务。 
      4, Stage 
      一个管道可以由多个stage组成,这些stage同时运行,所以管道的速度取决于最慢的stage。 
      5, Texture   blending   cascade 
      Texture   blending   cascade是一个pipeline,它完成在一个pass中混合多个纹理这个任务。 
      6, Texture   Stage(也叫做texture   unit) 
      Texture   blending   cascade由许多Texture   Stage构成,每个Texture   Stage混合两个纹理(或经过计算的顶点集),通常是RGB和Alpha值,并将结果(经过计算的顶点集)传递给下一个Texture   Stage。 
      理解了上面的那些概念,理解SetTextureStageState函数就很容易了。 
      HRESULT   SetTextureStageState( 
          DWORD   Stage, 
          D3DTEXTURESTAGESTATETYPE   Type, 
          DWORD   Value 
      ); 
      1, Stage参数,D3D支持8个Texture   Unit,索引值由0~7,通过此参数你可以指定是哪一个Texture   Unit。 
      2, Type参数,用来选择Texture   Stage不同的状态,如D3DTSS_COLOROP代表颜色混合操作,D3DTSS_ALPHAOP代表ALPHA值混合操作。 
      3,             Value参数,根据不同的Type,来设置其状态值。如:SetTextureStageState(   0,   D3DTSS_COLOROP,       D3DTOP_ADD   ),就是指在第一个Texture   Unit中,将两个颜色值的混合操作设定为累加。  /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

    HRESULT SetTextureStageState(
       DWORD Stage,
       D3DTEXTURESTAGESTATETYPE Type,
       DWORD Value
       );

       stage这个参数是指第几层纹理,1.2.3...9,, 这个版本的dx最多支持9层纹理。
       Type:Defines the type of operation that a texture stage will perform.//定义对该纹理的哪个属进行设置,值很多。。。
       Value: 指的是前面所选属性的值

    type:
        D3DTSS_ALPHAOP = 4,          //alpha通道的运算,
        D3DTSS_COLOROP = 1,           //颜色的运算
                                                       //这里的op 是operations,指对前面设置的颜色进行运算
                                                       //既后面的2个type:D3DTSS_COLORARG1,D3DTSS_COLORARG2
                                                       //或D3DTSS_ALPHAARG1,D3DTSS_ALPHAARG2 = 6
    value:
        D3DTOP_DISABLE = 1,                           //该纹理无效,既不显示
        D3DTOP_SELECTARG1 = 2,                  //Arg1
        D3DTOP_SELECTARG2 = 3,                   //Arg2
        D3DTOP_MODULATE = 4,                        //Arg1 * Arg2
        D3DTOP_MODULATE2X = 5,                      //Arg1 * Arg2 * 2
        D3DTOP_MODULATE4X = 6,                      //Arg1 * Arg2 * 4
        D3DTOP_ADD = 7,                             // Arg1 + Arg2
        D3DTOP_ADDSIGNED = 8,                   //(Arg1 + Arg2 - 0.5)
        D3DTOP_ADDSIGNED2X = 9,   //(Arg1 + Arg2 - 0.5)*2
        D3DTOP_SUBTRACT = 10,   //Arg1 - Arg2
        D3DTOP_ADDSMOOTH = 11,   //Arg1 + Arg2 – Arg1 * Arg2
        D3DTOP_BLENDDIFFUSEALPHA = 12,  //将Arg1与Arg2使用Alpha值进行线性插值。这是标准的Alpha混合效果。纹理参数常数         TextureArgumentConstants同样可以设置到Value里

        D3DTOP_BLENDTEXTUREALPHA = 13,
        D3DTOP_BLENDFACTORALPHA = 14,
        D3DTOP_BLENDTEXTUREALPHAPM = 15,
        D3DTOP_BLENDCURRENTALPHA = 16,
        D3DTOP_PREMODULATE = 17,
        D3DTOP_MODULATEALPHA_ADDCOLOR = 18,
        D3DTOP_MODULATECOLOR_ADDALPHA = 19,
        D3DTOP_MODULATEINVALPHA_ADDCOLOR = 20,
        D3DTOP_MODULATEINVCOLOR_ADDALPHA = 21,
        D3DTOP_BUMPENVMAP = 22,
        D3DTOP_BUMPENVMAPLUMINANCE = 23,
        D3DTOP_DOTPRODUCT3 = 24,
        D3DTOP_MULTIPLYADD = 25,   //SRGBA = Arg1 + Arg2 * Arg3
        D3DTOP_LERP = 26,
        D3DTOP_FORCE_DWORD = 0x7fffffff,

    type:
        D3DTSS_COLORARG1 = 2, 
        D3DTSS_COLORARG2 = 3,
        D3DTSS_ALPHAARG1 = 5,
        D3DTSS_ALPHAARG2 = 6,
        D3DTSS_COLORARG0 = 26,
        D3DTSS_ALPHAARG0 = 27,
        D3DTSS_RESULTARG = 28,
    value:
         这里的TA指的是texture arguments ,
          D3DTA_CURRENT   表示上一个Stage混合的结果。Stage=0时,这个值表示的是D3DTA_DIFFUSE
          D3DTA_CONSTANT                    //给当前纹理一个固定的值;
          D3DTA_DIFFUSE;                 //diffuse的值作为参数 diffuse 可能有多个来源。。比如材质,vertex
          D3DTA_SELECTMASK         //Mask value for all arguments; not used when setting texture arguments 这句话不理解啊,为什么要伪装呢 
          D3DTA_SPECULAR             //取spercular 的值作为参数  来源同diffuse
          D3DTA_TEMP                     //待定。。
          D3DTA_TEXTURE              //用纹理的颜色值作为参数
          D3DTA_TFACTOR              //待定。。
    D3DTSS_BUMPENVMAT00 = 7,
    D3DTSS_BUMPENVMAT01 = 8,
    D3DTSS_BUMPENVMAT10 = 9,
    D3DTSS_BUMPENVMAT11 = 10,
    D3DTSS_TEXCOORDINDEX = 11,
    D3DTSS_BUMPENVLSCALE = 22,
    D3DTSS_BUMPENVLOFFSET = 23,
    D3DTSS_TEXTURETRANSFORMFLAGS = 24,
    D3DTSS_CONSTANT = 32,
    D3DTSS_FORCE_DWORD = 0x7fffffff,

    m_pD3DDevice->SetTexture( 0, m_pTexture0 ); // 土地材質
    m_pD3DDevice->SetTextureStageState( 0, D3DTSS_TEXCOORDINDEX, 0 );

    // TextureStage 0 (不做任何改變)
    m_pD3DDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1 );
    m_pD3DDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
    m_pD3DDevice->SetTextureStageState( 0, D3DTSS_ALPHAOP, D3DTOP_DISABLE );

    //------------

    m_pD3DDevice->SetTexture( 1, m_pTexture1 ); // 草地材質
    m_pD3DDevice->SetTextureStageState( 1, D3DTSS_TEXCOORDINDEX, 0 );

    // TextureStage 1 (使用頂點alpha值計算混合)
    m_pD3DDevice->SetTextureStageState( 1, D3DTSS_COLOROP, D3DTOP_BLENDDIFFUSEALPHA );
    m_pD3DDevice->SetTextureStageState( 1, D3DTSS_COLORARG1, D3DTA_TEXTURE );
    m_pD3DDevice->SetTextureStageState( 1, D3DTSS_COLORARG2, D3DTA_CURRENT );
    m_pD3DDevice->SetTextureStageState( 1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );

    //------------

    // TextureStage 2 (使用光影遮罩圖) // 光影材質
    m_pD3DDevice->SetTexture( 2, m_pTexture2 );
    m_pD3DDevice->SetTextureStageState( 2, D3DTSS_TEXCOORDINDEX, 1 );
    m_pD3DDevice->SetTextureStageState( 2, D3DTSS_COLOROP, D3DTOP_MODULATE2X );
    m_pD3DDevice->SetTextureStageState( 2, D3DTSS_COLORARG1, D3DTA_TEXTURE );
    m_pD3DDevice->SetTextureStageState( 2, D3DTSS_COLORARG2, D3DTA_CURRENT );
    m_pD3DDevice->SetTextureStageState( 2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );

    //------------

    // TextureStage 3 (使用頂點值計算陰影)
    m_pD3DDevice->SetTextureStageState( 3, D3DTSS_COLOROP, D3DTOP_MODULATE );
    m_pD3DDevice->SetTextureStageState( 3, D3DTSS_COLORARG1, D3DTA_DIFFUSE );
    m_pD3DDevice->SetTextureStageState( 3, D3DTSS_COLORARG2, D3DTA_CURRENT );
    m_pD3DDevice->SetTextureStageState( 3, D3DTSS_ALPHAOP, D3DTOP_DISABLE );

    黑暗纹理
    通过纹理映射来模拟逐像素光照效果,通常是将第一层纹理设置为物体原来的表面纹理,将第二层纹理设置为光照纹理,然后将两张纹理的颜色相乘,所以有时将两张纹理的颜色相乘称为光照映射(light mapping)。由于这种技术经常被用于使一张纹理变暗,有时也称为黑暗映射(dark mapping)。

    混合纹理与顶点漫反射颜色

    当很强的阳光照射在物体表面上时,会使它表面的颜色变得更加明亮,这可以通过将纹理与顶点的漫反射颜色相混合来模拟这种效果。当一个白色材质反射一个方向光时,反射量越多,就意味着纹理颜色在最终显示结果中所占的成分越少。因此,那些被光直接照射到表面会呈现出白色。示例代码如下:

    // setup light

    ZeroMemory(&g_light, sizeof(D3DLIGHT9));

    g_light.Type = D3DLIGHT_DIRECTIONAL;
    g_light.Diffuse.r = 0.5f;
    g_light.Diffuse.g = 0.5f;
    g_light.Diffuse.b = 0.5f;

    D3DXVECTOR3 light_dir(0, 0, 10);
    D3DXVec3Normalize((D3DXVECTOR3*) &g_light.Direction, &light_dir);

    // setup material

    ZeroMemory(&g_material, sizeof(D3DMATERIAL9));

    g_material.Ambient.r = 1.0f;
    g_material.Ambient.g = 1.0f;
    g_material.Ambient.b = 1.0f;
    g_material.Ambient.a = 1.0f;
    g_material.Diffuse.r = 0.7f;
    g_material.Diffuse.g = 0.7f;
    g_material.Diffuse.b = 0.7f;
    g_material.Diffuse.a = 0.5f;

    pd3dDevice->SetRenderState(D3DRS_LIGHTING, TRUE);
    pd3dDevice->SetRenderState(D3DRS_AMBIENT, 0x00808080);
    pd3dDevice->SetLight(0, &g_light);
    pd3dDevice->LightEnable(0, TRUE);
    pd3dDevice->SetMaterial(&g_material);

    pd3dDevice->SetTexture(0, g_base_texture);
    pd3dDevice->SetTextureStageState(0, D3DTSS_TEXCOORDINDEX, 0);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_ADD);
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);

    发光映射

    发光映射(glowing mapping)与黑暗映射正好相反,它对于模拟那些具有独立于基础贴图的发光部分的物体很有用,比如模拟发光二极管、按钮、建筑物内的灯光、太空船上的灯光等。发光映射应仅影响基础贴图上的发光区域,而不影响其他部分。因此需要对发光效果做加法,而不是做乘法。

    pd3dDevice->SetTexture(0, g_base_texture);
    pd3dDevice->SetTextureStageState(0, D3DTSS_TEXCOORDINDEX, 0);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);

    pd3dDevice->SetTexture(1, g_dark_texture);
    pd3dDevice->SetTextureStageState(1, D3DTSS_TEXCOORDINDEX, 0);
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLORARG1, D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLORARG2, D3DTA_CURRENT);
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_ADD);

    细节映射

    如果要模拟一块粗糙的石灰泥墙壁,可以通过细节映射(detail mapping)来实现。实现过程是:将基础贴图(也就是第一张纹理)的颜色未经修改便作为第二个纹理操作阶段中的第二个参数,然后通过D3DTOP_ADDSIGNED将灰色的细节纹理与基础贴图相加。这个操作本质上是做了一个加法,只是使用了有符号的颜色值来代替平时使用的无符号值。在对两张纹理的像素颜色进行D3DTOP_ADDSIGNED操作时,它将参数的每个成分相加后再减去偏移量0.5,从而使有效值域变为-0.5 ~ 0.5。对一些比较旧的显卡,当其不能支持D3DTOP_ADDSIGNED操作时,可以使用D3DTOP_MODULATE2X代替D3DTOP_ADDSIGNED操作进行模拟。

    在细节贴图中较亮的灰色纹理元素会使基础贴图变得更亮,而较暗的灰色纹理元素会使基础贴图变得更暗。由此可使物体呈现出粗糙的表面,从而使之看上去更为真实。示例代码如下:

    pd3dDevice->SetTexture(0, g_base_texture);
    pd3dDevice->SetTextureStageState(0, D3DTSS_TEXCOORDINDEX, 0);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG1,  D3DTA_TEXTURE); 
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLOROP,  D3DTOP_SELECTARG1);
    pd3dDevice->SetTexture(1, g_detail_texture);
    pd3dDevice->SetTextureStageState(1, D3DTSS_TEXCOORDINDEX, 0);
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLORARG1,  D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLORARG2,  D3DTA_CURRENT);
    hr = pd3dDevice->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_ADDSIGNED);
    if(FAILED(hr))
    pd3dDevice->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_MODULATE2X);

    ALPHA混合操作
    Direct3D在渲染一个场景时,它可以结合几种来源的颜色信息:顶点、当前材质、纹理贴图、先前写入渲染目标的颜色信息,然后将其中的一些颜色混合起来。同时也可以使用Alpha来指定Direct3D该以怎样的权重混合这些颜色,Alpha信息可以存储在顶点中、材质中、纹理贴图中。Alpha值为0表示完全透明,Alpha值为1表示不透明,其余0~1之间的值表示不同程度的透明。

    如果要从一张纹理中获取Alpha值,应将D3DTA_TEXTURE作为Alpha参数。

    如果要使用来自顶点中的Alpha值,应将D3DTA_DIFFUSE作为Alpha参数,并确保渲染状态D3DRS_DIFFUSEMATERIALSOURCE被设置为D3DMCS_COLOR1(这也是默认状态)。

    如果要使用来自材质中的Alpha值,应将D3DTA_DIFFUSE作为Alpha参数,并确保渲染状态D3DRS_DIFFUSEMATERIALSOURCE被设置为D3DMCS_MATERIAL。

    如果未用SetRenderState()设置D3DRS_DIFFUSEMATERIALSOURCE参数,则从默认来源(即顶点)获取漫反射颜色。

    pd3dDevice->SetTexture(0, g_texture);
    pd3dDevice->SetTextureStageState(0, D3DTSS_TEXCOORDINDEX, 0);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);

    pd3dDevice->SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1);

    pd3dDevice->SetRenderState(D3DRS_ALPHABLENDENABLE, TRUE);
    pd3dDevice->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
    pd3dDevice->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);

    纹理坐标自动生成

    在Direct3D程序中,不仅可以在模型载入阶段或渲染阶段指定物体的纹理坐标,还可以通过Direct3D渲染引擎自动生成纹理坐标,用于诸如环境映射等特殊的视觉效果。与手动设置纹理坐标相比,纹理坐标自动生成在Direct3D坐标变换和光照流水线中完成,执行速度更快。

    Direct3D系统可以使用经过变换的摄像机空间顶点位置坐标、法线信息来生成纹理坐标。如果使用纹理坐标自动生成,那么在顶点中就可以不用包含纹理坐标数据,从而可以降低图形渲染时的数据传输量。纹理坐标自动生成主要用于产生一些特殊效果,在大多数情况下还是手工为每个顶点指定纹理坐标。

    通过调用SetTextureStageState()并将第二个参数设置为D3DTSS_TEXCOORDINDEX来控制Direct3D系统如何自动生成纹理坐标。
    D3DTSS_TEXCOORDINDEX用于指定特定纹理层使用顶点中的第几组纹理坐标,但如果指定了上表中的成员值,Direct3D将忽略顶点中的纹理坐标,转而使用自动生成的纹理坐标。

    D3DTSS_TEXTURETRANSFORMFLAGS用来控制生成的纹理坐标的输出,在大多数情况下纹理坐标是二维的,即将D3DTSS_TEXTURETRANSFORMFLAGS设置为D3DTTFF_COUNT2。但当绘制线段或三维纹理时,纹理坐标可能是一维或三维的。

    纹理坐标变换
    Direct3D提供了对生成的纹理坐标进行坐标变换的功能,与顶点坐标变换相类似,可以指定一个4x4的纹理坐标变换矩阵,把它与生成的纹理坐标相乘,然后将变换之后的纹理坐标输出至Direct3D渲染流水线。使用纹理坐标变换可以对纹理坐标进行诸如平移、旋转和缩放等三维变换。纹理坐标变换对于生成一些特殊效果是非常有用的,它不用直接修改顶点的纹理坐标。例如可以通过一个简单的平移矩阵对纹理坐标进行变换,从而使物体表面上的纹理不断变换位置,产生动画效果。纹理坐标自动生成在三维图形程序中最广泛的应用是环境映射。

    可通过函数IDirect3DDevice9::SetTransform()来设置4x4的纹理坐标变换矩阵,它以D3DTS_TEXTURE0~ D3DTS_TEXTURE7作为第一个参数,表示设置纹理层0~7的纹理矩阵。下列代码对纹理层0设置了一个将纹理坐标u、v缩小到原来一半的纹理矩阵:

    D3DXMATRIX mat;
    D3DXMatrixIdentity(&mat);
    mat._11 = 0.5f;
    mat._22 = 0.5f;
    pd3dDevice->SetTransform(D3DTS_TEXTURE0, &mat);

    下面的代码将原来的纹理坐标平移(1.0, 1.0, 0)个单位。

    D3DXMATRIX mat;
    D3DXMatrixIdentity(&mat);
    mat._41 = 1.0f;
    mat._42 = 1.0f;
    mat._43 = 0.0f;
    pd3dDevice->SetTransform(D3DTS_TEXTURE0, &mat);

    示例程序通过下列代码对自动生成的纹理坐标进行变换:

    // texture coordinate transform

    D3DXMATRIX mat_texture, mat_scale, mat_trans;

    D3DXMatrixIdentity(&mat_texture);
    D3DXMatrixScaling(&mat_scale, 0.5f, -0.5f, 1.0f);
    D3DXMatrixTranslation(&mat_trans, 0.5f, 0.5f, 1.0f);

    mat_texture = mat_texture * mat_scale * mat_trans;
    pd3dDevice->SetTransform(D3DTS_TEXTURE0, &mat_texture);

    立方体环境映射

    立方体环境映射图有时又称为立方体映射图,是一组包含物体周围环境图像的纹理贴图,好像物体在立方体的中心。立方体环境图的每个面覆盖水平和垂直方向上各90度视角区域,一共6个面.

    球形环境映射

    球形环境映射图(或称为球形映射图)和立方体环境映射图类似,也是一幅包含周围场景图像的特殊纹理。和立方体环境映射图不同的是,球形环境映射图不直接代表物体周围的环境。球形映射图就好像通过鱼眼(fish-eye)凸透镜观察到的景象一样,是一个物体周围环境360度全方位视域的三维表现。

    首先使用一张球形的背景图作为环境映射纹理,接着在回调函数OnCreateDevice()中加载纹理和网格模型,接着在回调函数OnResetDevice()中自动生成纹理坐标,并设置纹理阶段颜色混合方法,最后在回调函数OnFrameRender()中渲染茶壶:

    V_RETURN(D3DXCreateTextureFromFile(pd3dDevice, L"spheremap.bmp", &g_env_texture));
    ID3DXBuffer* material_buffer;
    V_RETURN(D3DXLoadMeshFromXW(L"teapot.x", D3DXMESH_MANAGED, pd3dDevice, NULL, &material_buffer, NULL,        &g_num_materials, &g_mesh));
    D3DXMATERIAL* xmaterials = (D3DXMATERIAL*) material_buffer->GetBufferPointer();g_mesh_materials = new D3DMATERIAL9[g_num_materials];
    for(DWORD i = 0; i < g_num_materials; i++){ g_mesh_materials[i] = xmaterials[i].MatD3D;
    // .x file do not save ambient data, so set it here. g_mesh_materials[i].Ambient = g_mesh_materials[i].Diffuse; }
    material_buffer->Release();

    pd3dDevice->SetTexture(0, g_env_texture);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
    pd3dDevice->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_DISABLE);

    pd3dDevice->SetTextureStageState(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_SPHEREMAP);
    pd3dDevice->SetTextureStageState(0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);

    // Clear the render target and the zbuffer V( pd3dDevice->Clear(0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, D3DCOLOR_ARGB(0, 0, 0, 0), 1.0f, 0) );
    // Render the scene
    if( SUCCEEDED( pd3dDevice->BeginScene() ) )
    { for(DWORD i = 0; i < g_num_materials; i++)

      pd3dDevice->SetMaterial(&g_mesh_materials[i]); 
      g_mesh->DrawSubset(i);
    }
    RenderText();
    V(g_button_dlg.OnRender(fElapsedTime));
         V( pd3dDevice->EndScene() );
    }

    DXT纹理压缩
    要渲染看起来真实的场景,最好是使用高分辨率而且颜色丰富的纹理,但这样的纹理可能会耗费大量的内存,例如,一张每像素16位颜色的256 x 256纹理将使用128KB的内存。如果在该纹理中使用多级渐进纹理,还需要额外的43KB内存。一个使用50张这种纹理的场景将需要8MB的内存,如果需要更强的真实性,可以使用每像素32位颜色的512 x 512纹理,但那就需要8倍的内存。

    为了减少纹理消耗的系统带宽和内存空间,Direct3D支持纹理压缩和实时解压,即DXT纹理压缩。压缩后的纹理被存储在Direct3D纹理指针中,当Direct3D渲染物体时,Direct3D引擎自动对纹理进行解压。应用DXT压缩纹理不仅可以节省内存空间,而且能有效地降低纹理传输带宽,提高图形系统的整体性能。
    随着DirectX对纹理压缩格式的推广,目前大部分显卡都支持DXT压缩纹理,而且DXT压缩纹理在图形质量和运行速度之间取得了很好的平衡。

    DXT是一种DirectDraw表面,它以压缩形式存储图形数据,该表面可以节省大量的系统带宽和内存。即使不直接使用DXT表面渲染,也可以通过DXT格式创建纹理的方法节省磁盘空间。Direct3D提供了D3DFMT_DXT1 ~ D3DFMT_DXT5共5种压缩纹理格式。其中,D3DFMT_DXT1支持15位RGB和1位alpha图形格式,D3DFMT_DXT2、D3DFMT_DXT3支持12位RGB和4位alpha,D3DFMT_DXT4、D3DFMT_DXT5则采取了线性插值方式生成alpha。

    DXT1格式的压缩比例是4 : 1(4x4块16位RGB纹理元素可压缩为64位,2个16位RGB565值和16个2位索引),这样的压缩比并不很高,但足以有效地将3D加速卡用于存储纹理的容量提高4倍

  • 相关阅读:
    OSPF
    【今日CS 视觉论文速览】 24 Jan 2019
    【今日CS 视觉论文速览】Wed, 23 Jan 2019
    【今日CS 视觉论文速览】 21 Jan 2019
    【Processing学习笔记】安装与入门
    【今日CS 视觉论文速览】Part2, 18 Jan 2019
    【今日CS 视觉论文速览】Fri, 18 Jan 2019
    【今日CS 视觉论文速览】Thu, 17 Jan 2019
    【今日CS 视觉论文速览】Part2, 16 Jan 2019
    【今日CS 视觉论文速览】Wed, 16 Jan 2019
  • 原文地址:https://www.cnblogs.com/zsb517/p/3540842.html
Copyright © 2011-2022 走看看