この話では、Quest開発をするためのノウハウ話ではなく、あくまでもPlayAniMakerをPC版からQuest版にするために行った最適化を解説した内容になります。
Quest開発を行うにあたってフレームシンセシスさんのブログを参考に開発を進めました。すごく詳しく書いてあるのでQuest開発をしたい人は必読!
まずは、Questで動くようにブログを見ながら設定をしてQuest出力をしてみましたが、想像通り処理が重かったです。。。。
twitter post: 1399692531722383361
↑このとき、動くには動いたが処理は重かったです。
UnityProfilerを見ながら処理が重い個所を見つけていきました。調べた感じだと特に処理負荷が大きいところは下記の二点でした。
・ポストエフェクト
・キャラクター描画
GPUまわりの処理が負荷の原因だったのでGPUを減らすように最適化を始めました。
アニメ表現を入れるためにポストエフェクト機能を入れていたのですが、使っているエフェクトをどんなに少なくしても処理落ちしてしまうので、仕方なくポストエフェクトは削除することにしました。。。。
これだけでFPSが40→50FPSくらいまで回復。合わせてRenderTextureも最小限の数に変更。FPSが50→60まで回復。
描画で負荷になっている場合、原因として考えられるのは主に下記の3つ。
・ポリゴン数
・シェーダーの種類
・マテリアルやテクスチャの数
ここから要素を分解して原因を探してみます。
経験からこの場合、ポリゴン数というよりシェーダーやマテリアル関係だということが予想できたので、まずはそっちを調べました。
余談ですが、VRで描画負荷の原因を見つけるときよくやるのは、何もない場所と物がある場所(PlayAniMakerの場合だとキャラクターが1人立っている場所)を交互に見て物がある場所を見た時だけFPSの負荷が上がる場合は、描画負荷を疑うと良いです。逆に何もない場所を見ているのに負荷が上がる場合は描画ではない原因(CPU側の問題)を疑うと良いです。
1.シェーダーを変えてみる。
PC版ではMToonを使っていたのですが、シェーダーをUnity標準のUnlit Shaderに変更。この段階でほぼ68FPSくらいまで回復しました。(どうやらシェーダーは重みたいだ。)
2.マテリアル数を変える
Vroidモデルを使用しているので髪の毛のマテリアルがすごい量になっています。
なのでこれらのマテリアルを統合して1つにマテリアルにしました。
統合にはMeshBakerを使用。詳しい使い方はこちらの記事を見ると参考になります。
これにより72PFSをキープすることが出来た出来ました
Unlit Shaderなら描画負荷としてはオーケーなことが分かったのですが、PlayAniMakerの表現としてアニメ調の表現が出来るようにしたいのでUnlitのままではダメでした。なのでMToonをベースに軽量化を開始。(と言っても自分はシェーダーのこと全然わからんので出来る範囲で対処をしてみることにしました。)
Unity公式のシェーダーを書く場合のパフォーマンスのヒントを読みながらやってみた。
1.float →halfやfixedに変える
記事によるとfloatの処理は重くてmobile向けではないらしい。
とのことなので、float部分を変えてみる。
MToonの場合MToonCore.cgincにシェーダーの内容が書かれているので、これを改変していきます。
例えばこんな感じ↓
これだけでもまだ描画負荷があったのでRimLightなど計算負荷が掛かりそうな項目を消して、表現に必要最小限の項目だけに内容を限定しました。(RimLightが計算処理が重いのかよくわからんけど。。。)
という感じに自分の出来る範囲でシェーダーの軽量化して、なんとか表現したい見た目を維持したまま72FPSを維持できるようになりました。
ここで注意が必要なのがUnity Editor上とQuest上で見た目が変わるときがあるで最終的は見た目はQuestで確認が必須。(Unityの使用なのかわからないですが、どうやらPC 上では常に最高の設定(float)の見た目で表現されてしまうらしい)
これで常時72FPSをキープをきるようになった!嬉しい!(※だだしQuest2ではという話なだけでQuest1で出来ているのか怪しい・・・・。これらかじっくり調べていく必要がありそう。)
Questのローカルファイルパスにアクセスする場合、AndroidManifest.xmlに記述を追加する必要があります。
"android.permission.READ_EXTERNAL_STORAGE"を追加すれば出来ると思ったのですがもう一つ追加する必要がありました。
android:requestLegacyExternalStorage = "true"を記述する必要がある。
参考URL https://qiita.com/colllet/items/5ab293c52f4bd4e2ecbb
これに気付かずにすごく時間を消費してしまった。。。