アセットの同期/非同期ローディング

今回の主な話題:「アセットの同期/非同期ローディング」、「Physics2D浮動小数点数衝突」、「SendWillRenderCanvasコスト」…


UI

Q1: 二つのフォントコントロールは毎フレームに異なる数字を表示し、1つ目が8文字、2つ目が6~7文字であります。認識のためにoutlineを開く必要があり、高いパフォーマンスコストを引き起こします。この2つのコントロールを別々に独立のCanvasに置いても、問題は依然としてあります。今が分かれるのは、このコストは二つのフォントコントロールの毎フレームのテキスト変更によって引き起こされます。

UIの配置は下記のように。

引き起こされたコストは下記のように。

コメントに「一つが8文字、もう一つは6〜7文字」で言いながら、二つともoutlineを開きました。最初に「この二つを禁止された後、SendWillのコストはなしになるかどうか」をもう一度確認すると提案します。この数字を見るとそんなに高いコストを引き起こす可能性は高くないです。

次に、もしこの二つは確かに原因であれば、outline効果あり静的フォントに変えるかどうかが考えられます。できなければ更新頻度を下げることができるかどうか、本当に毎フレームに変化必要はありませんかを考えてください。

もしこれ以上下げたいなら、静的フォントしか考えられません。テキストは確定なら処理しやすいが、チャットのように次の内容は分からない場合には仕方がありません。あるいはローエンドモデルにシャドウでやります。


物理

Q2:ゲームシーンに一つのboxcollider2Dがあり、位置は(0.0f,0.0f) から (1.0f,1.0f)、Physics2D.BoxCast(new Vector2(1.0f,1.702), Vector2(1.0f, 1.4f), 0, Vector2(0.0f,1.0f), 2.0f)を採用したら衝突が引き起こします。理論上衝突の境界は1.700であり、私はすでに位置を1.702に置いて、浮動小数点数の誤差を避けたはずです。もしこの値を1.706に拡大すれば衝突は発生しませんので、この誤差の範囲はどちらに調整できますか。

Unity 2017.1のPhysics2DSettingsに一つのDefault Contact Offsetがあり、二つcolliderの間の距離は彼らのContactOffsetの足し算の結果より小さいなら衝突が発生します。この値を小さく設定しますと問題主の質問が解決できはずです。下図のように:

Unity 5.xのContact Offsetは,デフォルトで0.01であります。これも1.702ではできませんが,1.706ではできる理由であります。


レンダリング

Q3:UWAにある文章がMaterialPropertyBlock方式でMaterial属性を操作するとおすすめし、効率を上昇できると説明されました。ShaderLab: Propertiesファイルを調べる時、このような文が書いてあります。

[PerRendererData] - indicates that a texture property will be coming from per-renderer data in the form of a MaterialPropertyBlock. Material inspector changes the texture slot UI for these properties.

これに質問があります。Shaderバラメータは[PerRendererData]で記述すべきかどうか、MaterialPropertyBlock操作に対して影響がありませんか。「使う」と「使わない」二つの状況を試しましたが、表示効果はいずれも正常でした。

理論的に[PerRendererData]はEditorの表示行為のみ改めません。問題主がMaterialPropertyBlockを使って、あるMaterialのTextureを変えた後に、これを加えるしかプレビュー対応のMaterialパネルにこの新しいTextureが見られません。

下記の図1はPerRendererDataのない場合に、EditorでまたRuntime時に表示された内容です。PerRendererDataを加えた後に、図2はEditorで、図3はRuntime時に表示された内容です。

図1

図2

図3


ローディング

Q4:現在、Resources.Load()でアセットをロードする時、UIアニメーションに重い現象がよく現れます。解消したいなら、非同期ロードする、Prefabを分割するや材質メッシュアニメーションを最適化するみたいな操作しか実現させませんか。それともUIアニメーションは他のスレッドで再生されませんか。非同期する速度は絶対に同期するのより遅いですか。

非同期ロードは同期ロードの重い現象を緩和することができますが、効果はあまりよくないです、こちらの文章を参考してください。アセット分割りを試し、同一時間にロードしないようにすることをおすすめします。即時表示されたUIや他のGameObjectではなければ、時間がかかる部分的なアセット(Atlas、Shadderなど)を事前にロードしようと試みることができます。即時表示されたUIであれば、非同期ロードはこの要求を満たすことができませんので、考える必要がありません。

非同期ロードの速度は絶対に同期ロードより遅いではありません。ただ、一般的にはそうであります。しかし、具体的にいくら遅いかは、ロードされたアセットの種類と量次第です。


アニメーション

Q5:ゲーム内対戦時には頻繁に武器を変わるやスキルを使う時(主にネットワークプレイヤー)、違う動作を取り替えます。ただし、毎回animatorOverride[name]=clip(3〜6個)を設定しますと、CPU占有は50-180msであり、これはどうしてですか。 公式の指導により一つのリストを保存しました(https://docs.unity3d.com/scriptreference/animatoroverridecontroller.applyoverrides.html)、毎回LateUpdateをする時ApplyOverridesを使って、占有はより高くなる(400ms)と発見されました、これはどうやって解決できますか。現在各ネットワークプレーヤのプレイヤOverRidesCountは73であり,Clipが多すぎるの原因ではありませんか。

実機で実行する時、animatorOverride[name]=clipの時間コストはanimatorcotrollor中のclipに影響され、数が多くなるにつれて時間コストが著しく増え、70個以上のclipがあれば時間コストは確かに50ms(Redmi note2)以上になれます。しかし,applyOverrides法に変えても時間コストは高いです。またMonoメモリの割当ても現れますが、400ms程度にはなれません。

一方、AnimatorOverrideControllerを全体的に変えることも試しました。すなわち、現用使っているAnimatorOverrideControllerにclipを取り替えるではなく、別のoverridecontrollerでclipを取り替えた後、全体的にruntimeAnimatorControllerに取り替えます。これでコストを低くなされます。


UWA公式サイト:https://jp.uwa4d.com

UWA公式ブログ:https://blog.jp.uwa4d.com

UWA公式Q&Aコミュニティ:https://answer.uwa4d.com