[UMG]ディゾルブエフェクトもできる、RetainerBoxについて

RetainerBoxについて紹介します。これを使うと、例えば図1のようなUMG用ディゾルブエフェクトを作成することも可能です。
図1 UMG用ディゾルブエフェクト

RetainerBoxとは

Optimization(最適化)に分類されるウィジェットです。Retainer Boxの子ウィジェットの内容を、テクスチャ(RenderTarget)に指定間隔でオフスクリーンレンダリング(OSRと略します)し、その結果のテクスチャをスクリーンに描画するウィジェットです。OSRは毎フレーム行われるわけではなく、OSRが行われないフレームの間は最後にOSRされたテクスチャを再利用することでスクリーンへの描画負荷を減らします。
子ウィジェットの内容が複雑なものである場合、OSRの頻度が少ないほど描画パフォーマンスが向上する可能性があります。ただし、OSRの頻度を「毎フレーム」に設定したりすると、OSRされたテクスチャをスクリーンに描画する「二度手間」がある分、逆にパフォーマンスは悪化すると考えられます。今回は最適化の話に焦点を合わせませんが、使うときはパフォーマンスに留意する必要があると思われます
今回は、Retainer Boxを用いたエフェクトを主に紹介します。実は、Retainer BoxはOSRされたテクスチャをスクリーンに描画する際、マテリアルによって描画内容を変えることが可能です。これはBorderやImageウィジェットのBrushにエフェクト用マテリアルを適用するのとは異なり、Retainer Boxにエフェクト用マテリアルを適用すると、子ウィジェット全てに対してエフェクトが適用されるのと同じ表現ができます。

Retainer Boxを使ってみる

前準備として、図2のようなUser Widgetを作成します。今回は、これをRetainer Boxの子ウィジェットにして全体にエフェクトを適用します。
図2 様々なウィジェットが配置されたUser Widget(左下はレイアウト階層)

まず、図2のウィジェットをRetainer Boxでラップして、図3のようにします。余談ですが、ウィジェットをラップするときはコピー&ペーストで作るより、Wrap With...の中から親としたいパネルウィジェットを選ぶ方が簡単です。
図3 Retainer Boxでラップする

次に、Retainer BoxのEffect Materialにマテリアルを設定します。ここではCreate Materialを選んで、新しいマテリアル(アセット名はM_RetainerTestとしました)を作成しました。
図4 Effect Materialにマテリアルを設定する

次に、マテリアルを図5のように実装しました。マテリアルの内容はTextureSampleParameter2Dをそのまま繋いでいるだけです。注目したいのは、TextureSampleParameter2Dのパラメータ名を「RetainerOSR」としている点です。Retainer BoxのOSRの結果は、Texture Parameterに設定した名前(ここではRetainerOSR)と同名のTextureSampleParameter2Dに格納されます。
図5 Effect Materialを実装する

ここまで実装したら、一度User Widgetを画面に表示してみます。おそらく、図2とほとんど変わらない表示結果になると思います。
それもそのはず、図5の実装は「OSRの結果をそのままスクリーンに描画する」といった処理をしているだけなので、このままでは表示結果はRetainer Boxを使わないときと何も変わりません。
そこで、図6のようにマスクをかけてみます。
図6 OSRの結果からR成分を抜く

これを実行すると図7のようになります。Retainer Boxの子ウィジェット全てに対して、R成分が抜くエフェクトが適用されました。
図7 Retainer Boxを使用してエフェクトをかけた結果

ディゾルブエフェクトを実装する

Retainer Boxの基本的な使い方を説明したので、続いて図1のようなディゾルブエフェクトを実装してみます。
まず、図8のようなディゾルブエフェクト用のマテリアルを組みます。このマテリアルの詳細は主旨からはずれるので解説しません。
パラメータだけ説明すると、Lenはノイズがかかって消えかかる部分の長さです。Offsetがエフェクトのかかり具合で、Offset=-Lenのときエフェクトは一切かからず、Offset=1+lenのときエフェクトがかかりきって完全に透明になります。Offsetをその範囲でゆっくり変化させれば、ディゾルブエフェクトっぽくなります。
図8 ディゾルブエフェクト用マテリアル

次に、マテリアルインスタンスを作成します。図9のようしました。Offsetは、-Lenのときエフェクトがかかっていない状態なので、Lenの数値から-0.25という値を設定しています。
図9 マテリアルインスタンスの設定

このマテリアルを、図10のようなレイアウトのUser Widgetに適用します。今回は見栄えのために複雑なレイアウトをしていますが、どのようなレイアウトのウィジェットでも、Retainer Boxは期待したディゾルブエフェクトを表示することができます。
図10 ウィジェットのレイアウト


最後に、図11のようなBlueprintを作ります。ボタンが押された時に、Offsetを徐々に変更する処理を作りました。
図11 Offsetを徐々に変更していく処理

これでディゾルブエフェクトが実装できました。ダイアログのボタンをクリックしてみると、図1のようになります。

注意事項

Retainer Boxは便利なウィジェットですが、いくつか注意事項があります。
  • Background Blurのような特殊なウィジェットには対応できない
  • Angleを利用した回転はできない。詳しくはここ

おわりに

どうでしたか。Retainer Boxは最適化に分類されるウィジェットですが、工夫次第で様々な応用ができる可能性を秘めたウィジェットだと思います。素敵なUIを作りたい方は、一度使ってみるのはどうでしょうか。



この記事は次のバージョンで作成されました。
Unreal Editor(4.15.1-3348071+++UE4+Release-4.15)

コメント