背景メッシュの結合による最適化に向けたトライ&エラー
by
Katsuya100
Link
Embed
Share
Beginning
This slide
Copy link URL
Copy link URL
Copy iframe embed code
Copy iframe embed code
Copy javascript embed code
Copy javascript embed code
Share
Tweet
Share
Tweet
Slide 1
Slide 1 text
背景メッシュの結合による 最適化に向けたトライ&エラー 村上克弥 ファイトリーグ事業部 クライアント開発グループ 2018/07/25
Slide 2
Slide 2 text
自己紹介 所属 株式会社ミクシィ XFLAG スタジオ ファイトリーグ事業部 クライアント開発グループ 経歴 2013年 東京の某社に入社 ・K社の有名なIPとか ・S社の有名なIPを扱ったタイトルとか 2017年 ミクシィ入社 ・ファイトリーグでクライアント開発やってます ・実装とかツール作りとか色々やってます。 その他 褒められたい 名前:村上克弥
Slide 3
Slide 3 text
突然ですが うちのプロジェクト 背景のGameObject数がそこそこあるんです。
Slide 4
Slide 4 text
でも、デザイナさんに罪はないので メッシュ結合ツールを作りました。
Slide 5
Slide 5 text
意外と大変でした。 頑張ったんで、褒めてほしいです。 聞いてください。
Slide 6
Slide 6 text
要件 ・背景メッシュを結合し、GameObjectを減らす ・本来の見た目を問題ない範囲で維持する ・それによってパフォーマンスを低下させない ・あわよくばドローコールを減らす ・レンダラーパラメーターの異なるものを結合しない ・アニメーションするメッシュは結合しない ・スキンメッシュは結合しない ・参照されているゲームオブジェクトは結合しない ・褒めてほしい
Slide 7
Slide 7 text
要件 ・背景メッシュを結合し、GameObjectを減らす ・本来の見た目を問題ない範囲で維持する ・それによってパフォーマンスを低下させない ・あわよくばドローコールを減らす ・レンダラーパラメーターの異なるものを結合しない ・アニメーションするメッシュは結合しない ・スキンメッシュは結合しない ・参照されているゲームオブジェクトは結合しない ・褒めてほしい ↑この辺は大変じゃなかったんで、語りません。
Slide 8
Slide 8 text
↓これですが。 要件 ・本来の見た目を問題ない範囲で維持する
Slide 9
Slide 9 text
要件 今回サンプルに選んだのは、 で使用している背景
Slide 10
Slide 10 text
要件 ゲームオブジェクト数はこれくらい。
Slide 11
Slide 11 text
では、やっていきます
Slide 12
Slide 12 text
CombineMeshes まず最初に思いつくのはこれです。
Slide 13
Slide 13 text
CombineMeshes 理想では、こんなふうに結合してくれるはずです。 やってみました。
Slide 14
Slide 14 text
駄目です。
Slide 15
Slide 15 text
CombineMeshes このAPIは、SubMeshがある場合 サブメッシュごとに結合しなければなりません。
Slide 16
Slide 16 text
CombineMeshes 一度、別のメッシュに分離するので、 サブメッシュ間の共有頂点が複製されてしまい、 頂点数が増えます。
Slide 17
Slide 17 text
CombineMeshes(を手作り) 幸い、経験上、Meshクラスの構造には 覚えがありました。 マテリアルの情報からサブメッシュを振り分け、 まとめて一回でメッシュ結合する仕組みを作ります。
Slide 18
Slide 18 text
CombineMeshes(を手作り) 出来ました。 ※ライトマップは焼いてません
Slide 19
Slide 19 text
CombineMeshes(を手作り) GameObject数も激減。
Slide 20
Slide 20 text
CombineMeshes(を手作り) あとは、ライトマップを焼いて、 左の見た目になれば成功です。 やってみました。
Slide 21
Slide 21 text
駄目です。
Slide 22
Slide 22 text
CombineMeshes(を手作り) やってみた結果
Slide 23
Slide 23 text
CombineMeshes(を手作り)
Slide 24
Slide 24 text
CombineMeshes(を手作り) 理想 現実
Slide 25
Slide 25 text
CombineMeshes(を手作り) 世紀末
Slide 26
Slide 26 text
CombineMeshes(を手作り) 謎の荒れの原因は、ライトマップ用のUVが作られていな かったことです。 Unityではuv2をライトマップ用UVとして使うので uv2を生成する必要があります。
Slide 27
Slide 27 text
SecondaryUVを生成 こんな関数を見つけました。 実際に使ってみました。
Slide 28
Slide 28 text
SecondaryUVを生成 お!いいかんじ!
Slide 29
Slide 29 text
駄目です。
Slide 30
Slide 30 text
SecondaryUVを生成 ライトマップテクスチャがページングされていました。 このままでは、ドローコール増加につながるため パフォーマンスが低下します。
Slide 31
Slide 31 text
SecondaryUVを生成 原因は、メッシュを結合する際 MeshRendererの「Scale In Lightmap」を 考慮していないせいです。 そのせいで、等倍のライトマップが生成されています。
Slide 32
Slide 32 text
「Scale In Lightmap」を逆算 結合前の全メッシュのライトマップ総面積を足して、 その平方を取れば、 同じ面積でライトマップを生成できるはずです。 問題はその計算式です。
Slide 33
Slide 33 text
「Scale In Lightmap」を逆算
Slide 34
Slide 34 text
ありました。 「Scale In Lightmap」を逆算
Slide 35
Slide 35 text
この辺はリフレクションで呼び出します。 「Scale In Lightmap」を逆算
Slide 36
Slide 36 text
「Scale In Lightmap」を逆算 そして出来た「Scale In Lightmap」です。
Slide 37
Slide 37 text
ぱっとみ良さげに見えるし、 ライトマップテクスチャも1枚です。 これならいけるのでは? 「Scale In Lightmap」を逆算
Slide 38
Slide 38 text
駄目です。
Slide 39
Slide 39 text
解像度の低い部分が出てしまいます。 これではデザイナさんの調整が死にます。 結合前 結合後 「Scale In Lightmap」を逆算
Slide 40
Slide 40 text
アプローチを変えました。 「Scale In Lightmap」を逆算
Slide 41
Slide 41 text
結合前にライトマップを焼く uv2にライトマップのUVが入っているので 結合前のライトマップテクスチャを 使うことができるはずです。
Slide 42
Slide 42 text
結合前にライトマップを焼く PropertyBlockでテクスチャを適用するコンポーネントを作成。 lightmapScaleOffsetからUVを再計算。 シェーダーキーワード「LIGHTMAP_ON」を適用。
Slide 43
Slide 43 text
結合前にライトマップを焼く これで今度こそいけるはずです!
Slide 44
Slide 44 text
駄目です。
Slide 45
Slide 45 text
結合前にライトマップを焼く ライトマップは適用されてるけど めっちゃ明るくなった…。
Slide 46
Slide 46 text
結合前にライトマップを焼く FrameDebuggerで見てみると
Slide 47
Slide 47 text
結合前にライトマップを焼く 誰やねんお前
Slide 48
Slide 48 text
LIGHTPROBE_SHをスキップ 「LIGHTPROBE_SH」は Unityによって、強制的に設定されます。 Lightmap焼き込み済みのオブジェクトは 「LIGHTPROBE_SH」が除外されるようです。 なので 「#pragma skip_variants LIGHTPROBE_SH」 を記述したシェーダーを作成します。 (#pragmaは#ifdefで弾けない…仕様?) 結合時にシェーダーを差し替えることで、 対応します。
Slide 49
Slide 49 text
LIGHTPROBE_SHをスキップ 結果
Slide 50
Slide 50 text
LIGHTPROBE_SHをスキップ
Slide 51
Slide 51 text
LIGHTPROBE_SHをスキップ 結合前 結合後 見た目よし…。
Slide 52
Slide 52 text
LIGHTPROBE_SHをスキップ 結合前 結合後 諸々、数値よし…。
Slide 53
Slide 53 text
OKです!
Slide 54
Slide 54 text
まとめ
Slide 55
Slide 55 text
まとめ ライトマップの解決は大変。 褒めてほしい。