共用方式為


編譯效果 (Direct3D 10)

一旦撰寫效果,第一個步驟是編譯器代碼以檢查語法問題。 這是藉由呼叫其中一個編譯 API (,例如 D3DX10CompileEffectFromFile、D3DX10CompileEffectFromResource、D3DX10CompileEffectFromMemory) 來完成。 這些 API 會叫用效果編譯器fxc.exe,這是用來編譯 HLSL 程式碼的編譯器。 這就是為什麼效果中的程式碼語法看起來非常類似 HLSL 程式碼, (稍後會處理幾個例外狀況) 。 如此一來,效果編譯器/hlsl 編譯器 (fxc.exe) 會位於公用程式資料夾中的 SDK 中,如此一來,您可以選擇離線編譯著色器 (或) 效果。 請參閱從命令列執行編譯器的檔。

以下是從 BasicHLSL10 範例) 編譯效果檔案 (的範例。

WCHAR str[MAX_PATH];
DXUTFindDXSDKMediaFileCch( str, MAX_PATH, L"BasicHLSL10.fx" );

hr = D3DX10CompileEffectFromFile( str, NULL, NULL, "fx_4_0", 
    D3D10_SHADER_ENABLE_STRICTNESS, 0, pd3dDevice, NULL, NULL, 
    &l_pBlob_Effect, &l_pBlob_Errors, NULL );

Includes

其中一個參數是 include 介面。 如果您想要在讀取 Include 檔案時包含自訂行為,請產生其中一個。 每次建立使用 include 指標) 的效果 (,或編譯使用 include 指標) 的效果 (時,就會執行這個自訂行為。 若要實作自訂的 Include 行為,請從 Include 介面衍生類別。 這提供您的類別兩種方法:Open 和 Close。 在 Open 和 Close 方法中實作自訂行為。

巨集

效果編譯也可以取得其他位置所定義的宏指標。 例如,假設您在 BasicHLSL10 中修改效果,以使用兩個宏:零和一個。 此處顯示使用兩個宏的效果程式碼。

if( bAnimate )
    vAnimatedPos += float4(vNormal, zero) *  
        (sin(g_fTime+5.5)+0.5)*5;
        
    Output.Diffuse.a = one;         

以下是兩個宏的宣告。

D3D_SHADER_MACRO Shader_Macros[3] = { "zero", "0", "one", "1.0f", NULL, NULL };

宏是以 Null 終止的宏陣列;其中每個宏都是使用 D3D_SHADER_MACRO 結構來定義。

最後,修改編譯效果呼叫以取得宏的指標。

D3DX10CreateEffectFromFile( str, Shader_Macros, NULL, 
    D3D10_SHADER_ENABLE_STRICTNESS, 0, pd3dDevice, NULL, NULL, 
    &g_pEffect10, NULL );

HLSL 著色器旗標

著色器旗標會指定 HLSL 編譯器的著色器條件約束。 這些旗標會影響著色器編譯器所產生的程式碼,包括:

  • 大小考慮:將程式碼優化。
  • 偵錯考慮:包括偵錯資訊、防止流量控制。
  • 硬體考慮:編譯目標,以及著色器是否可以在舊版硬體上執行。

一般而言,這些旗標可以邏輯方式結合,假設您未指定兩個衝突的特性。 如需旗標的清單,請參閱 效果常數 (Direct3D 10)

FX 旗標

這些旗標會在建立效果時用來定義編譯行為或執行時間效果行為。 如需旗標的清單,請參閱 效果常數 (Direct3D 10)

檢查錯誤

如果在編譯期間發生錯誤,API 會傳回介面,其中包含從效果編譯器傳回的錯誤。 此介面稱為 ID3D10Blob。 不過,它無法直接讀取,只要傳回包含資料 (的緩衝區指標,即字串) ,即可看到任何編譯錯誤。

在此範例中,藉由複製第一個變數宣告兩次,將錯誤引入 BasicHLSL.fx 效果。

//-------------------------------------------------------------------
// Global variables
//-------------------------------------------------------------------
float4 g_MaterialAmbientColor;      // Material's ambient color

// Declare the same variable twice
float4 g_MaterialAmbientColor;      // Material's ambient color

此錯誤導致編譯器傳回下列錯誤,如 Microsoft Visual Studio 中watch視窗的下列螢幕擷取畫面所示。

visual Studio watch視窗的螢幕擷取畫面

因為錯誤會在 LPVOID 指標中傳回,所以將它轉換成watch視窗中的字元字串。

以下是用來從失敗編譯傳回錯誤的程式碼。

// Read the D3DX effect file
WCHAR str[MAX_PATH];
ID3D10Blob* l_pBlob_Effect = NULL;
ID3D10Blob* l_pBlob_Errors = NULL;
hr = DXUTFindDXSDKMediaFileCch( str, MAX_PATH, L"BasicHLSL10.fx" );
hr = D3DX10CompileEffectFromFile( str, NULL, NULL, 
    D3D10_SHADER_ENABLE_STRICTNESS, 0, NULL, 
    &l_pBlob_Effect, &l_pBlob_Errors );

LPVOID l_pError = NULL;
if( l_pBlob_Errors )
{
    l_pError = l_pBlob_Errors->GetBufferPointer();
    // then cast to a char* to see it in the locals window
}

轉譯效果 (Direct3D 10)