大量にプリセットで用意された3Dオブジェクトやアニメーションデータをユーザーが好きに組み合わせてシーンを構築するコンテンツをUnity3Dで作っているときにハマったこと。
今までUnity3Dで作成したコンテンツはどれもアプリ起動時にメモリ内にすべてのリソースを読み込んでいたけど、今回のはあまりにもリソース量が多い & アプリ本体を更新せずに素材の追加配信を行いたい、ということでAssetBundleという仕組みを利用しリソースをアプリ外に押しやり、必要な時に逐次読み込み & 逐次破棄を行うことにした。
実装自体はパパッと出来たんだけどここで一つ問題が。
読み込んだAssetBundleが不要になったのでAssetBundle.Unloadで破棄しようとしてもメモリが解放されない。
なので、シーンを構築するために3Dオブジェクトやアニメーションデータを色々と読み替えているとメモリ使用量が膨れあがりそのうち「メモリが確保できない」というエラーメッセージとともにアプリケーションがクラッシュすることに...。
前置きはここまでで、この問題の解決方法。
Resources.UnloadUnusedAssets() を呼ぶ。
調べてわかったのですが、これはAssetBundleを破棄するときだけではなく、Resources.Loadでリソースを読み込んで破棄する場合にも呼ぶ必要があるみたい。
勿論 Resources.UnloadUnusedAssets() 呼ぶ前に対象を参照している変数にnullを突っ込まないと残念なことになるので注意。
Resources.UnloadUnusedAssets() を呼んでもメモリ使用量が減らない場合は何処かで参照していないか疑いましょう。
0 件のコメント:
コメントを投稿