1 | Real-Time Glow & Bloom

https://software.intel.com/content/www/us/en/develop/articles/compute-shader-hdr-and-bloom.html

## 前書き
先々週、画像ぼかし処理のアルゴリズムの効率を探りながら、コアアイデアを深く理解しました。これらのアイデアは多くの後処理効果に適用します。

- [Gaussian Blur](https://qiita.com/UWATechnology/items/9a92f3c1430d5fb5f280)
- [Box Blur](https://qiita.com/UWATechnology/items/c63032f0770bdaff2e24)
- [Kawase Blur](https://qiita.com/UWATechnology/items/4a7b6c72335a902103ba)
- [Dual Blur](https://qiita.com/UWATechnology/items/8b0eff5650d2c659c019)

それでは、いくつかの一般的な画面後処理効果を実装する方法を学びましょう。

## 基礎知識
Bloom（Glow）特殊効果は、ゲームでよく使われる画面の後処理特殊効果の一つで、ハイライトオブジェクトに投光照明（floodlight）効果を与え、光影の表現力を向上させる機能を持ちます。Bloomは通常、より良い結果を得るためにHDRおよびToneMappingとペアになっています。

 

まず、HDRとToneMappingとは何かを理解する必要があります。電子機器は表示範囲が限られているため、RGBの3つのチャネルにとって、各チャネルは8ビットで、合計(2^8)^3=16777216種類の色を表示することができます。この範囲は低ダイナミックレンジ（Low-Dynamic Range）と呼ばれます。この範囲は経験的な輝度の範囲であり、人間の目に害を及ぼすことはありません。それに対して、この範囲を超える色空間は、ハイダイナミックレンジ（High-Dynamic Range）と呼ばれます。実生活での輝度には範囲制限はありません。より多くの輝度を表現するには、RGBの各チャンネルを12ビット以上に拡張します。演算が完了したら、出力時にToneMapping（トーンマッピング）を介してHDR空間の色彩情報をLDR空間に変換して、モニターに表示させる必要があります。実生活で起こったBloomは人間の水晶体の散乱に由来します。例えば、明るい光を浴びるとき、見えにくくなります。従って、Bloomでハイライトブルームの効果を表すことでこの現象をシミュレートします。

 

HDR、LDR、およびToneMappingの詳細については、「HDRと色彩管理」シリーズ（以下のリンク）を参照してください。

- [光、色、色度図](https://qiita.com/UWATechnology/items/6152dd166ff5dd2474eb)
- [色空間](https://qiita.com/UWATechnology/items/852a7c87620a36d5a8c7)
- [SDRとHDR](https://qiita.com/UWATechnology/items/ab42149a9d6438b36043)
- [HDR標準とACES](https://qiita.com/UWATechnology/items/2a40dbc66bf48041d405)
- [ゲームにおけるHDR](https://qiita.com/UWATechnology/items/3e661ccd85b661ae5042)

一般的なBloom効果は、畳み込みによって画像のハイライトされた部分をぼかし、元の画像に重ね合わせることによって作成されます。「画面後処理効果シリーズの画像ぼけアルゴリズム」（以下のリンク）では、さまざまな画像ぼかしアルゴリズムを紹介し、最も効率的なDual Blur方法を使用してぼかし処理を行うことにしました。

- [Gaussian Blur](https://qiita.com/UWATechnology/items/9a92f3c1430d5fb5f280)
- [Box Blur](https://qiita.com/UWATechnology/items/c63032f0770bdaff2e24)
- [Kawase Blur](https://qiita.com/UWATechnology/items/4a7b6c72335a902103ba)
- [Dual Blur](https://qiita.com/UWATechnology/items/8b0eff5650d2c659c019)

## Unityの実装：
まず、しきい値を設定し、画像をサンプリングします。しきい値を超える画像内のピクセルがハイライトされた部分として決定します。ハイライトされた部分は色を保持し、残りは0に戻し、RTに保存します。
```
BloomMaterial.SetFloat("_Threhold", threshold);
BloomMaterial.SetFloat("_Intensity", intensity);
RenderTexture HighLighrRT=RenderTexture.GetTemporary(src.descriptor);
Graphics.Blit(src, HighLighrRT, BloomMaterial, 0);
```
 
```
Boom.shader：
Pass
{
	CGPROGRAM

	#pragma vertex vert_img
	#pragma fragment frag

	fixed4 frag(v2f_img input) : SV_Target
	{
		float4 color = tex2D(_MainTex, input.uv);
		return max(color - _Threhold, 0) * _Intensity;
	}

	ENDCG
}
```
次に、ハイライトされた部分をぼかして、元の画像に重ね合わせます。
```
Pass
{
	CGPROGRAM

	#pragma vertex vert_img
	#pragma fragment frag
	sampler2D _CompositeTex;
	float4    _CompositeColor;
	fixed4 frag(v2f_img input) : SV_Target
	{
		float4 mainColor = tex2D(_MainTex,input.uv);
		float4 compositeColor = tex2D(_CompositeTex, input.uv);
		return saturate(mainColor + compositeColor);
	}
	ENDCG
}
```
効果は図のようになります。
![image1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653855/574672f3-d7e6-3417-728f-1e166bb4b1fc.png)



元の画像は次のとおりです。
![image2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653855/086e954d-4b60-6727-3901-c8c4c34d2704.png)



同様に、「ライトセーバー」効果の実現を模倣します。
![image3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653855/a85a98cf-24cc-8ae6-4f84-79122f3e8213.png)



## まとめ
Bloom効果は、ゲームで使用される最も一般的な画面後処理効果だと言え、実装も簡単です。これからは、ぼかし処理で自然に滑らかに色をぼかし、色を重ねることで輝度を向上させることができるようになります。

 

ブルーム効果のパフォーマンスに影響を与える最大の要因は、ぼかし処理を行うコストです。Dual Blurアルゴリズムを選んで処理することをお勧めします。

---
UWA Technologyは、モバイル/VRなど様々なゲーム開発者向け、**パフォーマンス分析**と**最適化ソリューション**及び**コンサルティングサービス**を提供している会社でございます。

今なら、UWA GOTローカルツールが**15日間に無償試用**できます！！
よければ、ぜひ！

UWA公式サイト：https://jp.uwa4d.com
UWA GOT OnlineレポートDemo：https://jp.uwa4d.com/u/got/demo.html
UWA公式ブログ：https://blog.jp.uwa4d.com