9.3K Views
January 08, 26
スライド概要
Unreal Engine Meetup Connect - Vol.5の講演における公開資料です。
Unreal Engine 5で制作するUIのワークフローと最適化にあたっての注意点をまとめています。
UE4で作成するUIと最適化手法 は以下のリンクをご参照ください。
https://www.docswell.com/s/EpicGamesJapan/KLG385-UE4_GCC20_UI_Optimize
Unreal Engineを開発・提供しているエピック ゲームズ ジャパンによる公式アカウントです。 勉強会や配信などで行った講演資料を公開しています。 公式サイトはこちら https://www.unrealengine.com/ja/
UE5で作成するUIと最適化手法 Epic Games Japan Lead Software Engineer, Developer Relations 鍬農 健二郎
5年前にUE4版の講演を行いました https://www.docswell.com/s/EpicGamesJapan/KLG385UE4_GCC20_UI_Optimize
● UE5の新機能紹介 新しく追加されたUI関連の機能を知る Agenda ● UE5のUI構築 UIの設計と実装の作法を知る ● UE5のUI最適化 パフォーマンスに原理と対策を知る
UE5の新機能紹介
UE5のUI新機能 UMG Preview Slate PostBuffer 簡易UIプレビュー機能 UI用ポストプロセス UI Component SlateIM UIコンポーネントフレームワーク デバッグ用UI作成機能 CommonUI UMG ViewModel 新しいUIフレームワーク UI分離フレームワーク
UMG Preview UE5.55.7 Experimental ● PIEを実行せずにボタンのアニメーション やレイアウトを即座に確認できる機能 ○ イテレーションが良くなる ○ ● アンカーやレイアウト崩れの早期発見 UMG編集 PIE再生 Preview 使用方法 ○ ○ コンソールコマンド UMG.EnablePreviewMode 1 Widget Preview アセットを作成 UI確認 UMG実装によるUI確認サイクル
UMG Preview の機能
UMG Preview 操作 ② Preview] 選択 ① コンソールコマンド入力
Slate PostBuffer UE5.45.7 Experimental ● UI用として利用可能なSlateの ポストプロセスバッファ機能 ○ シーンの画像をUIマテリアル から参照しUI上でブラー効果 などを適用 ○ GPUパフォーマンスに影響が あるので、適用範囲と同時に 利用する数を制限すること 公式ドキュメント: https://dev.epicgames.com/documentation/ja-jp/unreal-engine/using-slate-postbuffers-in-unreal-engine
Slate Postbufferの適用イメージ
UI Component UE5.55.7 Experimental ● Widget 階層を変更せずに機能を追加 するための仕組み ○ ○ ○ 既存 Widget に機能を付与したい メモリの観点でも Widget よりも軽量 Actor に対する Actor Component ■ 複数 Component の追加も可能
UI Component の特徴 例)Size Box Component Widgetを指定サイズに固定 Component を追加して機能を追加 Widgetに追加したComponentのプロパティが表示 例)Navigation UIComponent UIカーソル移動に伴うナビゲーションを処理
UI Componentを使うと実際にはSlateが追加される シンプルなボタン(Button)ウィジェットに SizeBoxComponent を追加する/追加しない 時のWidgetTreeの違いを見てみる SizeBoxComponentを追加しない(左)に対 して、追加した方(右)は SBox が作成され ていることが分かる つまり、UIComponentをアタッチしたケー スにおいても階層は考慮する必要がある
SlateIM UE5.65.7 Experimental ● 即時モード(Immediate Mode:IM)でUIを作 成するフレームワーク ○ ○ ● Immediate Mode:UIを毎フレーム描画更新 ■ 滑らかに描画をすることが可能 Retained Mode:毎フレーム描画更新しない ■ UMGはこちら、キャッシュ利用により高速 デバッグ・開発ツールの作成の目的で利用 ○ ○ imgui の代替的の位置づけ エディタ/ランタイムで利用可能
SlateIMのランタイム動作 コンソールコマンドからSlateIMのデバッグメニューを表示
SlateIMのシンプルなサンプル
GameDebugWindow.cpp
#include "SlateIM.h"
GameDebugWindow.h
#include "SlateIMWidgetBase.h"
class FGameDebugWindow : public FSlateIMWidgetBase
{
using Super = FSlateIMWidgetBase ;
private :
FGameDebugWindow () : Super(TEXT("DebugMenu" )) {}
virtual void DrawWidget (float DeltaTime)
override;
public :
static FGameDebugWindow StaticWindow;
};
Project.Build.cs
PrivateDependencyModuleNames. AddRange (new string [] {
"Slate" ,
"SlateCore" ,
"SlateIM"
});
static FAutoConsoleCommandWithWorldAndArgs CToggleDebugMenu(
TEXT("ToggleDebugMenu" ),
TEXT("Toggles debug menu." ),
FConsoleCommandWithWorldAndArgsDelegate ::CreateLambda([]( const
TArray <FString >& Params, UWorld * World)
FGameDebugWindow ::StaticWindow. IsWidgetEnabled () ?
FGameDebugWindow ::StaticWindow. DisableWidget () :
FGameDebugWindow ::StaticWindow. EnableWidget ();
}),
ECVF_Cheat );
FGameDebugWindow FGameDebugWindow ::StaticWindow;
void FGameDebugWindow ::DrawWidget (float DeltaTime)
{
if (!SlateIM:: BeginWindowRoot (GetWidgetName(), TEXT("Debug
Menu"), FVector2f (200.0f , 400.0f )))
{
SlateIM:: EndRoot ();
DisableWidget();
return;
}
// テキスト表示
SlateIM:: Text(TEXT("Hello, SlateIM!" ));
// ボタン
if (SlateIM:: Button (TEXT("クリック ")))
{
UE_LOG(LogTemp, Log, TEXT("ボタンがクリックされました "));
}
// 必ず終了する
SlateIM:: EndRoot ();
}
SlateIMのサンプル例 SlateIM.ToggleSlateStyleBrowser: エンジンの既存のスタイルを表示 SlateIM.ToggleTestSuiteWindow: サンプルウィンドウを表示
CommonUI UE4.27UE5.2 Experimental, UE5.35.7 Beta ● ● 共通UIフレームワーク ○ 右図のようなウィジェットが追加された ○ 入力方法を問わず一貫したUI動作を実現 ○ UE5以降はCommonUIの利用を推奨 主な機能 ○ 効率的なUIレイヤー管理 ○ UIナビゲーション制御 ○ 入力デバイスアイコンの自動切替 ○ 共通スタイル適用 Button Text Border Common Button Common Text Common Border 公式ドキュメント: https://dev.epicgames.com/documentation/ja-jp/unreal-engine/common-ui-plugin-for-advanced-user-interfaces-in-unreal-engine
CommonUI フレームワークが提供する機能 UIレイヤー: 入力受付可能なレイヤーを管理 UIナビゲーション: レイヤー毎の自動制御
CommonUI フレームワークが提供する機能 キー設定 プラットフォームに応じたボタン設定 スタイル適用 共通のテキストなどのプリセット
UMG ViewModel UE5.15.7 Beta ● ウィジェットとデータを分離してUIを構築する ことができる新しいシステム ○ ○ ○ ● 作業の競合を避ける パフォーマンスの改善 UIの変更に強くなる MVVMなし MVVMあり ウィジェット ウィジェット Model-View-ViewModelアーキテクチャ ○ データ オブジェクト 設計パターンの1つ ■ View:ウィジェット ■ ViewModel:データオブジェクト ■ Model:データ データ 公式ドキュメント: https://dev.epicgames.com/documentation/ja-jp/unreal-engine/umg-viewmodel-for-unreal-engine データ
HPゲージの例(従来のフロー:MVVMを使用しない) M odel V iew データ 見た目 更新時に 通知 Tickで 見に行く 密結合 Direct call/binding
HPゲージの例(新しいフロー: MVVMを使用) M odel V iewM odel View データ データオブジェクト 見た目 自動更新 更新 Binding Layer Subsystem Field Notify Property Bind 登録 役割分離 & 自動更 新
HPゲージの例(View Modelについて) V iewM odel ● UIが必要とする “表示用の値をUIに都合のいい形で 提供する” もの ● 機能やカテゴリ毎に ViewModel を作成する ○ Widget 毎には作成しない ● 作業の競合は減るが ViewModel 作成が大変では? ○ 表示とデータの分離が不要なら作成不要 ○ 長期的に見ると大規模プロジェクトでは有利 データオブジェクト Binding Layer Subsystem Field Notify Property Bind
MVVM 利用時のUMG
MVVM 利用時のUMG(Viewmodels) データロジック(ViewModels)を設定 → ”このViewModelsに紐づける” の意
MVVM 利用時のUMG(View Bindings) Bindings(データの変更を反映するトリガー)を登録 → ViewModels の GetCurrentHPRate() 関数を介して ProgressBar の Percent に 反映
UE5のUI構築
UI構築のワークフロー UIデザイン UIデザイン Widget作成 Widget作成 画面遷移 画面遷移 データ連携 データ連携 最適化
スタイル作成 Common UI によるスタイル設定 ● Common UIを利用することで見た目を スタイル(プリセット)で設定 ○ ○ ● スタイルを複数ウィジェットで共有 CommonButton や CommonTextは必 ずスタイルを設定 グローバルスタイル(テーマ)の適用 ○ ○ プロジェクト設定で ”テンプレートス タイル” を設定が可能 デフォルトのスタイルを設定すること で、Widget に自動でスタイルを適用
テクスチャ設定 ● MipGenSettings は基本 NoMipmaps ● ● TextureGroup は UI NeverStream は 基本 有効 ○ ● CompressionSettings は 用途次第 ○ ● “UI” または “NeverStream有効“の場合 テクスチャストリーミング無効 基本は Default, 品質が必要な場合は BC7, 特殊用途は RGBA8 TextureSize は 2048x2048 以下目標 ○ ○ アイコンなどは 2のべき乗サイズ 等倍で表示するものはそのまま
マテリアル設定 ● UIアニメーションなどに利用 ● Material Domain は “User Interface” ● Blend Mode は 基本 “Translucent” ● Used With Static Mesh は オフ ● 複数パラメータの変更には MPC 利用 ○ 少なければ通常のパラメータ利用
フォント設定 ● Font Asset と Font Face の構成 ○ ○ ● Font Asset(Composit Font/Offline)と Font Face (TTF/OTF)に分離 Composite Font はランタイム生成、多言語対応 (Sub-Font Family)が可能 距離フィールドフォント(SDF/MSDF) ○ ○ ○ 拡大縮小しても輪郭が滑らかで高品質 UE5.5からはMSDFサポート 大文字やエフェクト(アウトライン、グロー)
Widget 作成のクラス設計 UserWidget CommonActivatableWidget 通常のウィジェット 高度な入力制御が不要な場合 CommonUIの基本ウィジェット 高度な入力制御が必要な場合 メリット ● シンプルで柔軟 ● 学習コスト低 メリット ● 全操作でも同じ操作感を実現 ● フォーカス移動管理が容易 デメリット ● 複雑な入力/フォーカスは自前実装 デメリット ● 学習コスト 利用ケース ● シンプルな表示用Widget ● HUD要素 ● 再利用可能なUIコンポーネント 利用ケース ● フルスクリーンUI / メイン画面 ● モーダルダイアログ / ポップアップ ● UI状態管理が必要な画面
Widget の作成におけるクラス選定 新しいウィジェット作成 フルスクリーン・モーダル? UIスタック・入力モード切替必要? No HUD要素? Yes Yes No No 既存パーツから派生? Yes CommonAcitivatableWidget UserWidget (CommonUserWidget) Button, ListView等
レイアウト 全体戦略 ● シンプルで意図が分かりやすい構造 ○ ○ 階層は浅く保ち不要な入れ子は避ける ボックスとグリッドを積極活用 ● 画面の目的を明確化 ○ クラス選択と配置はおのずと決まる ■ 固定配置 → Canvas ■ グリッド配置 → GridPanel ■ 重ね合わせ → Overlay ● レスポンシブデザインを考慮 ○ 画面サイズに自動スケール ○ アンカーとSize/Scale Box
レイアウト構築における検討事項 ⬜ Canvas Panel はレイアウト配置のみに利用 子Widget毎にDrawCall数が増加 ⬜ Overlay の多用は避ける 多用するとDrawCallが増加するため注意 ⬜ Size Boxの多用を避ける 最小サイズを定義するよりSpacerを利用 ⬜ Spacerの配置が不要ならPaddingを利用 Spacerよりも階層がなくなる分コストが良い ⬜ Scale Box と Size Box の重ね利用に注意 サイズが安定せずちらつくことがある パフォーマンスとの保守性のバランス
UIアニメーション ● シーケンサーで実装 ○ ○ ● マテリアルで実装 ○ ○ ● 厳密な時間での制御が必要なケースで利用 制御するパラメータが増えるとCPU負荷増 時間に依存しないアニメーション(ボタン エフェクト、グロー表現等)で活用 マテリアルを多用するとGPU負荷増 0フレーム目だけのプロパティ制御時は、 セクションの長さを1フレームに設定 ○ アニメ開始時のみの設定等、初期フレーム だけ評価されるようにする
ナビゲーション&入力 ● ゲームパッド・キーボード・マウス・タッチを考慮してUIを設計 ○ ○ ● UIのフォーカス遷移は画面上の見た目通りの行・列の並び順にする ○ ● CommonUI + Enhanced Input を活用 ゲームパッド操作でも移動しやすいレイアウト CommonUI 使用時は内部のナビゲーションルールで統一可能 バックスタック処理のルールを明確に定義 ○ ○ 入力のイベント統合については CommonUI 利用で統一化 メニュー階層を一つ閉じる/一括閉じるの基準、警告ダイアログなどの優先度づけ ■ UIマネージャ(Subsystem)を作成して一元管理
データ連携 ● データアクセスの原則 ○ データの変更や何らかのイベント発生 トリガーはイベント駆動でUIに伝える ● ロジックと表示の依存を下げる ○ Interface, MVVM, Subsystem 利用 ● UI側でデータを直接持たない ○ UI側からデータを取得しにいくか、マ ネージャクラスからデータ更新に伴い UIも更新を行うか ウィジェット Interface ViewModel Actor, Component, Object Subsystem Data Data
UE5のUI最適化
UI最適化の資料 ● 最適化 https://dev.epicgames.com/documentation/ja-jp/unreal-engine/optimizing-user-interfaces-inunreal-engine ● UMG (Unreal Motion Graphics) のベスト プラクティス https://dev.epicgames.com/documentation/ja-jp/unreal-engine/optimization-guidelines-for-u mg-in-unreal-engine ● Mobile UI Performance Tips https://dev.epicgames.com/community/learning/talks-and-demos/KPvx/unreal-engine-mobile-u i-performance-tips-unreal-fest-2024
UI最適化のチェック項目 ⬜ Tick処理の削減、重い処理を避ける ⬜ キャッシュ無効時はVolatileを有効化 ⬜ 非表示時の処理停止 ⬜ ScrollBoxよりもListViewを利用する ⬜ Canvasパネルの乱用禁止 ⬜ 不必要に巨大な半透明UIが存在しないか ⬜ Widgetの階層を深くしない ⬜ 読み込んだアセットが残り続けているか ⬜ プロパティバインドを使用しない ⬜ 複数表示するものはプール化しているか ⬜ 非表示時はHiddenよりもCollapsed ⬜ テクスチャの設定は適切か ⬜ InvalidationBox, RetainerBox 活用 ⬜ 不要なアセットが参照されていないか 覚えておいて実装の時から意識できていればなおよし
色々チェックすべき事項はあるが、 仕組みを理解して、計測して、 最適な最適化を適用できるのが理想
UI最適化でパフォーマンスを調べるツール Stat コマンド 簡易的な負荷計測 Unreal Insights 詳細な負荷計測 https://dev.epicgames.com/documentation/ja-jp/unreal-engine/statcommands-in-unreal-engine https://dev.epicgames.com/documentation/ja-jp/unreal-engine/slate -insights-in-unreal-engine Widget Reflector CSV Profiler 負荷ポイント調 軽量な負荷計測 査 https://dev.epicgames.com/documentation/ja-jp/unreal-engine/usin g-the-slate-widget-reflector-in-unreal-engine https://dev.epicgames.com/documentation/ja-jp/unreal-engine/csvprofiler?application_version=4.27
UI最適化の際に見るべきポイント CPU GPU UI最適化 Memory
UIを描画するまでの流れ 配置や描画物を決める CPUの指示に従って描く CPU GPU UI最適化 Memory 描くためのリソース
UIに関するCPU側の仕組み UI表示内容を計算 UI描画の効率化 GPUに命令を送る GameThread RenderThread RHIThread • UIの配置とレイアウト アニメーション等の更新 • DrawElement を作成 • 描画対象をリストアップ • 複数の DrawElement を Batch として纏める • テクスチャをGPUに転送 • BatchをGPUに転送 G P U
UIに関するCPU側の仕組み UI表示内容を計算 UI描画の効率化 GPUに命令を送る GameThread RenderThread RHIThread • UIの配置とレイアウト アニメーション等の更新 • DrawElement を作成 • 描画対象をリストアップ • 複数の DrawElement を Batch として纏める • テクスチャをGPUに転送 • BatchをGPUに転送 G P U
CPU処理が 重くなる /軽くなる Slow Path:低速パス Fast Path:高速パス UIに変化が発生しキャッシュを再生成するパス Slate の更新を最小限に抑えるパス Tick Slate Prepass OnPaint Tick Add Elements Slate Prepass OnPaint Add Elements 条件 ● TextBlock の文字列が変わった ● ProgressBar の値が変化した ● Layout, Padding, Visibility が変わった 条件 ● ウィジェットに変更がない ● Widget ツリーが再構築されていない ● Invalidationによりキャッシュされている 動作 ● 自分自身および親階層の無効化が発生 ● Draw Element を再生成しキャッシュ更新 動作 ● Layout 計算, OnPaint 呼び出し ● 過去のDraw Element キャッシュを再利用
Unreal Insights - Slate Insights
Unreal Insights (Slate Insights) でCPU負荷のポイントを調べ る ① “Invalidate Countˮ の多い部分箇所、 もしくは定常的に多い場合もその箇所を選択
Unreal Insights (Slate Insights) でCPU負荷のポイントを調べ る ② “Invalidationˮは「なんらかの原因で UIの Invalidation (高速パスが無効化 )されている」 ウィジェットを示す ⇒ 必要であればよいが、ここを極力減らすこと ③ “Updateˮは「なんらかの原因で UIの更新処理が 行 われている」ウィジェットを示す ⇒ 必要ならば処理するが、無駄がないかを確認 「なんらかの原因」の特定はこちらを参照: https://dev.epicgames.com/documentation/ja-jp/unreal-engine/slate-insights-in-unreal-engine
Widget Reflector Widget Tree でチェック項目 □ 階層構造でネストが深すぎないか □ Visibility が 用途に応じて適切な設定か □ スクロール中に”画面外のセル”を表示しているか □ InvalidationBox / RetainerBoxの配置は適切か □ “想定外に生きているWidget”がないか
Widget Reflector で更にデバッグ確認 Debug Option でチェック項目 □ Update 処理が行われるかどうか □ Paint 処理が行われるかどうか □ Prepass 処理が行われるかどうか □ Batch は適切かどうか □ Overdraw は適切かどうか
UIに関するCPU側の仕組み UI表示内容を計算 UI描画の効率化 GPUに命令を送る GameThread RenderThread RHIThread ID:1 ID:2 ID:4 ID:3 ID:5 • UIの配置とレイアウト アニメーション等の更新 • DrawElement を作成 Batch:1 ID:1 Batch:2 ID:2 Batch:3 ID:3 Batch:1 Draw:1 ID:5 Batch:2 Draw:2 ID:4 Batch:3 Draw:3 • 描画対象をリストアップ • 複数の DrawElement をBatch として纏める • テクスチャをGPUに転送 • BatchをGPUに転送 G P U
UIに関するGPU側の仕組み C P U 3Dオブジェクト描画 2Dオブジェクト描画 Scene Rendering SlateUI • Naniteのジオメトリ描画 • Lumenによるライティング描画 • ポストプロセスによる演出描画 • アップスケーリング • UIイメージやテキストなどのバッチ描画 • UIポストプロセス処理の適用 • UIレンダーターゲットの描画
Unreal Insights によるUIのGPU負荷の確認 “SlateUI”の箇所が GPU側のUI負荷
ProfileGPU コマンドによるUIのGPU負荷 ① ProfileGPU コマンドの実行 ゲーム起動中に ProfileGPU コマンドを実行 ログファイル(.log)に書き込まれるのでログを開いて内容を確認する
CSVプロファイルを使用したプロファイル ① CSVプロファイルのキャプチャ ゲーム起動中にコマンド(csvprofile start / csvprofile stop)実行 ② プロファイルを SVGグラフ化 C:\Engine\Launcher\UE_5.7\Engine\Binaries\DotNET\CsvTools\csvtosvg -csv Profile(20251128_173355).csv -stats Slate/*;*/Slate -nosnap -showaverages -interactive
UIに関するメモリの仕組み ● ● ● ● CPUメモリ (RAM) GPUメモリ (VRAM) 「UIを構築/計算」 「UIを要素を描画」 Widgetオブジェクトのデータ テクスチャの元データ フォントデータ テキスト情報 ● ● ● ● UIテクスチャ マテリアルのUI描画用バッファ DrawElement / DrawCall の結果 レンダーターゲット CPUとGPUでのUIメモリにおいてはテクスチャの利用に注目
Memreport コマンドでメモリ計測 ① memreport コマンドの実行 ゲーム起動中に memreport コマンドを実行 実際にゲーム中のそのシーンで利用されている Texture をリストアップ “TEXTUREGROUP_UI” でリストアップしたテクスチャが本当に使用するものか? 設定は適切か? エンジンの仕組み上、レベルが切り替わらない限りテクスチャが残り続ける ⇒ ソフト参照を利用することで読み捨てが可能 ([UE4] Widgetとリソースを切り離す方法)
Memory Insights で詳細なメモリ計測 ① Unreal Insightsのキャプチャ ゲーム起動引数に -trace=default,memory,metadata,assetmetadata -statnamedevents を付与して実行
Memory Insights でメモリ計測 (メモリを占有しがちな)テクスチャも、どのくらいのリソースを確保しているか確認可能
本講演のまとめ UE5 ではUIについても開発についても積極的に取り組んでおり、大規模プロ ジェクト向けの高度な機能や、デバッグ機能を利用できるようになりました このような機能や、旧来からのテクニックを活かす事で、 ● ● より効率的で変更に強いUIを作成することができる UIのパフォーマンスを低い状態に維持できる ようになり、コンテンツをより良いものにすることができます
THANK YOU!
Appendix
UI学習コンテンツ ● 公式サンプル Content Example, UI Material Lab ● ゲームUI GAME UI DATABASE : https://www.gameuidatabase.com/index.php Interface In Game :https://interfaceingame.com/ ● レイアウトについて https://www.youtube.com/watch?v=kTg2Le6QwrQ https://www.youtube.com/watch?v=FDnxmsNIqt4 https://www.youtube.com/watch?v=cmFb69OMdfE
Common UI Widget(既存からの派生) CommonButtonBase UButton) ● スタイルシステム(UCommonButtonStyle)による複数サイズ対応 ● 選択状態(Selected)の管理とスタイル切り替え ● ロック機能(Locked)でクリックをブロック ● ホールド入力対応(Press and Hold) ● 入力アクション自動バインド(TriggeringInputAction、 TriggeringEnhancedInputAction) ● プラットフォーム別アイコン表示(CommonActionWidget連携) ● 状態別サウンド(Pressed/Clicked/Hovered、Selected/Locked対 応) ● ダブルクリック対応 ● ドラッグ&ドロップ対応 ● フォーカス時の自動選択オプション ● トグル可能な選択状態 CommonTextBlock UTextBlock) ● スタイルシステム(UCommonTextStyle) ● 自動スクロール(UCommonTextScrollStyle) ● モバイル向けフォントサイズ倍率(MobileFontSizeMultiplier) ● 空テキスト時の自動コラプス ● テキストケース変換 CommonRichTextBlock URichTextBlock) ● モバイル向けテキストスケール(MobileTextBlockScale) ● インラインアイコン表示モード(IconOnly/TextOnly/IconAndText) ● インラインアイコンのティント ● 自動スクロール ● デフォルトテキストスタイルオーバーライド CommonAnimatedSwitcher UWidgetSwitcher) ● 遷移アニメーション(ECommonSwitcherTransition) ● 遷移カーブ(ETransitionCurve) ● 遷移時間設定 ● 遷移中の入力ガード ● CommonActivatableWidgetの自動アクティベーション/デアクティ ベーション CommonListView UListView) ● フォーカス時の自動スクロール ● タッチ入力時のスクロール継続 ● エントリ間隔設定(SetEntrySpacing) CommonTileView UTileView) ● フォーカス時の自動スクロール ● タッチ入力時のスクロール継続 CommonBorder UBorder) ● スタイルシステム(UCommonBorderStyle) ● セーフゾーン対応(bReducePaddingBySafezone) ● 最小パディング設定
CommonLazyImage UImage ● 非同期テクスチャ/マテリアル読み込み(TSoftObjectPtr) ● 読み込み中のスピナー表示 ● マテリアルテクスチャパラメータ自動設定 CommonHierarchicalScrollBox UScrollBox) ● 階層構造対応(SCommonHierarchicalScrollBox) CommonVisibilitySwitcher UOverlay) ● 可視性ベースのウィジェット切り替え ● CommonActivatableWidgetの自動アクティベーション ● スロット追加時の自動アクティベーション CommonCustomNavigation UBorder) ● カスタムナビゲーションイベント(OnNavigationEvent) CommonHardwareVisibilityBorder UCommonBorder) ● ハードウェア/プラットフォーム/入力タイプに基づく可視性制御 (FGameplayTagQuery) CommonRotator UCommonButtonBase) ● テキストラベルのローテーション ● コントローラーナビゲーション対応 ● 左右シフト機能 CommonDateTimeTextBlock UCommonTextBlock) ● 日時表示 ● カウントダウン表示 ● タイムスパン表示 ● 自動更新タイマー CommonBoundActionButton UCommonButtonBase) ● アクションバインド自動表示 ● アクション名テキスト表示 ● ホールドアクション連携 CommonBoundActionBar UDynamicEntryBoxBase) ● 現在利用可能なアクションの自動表示 ● アクションボタンの動的生成 ● 入力タイプ変更時の自動更新 CommonActivatableWidgetSwitcher UCommonAnimatedSwitcher) ● CommonActivatableWidgetの自動アクティベーション/デアクティ ベーション ● フォーカス復元ターゲットのクリア CommonNumericTextBlock UCommonTextBlock) ● 数値の補間アニメーション ● 数値タイプ(Number/Percentage/Seconds/Distance) ● カスタム数値フォーマット ● サイズ補間
Common UI Widget(新規) CommonActionWidget UWidget) ● プラットフォーム別入力アイコン表示 ● 入力アクション(FDataTableRowHandle、UInputAction)の可視化 ● 複数アクション対応 ● ホールドアクションの進捗表示(マテリアルパラメータ) ● 入力方法変更時の自動更新 CommonUserWidget UUserWidget) ● ポインター入力の消費制御 ● UIアクションバインド登録 ● スクロール受信者の登録 ● CommonUIサブシステムへのアクセス CommonActivatableWidget UCommonUserWidget) ● アクティベーション/デアクティベーション ● バックアクション処理 ● 入力ルーティングツリー管理 ● フォーカスターゲット管理 ● 入力マッピングコンテキスト適用 ● モーダル表示 ● 可視性バインディング CommonLazyWidget UWidget) ● 非同期ウィジェット読み込み(TSoftClassPtr) ● 読み込み中のスピナー表示 ● 読み込み状態変更イベント CommonLoadGuard UContentWidget) ● コンテンツ読み込み中のガード表示 ● スピナーとメッセージ表示 ● アセット自動読み込み(GuardAndLoadAsset) ● 読み込み状態管理 CommonWidgetCarousel UPanelWidget) ● ウィジェットカルーセル表示 ● 自動スクロール ● 遷移速度設定 ● 子ウィジェットキャッシュ CommonWidgetCarouselNavBar UWidget) ● カルーセルのナビゲーションバー ● ページボタンの自動生成 ● ボタングループ管理 CommonTabListWidgetBase UCommonUserWidget) ● タブリスト管理 ● タブ登録/削除 ● CommonAnimatedSwitcher連携 ● タブ間ナビゲーション(Next/Previous) ● タブの有効/無効制御
CommonVideoPlayer UWidget) ● メディア動画再生 ● 再生制御(Play/Pause/Seek) ● ループ再生 ● ミュート ● 再生イベント(Resumed/Paused/Complete) CommonVisualAttachment USizeBox) ● ゼロサイズのビジュアルアタッチメント ● コンテンツアンカーポイント設定 ● ラベル横のアイコン配置など CommonActivatableWidgetContainerBase UWidget) ● 複数のCommonActivatableWidget管理 ● 一度に1つのウィジェット表示 ● ウィジェットプール ● 遷移アニメーション CommonActivatableWidgetStack UCommonActivatableWidgetContainerBase) ● スタック形式のウィジェット管理 ● トップのみ表示/アクティブ ● デアクティベーション時の自動削除 ● ルートコンテンツ設定 CommonActivatableWidgetQueue UCommonActivatableWidgetContainerBase) ● キュー形式のウィジェット管理 ● 先頭のみ表示/アクティブ ● デアクティベーション時の自動削除と次への移行
Common UI -マルチレイヤーメニュー操作(レイヤー管理) レイヤー管理システム RootViewportLayout CommonActivatableWidget Queue CommonActivatableWidget Stack CommonActivatableWidget ContainerBase レイヤー階層 Layer1: HUD bIsModal=false アクティベーション管理 Layer2: Menu bIsModal=false Deactivate Widget Layer3: Modal Popup bIsModal=true Activate Widget ActivatableTreeRoot ActivatableTreeNode
Common UI -ウィジェットの追加とアクティベーション Application Widget Stack AddWidget Activatable Widget ActionRouter Activatable TreeRoot Activatable TreeNode CreateInstance Add to WidgetList Render Batch送信 InternalProcess Activation NotifyWidget Constructed Create/Update TreeRoot Create/ TreeNode RegisterInputTree UpdateLeafmost ActiveNode ApplyLeafmost NodeConfig InternalProcess Activation ウィジェットがアクティブになり入力を受け入れ取れる状態 SetCanReceiveInpu t
Common UI -入力ルーティング 入力リソース PlayerInput 入力ルーティング システム SlateApplication GameViewportCli ent CommonUIActionRouterBase LocalPlayerSubsystem ActivatableTreeRoot ActivatableTreeRoot UIActionBinding アクション管理 Process HoldInput アクティベーション管理 Process NormalInput Root Widget 1 PaintLayer: 100 Root Widget 2 PaintLayer: 200
Common UI -入力処理フロー PlayerInput GameViewport Client KeyPressEvent ActionRouter ProcessInput Activatable TreeRoot Find Leafmost ActiveNode LeafmostActi veLeafNode GetLeafmostNo de ActionBinding FindMatching Binding Activatable Widget ExecteAction Delegate HandleAction Handled Unhandled Unhandled RouteUIInputRe sult
Common UI -UIナビゲーション ナビゲーションタイプ ナビゲーション システム Mouse Navigation Click/Hover Gamepad Navigation D-Pad/Analog Keyboard Navigation Tab/Arrow UINavigationmanager SlateFocusSystem Navigation Routing アクション管理 FocusRestorat ionTarget LeafmostActiv eNode DesiredFocusT arget ナビゲーションポリシー Route To Button Most Child Accept Focus Route To Top Most Child Route To Left/Right Most Child
Slate PostBuffer アーキテクチャ サブシステム LoadGetPostBufferRT リソース UTextureRendererTarget2D (PostBuffer RenderTarget) USlateRHIRenderer Settings ウィジェット サブシステム USlateFX Subsystem FSlateRHIPostBuffer ProcessorProxy SPostBufferUpdate FPostBufferUpdater PostProcess_RenderTread 後処理実行 FRDGBuilder AddSlatePostProcessCopy バックバッファコピー レンダリング FSlateRHI Renderer FSlateElement Batcher
UI Component アーキテクチャ UserWidget UUserWidget UUIComponent UserWidgetExtention UWidgetTree 管理 含む UIComponent管理 含む UUIComponentContainer Widget階層 UTextBlock MyText UButton MyButton 保持 FUIComponentTarget配列 初期化 関連付け TargetName: MyText Component: UScaleBoxComponent UI Component 初期化 関連付け TargetName: MyButton Component: USizeBoxComponent 初期化 関連付け TargetName: MyButton Component: UMouseHoverComponent
UI最適化 (CPU) UMG Widget Slate Widget Widget構築 Layout System Invalidation Element Batcher Render Thread レイアウト計算 CPU負荷:高 再計算頻度高 変更検出 CPU負荷:中 差分変更処理 Draw Element作成 CPU負荷:中 バッチング処理 Render Batch送信 GPUコマンド作成
UI最適化 (GPU) Input Assembler 「データ読み込み」 Vertex Shader 「座標変換」 Rasterizer 「ピクセル化」 Pixel Shader 「色計算」 Output Merger 「画面に書き込み」 • UI要素の形を表すデータを読み込む • 三角形の組み合わせでUIを表現 • UI要素の位置を画面座標に変換 • テクスチャのどの部分を使うか計算 • 三角形を画面のピクセル(点)に分解 • 画面外の部分は除外 • テクスチャから色を読み取る • 透明度(アルファ)を処理 • UIとゲーム画面を合成 • 最終的な色を画面バッファに書き込む • 既存の色と合成(ブレンディング) Material GPU負荷:中