2023年8月26日土曜日

Depth Of Field 2 (被写界深度)

以前被写界深度についてやったとき、結果がいまいちだったので再度チャレンジ。

このサイトを見つけて単純な仕組みっぽいので簡単にできそう。


準備


・出来上がりの絵にブラーを掛けて、全体をぼかした画像を用意する。
・描画位置の座標を利用するため、深度バッファを用意する。


描画


・UVから、描画位置の位置を算出する。
・元絵の色とぼかした絵の色を用意する。
・フォーカス位置からの距離によって、元絵とぼかした絵の使う割合を変える。


シェーダ

	float Depth = TexDepth.Sample( BorderSampler, In.UV ).r ;
	float3 Pos = DepthToPos( Depth, In.UV, Cam.InversePV ).xyz ;

	float4 Col  = Src.Sample( Sampler, In.UV ) ;
	float4 BCol = Blur.Sample( Sampler, In.UV ) ;

	float blur = smoothstep( Param.MinDistance, Param.MaxDistance, length( Pos - Param.FocusPos )) ;
	Out.Col = lerp( Col, BCol, blur ) ;

FocusPos

焦点を合わせる位置

MinDistance

焦点を合わせる範囲

MaxDistance

焦点が完全に合わなくなる範囲

MinDistanceとMaxDistanceを同じにすると、ある部分から焦点があっている部分と合わない部分がくっきり分かれる。


結果



前回の結果とは雲泥の差になった。

以前実装したときはミップマップの仕組みすらない状態だった。
現状はミップマップぼかす仕組みがあり、それを呼び出すだけで今のシーンのぼかした画像が手に入るため、2つのテクスチャのブレンドをシェーダで書けば完成する。

昔の自分にこの手順を伝えてもすぐには作れないだろうから、手を出すタイミングも重要だな。


0 件のコメント:

コメントを投稿