オフライン コンパイル

エフェクト コンパイラ ツール (fxc.exe) は、HLSL シェーダーのオフライン コンパイル用に設計されています。

現在のコンパイラを使用したコンパイル

現在のコンパイラでサポートされているシェーダー モデルは、「 プロファイル」に示されています。 次の使用例は、シェーダー モデル 5.1 ターゲットのピクセル シェーダーをコンパイルします。

fxc /T ps_5_1 /Fo PixelShader1.fxc PixelShader1.hlsl

この例では、次のように記述されています。

  • ps_5_1はターゲット プロファイルです。
  • PixelShader1.fxc は、コンパイルされたシェーダーを含む出力オブジェクト ファイルです。
  • PixelShader1.hlsl がソースです。
fxc /Od /Zi /T ps_5_1 /Fo PixelShader1.fxc PixelShader1.hlsl

デバッグ オプションには、コンパイラの最適化 (Od) を無効にし、行番号やシンボルなどのデバッグ情報 (Zi) を有効にする追加のオプションが含まれています。

コマンド ライン オプションの完全な一覧については、 構文 に関するページを参照してください。

レガシ コンパイラを使用したコンパイル

Direct3D 10 以降では、一部のシェーダー モデルはサポートされなくなりました。 これには、非常に限られたリソースをサポートし、ハードウェアに依存するps_1_1、ps_1_2、ps_1_3、ps_1_4ピクセル シェーダー モデルが含まれます。 コンパイラはシェーダー モデル 2 (またはそれ以上) で再設計されました。これにより、コンパイルの効率が向上します。 もちろん、これはシェーダー モデル 2 以降をサポートするハードウェアで実行している必要があります。

また、/Gec スイッチの影響を受ける動作については、FXC コンパイラのバージョンに関連付けられている SDK リリース ノートを参照してください。

サブプロセスでのエフェクト コンパイラ ツールの使用

fxc.exeがアプリケーションによってサブプロセスとして生成される場合は、CreateProcess 関数に渡される出力パイプまたはエラー パイプ内のデータをアプリケーションがチェックして読み取るようにすることが重要です。 アプリケーションがサブプロセスの完了を待機し、パイプの 1 つが満杯になった場合、サブプロセスは完了しません。

次のコード例は、サブプロセスで待機し、サブプロセスに接続されている出力パイプとエラー パイプを読み取る方法を示しています。 配列の WaitHandles 内容は、サブプロセスのハンドル、stdout のパイプ、stderr のパイプに対応します。

HANDLE WaitHandles[] = {
  piProcInfo.hProcess, hReadOutPipe, hReadErrorPipe
};

const DWORD BUFSIZE = 4096;
BYTE buff[BUFSIZE];

while (1)
{
    DWORD dwBytesRead, dwBytesAvailable;

    dwWaitResult = WaitForMultipleObjects(3, WaitHandles, FALSE, 60000L);

    // Read from the pipes...
    while (PeekNamedPipe(hReadOutPipe, NULL, 0, NULL, &dwBytesAvailable, NULL) && dwBytesAvailable)
    {
        ReadFile(hReadOutPipe, buff, BUFSIZE - 1, &dwBytesRead, 0);
        streamOut << std::string((char*)buff, (size_t)dwBytesRead);
    }
    while (PeekNamedPipe(hReadErrorPipe, NULL, 0, NULL, &dwBytesAvailable, NULL) && dwBytesAvailable)
    {
        ReadFile(hReadErrorPipe, buff, BUFSIZE - 1, &dwBytesRead, 0);
        streamError << std::string((char*)buff, (size_t)dwBytesRead);
    }

    // Process is done, or we timed out:
    if (dwWaitResult == WAIT_OBJECT_0 || dwWaitResult == WAIT_TIMEOUT)
        break;
}

プロセスの生成の詳細については、 CreateProcess のリファレンス ページを参照してください。