接下来进入第二部分,Bloom,SDK里称为post-processing effect。代码所在文件为PostProcess.cpp。
LPDIRECT3DTEXTURE9 g_pBrightPassTex = NULL; // The results of performing a bright pass on the original HDR imagery
LPDIRECT3DTEXTURE9 g_pDownSampledTex = NULL; // The scaled down version of the bright pass results
LPDIRECT3DTEXTURE9 g_pBloomHorizontal = NULL; // The horizontally blurred version of the downsampled texture
LPDIRECT3DTEXTURE9 g_pBloomVertical = NULL; // The vertically blurred version of the horizontal blur
D3DFORMAT g_fmtHDR = D3DFMT_UNKNOWN; // What HDR (128 or 64) format is being used
LPDIRECT3DPIXELSHADER9 g_pBrightPassPS = NULL; // Represents the bright pass processing
LPD3DXCONSTANTTABLE g_pBrightPassConstants = NULL;
LPDIRECT3DPIXELSHADER9 g_pDownSamplePS = NULL; // Represents the downsampling processing
LPD3DXCONSTANTTABLE g_pDownSampleConstants = NULL;
LPDIRECT3DPIXELSHADER9 g_pHBloomPS = NULL; // Performs the first stage of the bloom rendering
LPD3DXCONSTANTTABLE g_pHBloomConstants = NULL;
LPDIRECT3DPIXELSHADER9 g_pVBloomPS = NULL; // Performs the second stage of the bloom rendering
LPD3DXCONSTANTTABLE g_pVBloomConstants = NULL;
从这些变量我们可以得知:一共需要4个纹理,对应4个像素着色器。
CreateResource就不说了,无非是创建纹理和载入着色器。
//--------------------------------------------------------------------------------------
// PerformPostProcessing( )
//
// DESC:
// This is the core function for this module - it takes the raw HDR image
// generated by the 'HDRScene' component and puts it through 4 post
// processing stages - to end up with a bloom effect on the over-exposed
// (HDR) parts of the image.
LPDIRECT3DTEXTURE9 pHDRSource = NULL;
HDRScene::GetOutputTexture( &pHDRSource );
LPDIRECT3DSURFACE9 pBrightPassSurf = NULL;
PostProcess::g_pBrightPassTex->GetSurfaceLevel( 0, &pBrightPassSurf );
pDevice->SetRenderTarget( 0, pBrightPassSurf ); // Configure the output of this stage
pDevice->SetTexture( 0, pHDRSource ); // Configure the input..
pDevice->SetPixelShader( PostProcess::g_pBrightPassPS );
PostProcess::g_pBrightPassConstants->SetFloat( pDevice, "fBrightPassThreshold", PostProcess::g_BrightThreshold );
// We need to compute the sampling offsets used for this pass.
// A 2x2 sampling pattern is used, so we need to generate 4 offsets
D3DXVECTOR4 offsets[4];
// Find the dimensions for the source data
D3DSURFACE_DESC srcDesc;
pHDRSource->GetLevelDesc( 0, &srcDesc );
// Because the source and destination are NOT the same sizes, we
// need to provide offsets to correctly map between them.
float sU = ( 1.0f / static_cast< float >( srcDesc.Width ) );
float sV = ( 1.0f / static_cast< float >( srcDesc.Height ) );
// The last two components (z,w) are unused. This makes for simpler code, but if
// constant-storage is limited then it is possible to pack 4 offsets into 2 float4's
offsets[0] = D3DXVECTOR4( -0.5f * sU, 0.5f * sV, 0.0f, 0.0f );
//省略其他offset
PostProcess::g_pBrightPassConstants->SetVectorArray( pDevice, "tcDownSampleOffsets", offsets, 4 );
RenderToTexture( pDevice );
流程都是一样的,计算所需要的变量,然后设置变量,渲染到RenderTarget。
接下来的DownSampling就不说了。然后就到了Blur,这个例子中先进行水平模糊,再进行垂直模糊。计算模糊值中用到了高斯分布函数。
那么下一节将进行最后效果合成代码的阅读。