2016-11-24 18 views
3

私はDirect2Dでビットマップを描画しています。ビットマップは透明度(アルファチャンネル)を使用します。Direct2D - ビットマップでガンマ補正透過(アルファ)を​​行う方法

ブレンドは正しくありません。

テストとして、50%透明度の純粋な黒色のpngイメージを読み込み、白い背景の上に描きました。結果は、赤、緑、青の値が127(0x7F7F7F)のピクセルです。これは、Direct2Dのブレンドがガンマを無視し、カラー値を線形であるかのように扱うことを示唆しています。

(ビットマップでは、通常のsRGBカラースペースが使用され、32ビット/ピクセル、赤、緑、青、アルファの各ビットが8ビットです)。それらはGUID_WICPixelFormat32bppPBGRA形式で読み込まれます。

sRGBでは、黒と白の中間のブレンドは186(0xBABABA)です。これは私が望む理想的な結果です。

Direct2Dは、ガンマに関して透明性を表示できますか?どうすればいい?どんな助けもありがたい。

Direct2D vs Gamma-correct blend

+0

私はあなたがそれを後方に持っていると思います。 sRGBでは、50%が黒と白の中間(明るさで、ちょっと)のように見えます。それはあまりにも明るく見えますか暗すぎますか?これは、表示されている方法による可能性があります。 –

+0

私の理解では、sRGB colorspaceはピクセルの強度と格納されている実際の数との間の非線形変換を定義します。すなわちガンマカーブである。 たとえば、8ビットのカラー値の範囲は0〜255ですが、ガンマカーブのため、輝度の約20%で127(途中)の値が表示されます。 したがって、ガンマ補正の50%黒と白のブレンドのピクセル値は186(フルスケールの73%)になります。だからDirect2dでは、私のブレンドは暗すぎます。 –

+0

@astraycat黒と白のピクセルを交互に見て、それらをソリッドブロックと比較すると、BABABAブロックは適切に較正されたモニター上で同じ明るさになるはずです。較正されていないモニタでも、BABABAは7F7F7Fよりも近くにある必要があります。 –

答えて

1

ブレンドは、適切に線形色空間で行われるので、sRGBの画素をブレンドする処理が

  1. 変換が
  2. ブレンド
  3. がsRGBに戻す変換線形するなければなりません。

黒または白のピクセルでは、ステップ(1)および(3)はno-opsであり省略することができます。

PNG仕様のalpha channel processingセクションを参照してください。具体的には、この点に注意してください。

複合サンプル値を計算するための式は、アルファ値及び入力及び出力サンプル値である

output = alpha * foreground + (1-alpha) * background

ある 範囲0で画分として発現1にこの計算は セクションに含まれる輝度サンプル(不ガンマエンコードサンプル)

で行われるべきですアルファチャネル処理のサンプルCコード

この質問が提起された時点で、HWNDレンダリングターゲット(画面への描画)は線形ピクセル形式をサポートしていませんでした。しかし、Direct-2D HwndRenderターゲットは、インタフェースID2D1DeviceContextに取って代わられました。これらはIDXGIFactory2::CreateSwapChainForHwnd()で作成され、ブレンド時に自動的に正しい色空間変換を実行するDXGI_FORMAT_B8G8R8A8_UNORM_SRGBなどのピクセルフォーマットをサポートしています(@Jeff McClintockが提供する情報)。

+0

乾杯、それは理にかなっています(線形色空間でブレンドを実行する)が、これをDirect2Dでどう実装するのですか? (おそらく、レンダーターゲットとビットマップを特定のピクセル形式に設定する必要があります)。 –

+1

私はいくつかの研究をしました。 AFAIK Direct2D HWNDレンダーターゲット(画面への描画)は線形ピクセル形式をサポートしていないため、ビットマップを線形形式に変換するとハードウェアアクセラレーション(Direct2Dの主な利点)をサポートしません。 DIrect3D(Direct2Dがベース)は、ビットマップ上の操作をサポートします。これにより、ピクセルは線形の色空間に変換され、ブレンド操作中に戻されます。 Pity Direct2Dはこれをサポートしていません。 –

+0

更新:直接2D HwndRenderターゲットは、インタフェース\t \t ID2D1DeviceContextによって置き換えられました。これらはIDXGIFactory2 :: CreateSwapChainForHwnd()によって作成され、ブレンド時に自動的に正しい色空間変換を実行するDXGI_FORMAT_B8G8R8A8_UNORM_SRGBなどのより多くのピクセル形式をサポートします。 –

0

Direct-2D 1.0 HwndRenderTargetは、ピクセル値に対して直接ブレンディング計算を実行します。これにより、アルファチャンネルを利用した標準的なsRGB画像が合成されます。このエラーは、Direct 2Dが線形強度値のようにガンマ圧縮強度値を扱っているためです。

ガンマを無視すると、低品質の合成、ジオメトリのアンチエイリアシング、画像のサイズ変更、テキストレンダリングが行われます。

ブレンド計算によって導入されたエラーを補正するために、ビットマップのアルファ値を「プレワープ(pre-warp)」する回避策があります。

例: 左のイメージは、線形の色空間でブレンドを実行して正しい合成を行います。中央のイメージはDirect 2D(影が濃くコントラスト)で、アルファチャネルをあらかじめワーピングした後、右のイメージがDirect2Dです。

Direct 2D Renders alpha blends to dark and 'contrasty'

参照:https://bel.fi/alankila/lcd/alpcor.html

UPDATE !:直接2Dの新しいバージョン(1.1)を正しくブレンディングを実行SRGBバックバッファをサポートします。改善された色深度オプションを使用するには、IDXGIFactory2 :: CreateSwapChainForHwnd()を使用します。

関連する問題