在某些情况下,为项目提供资源而不将资源作为场景的一部分进行加载是很有用的做法。例如,可能存在可出现在游戏的任何场景中但不经常使用的角色或其他对象(比如说,可能是“秘密”功能、错误消息或高分警报)。此外,甚至可能希望从单独的文件或 URL 加载资源,从而减少初始下载时间或支持可互换的游戏内容。
Unity 支持项目中的__资源文件夹__,允许在主游戏文件中提供内容,但在请求之前不加载这些内容。也可以创建__资源包__。这些文件完全独立于主游戏文件,其中包含游戏按需从文件或 URL 访问的资源。
资源包是外部资源集合。您可以拥有许多资源包,因此可以拥有许多不同的外部资源集合。这些文件存在于构建的 Unity 播放器之外,通常位于 Web 服务器上,供最终用户动态访问。
要构建资源包,可在 Editor 脚本中调用 BuildPipeline.BuildAssetBundles()。在参数中,指定要包含在构建文件中的__对象__数组以及其他一些选项。这将构建一个文件,稍后即可使用 AssetBundle.LoadAsset() 在运行时动态加载该文件。
资源文件夹是包含在构建的 Unity 播放器中但不一定链接到 Inspector 中任何游戏对象的资源集合。
要将任何内容放入资源文件夹,只需在 __Project 视图__中创建一个新文件夹,并将该文件夹命名为“Resources”。可在项目中以不同方式组织多个资源文件夹。每当想从其中一个文件夹加载资源时,请调用 Resources.Load()。
在 Resources 文件夹中找到的所有资源及其依赖项都存储在名为 resources.assets 的文件中。如果一个资源已被另一个关卡使用,则该资源会存储在该关卡的 .sharedAssets 文件中。 Edit > PlayerSettings First Streamed Level 设置决定了在哪个关卡收集 resources.assets 并将其包含在构建中。
如果“First streamed Level”之前的某个关卡在资源文件夹中包含某个资源,则该资源将存储在该关卡的资源中。如果随后包含该资源,则该关卡将从“resources.assets”文件中引用该资源。
通过 Resources.Load() 只能访问 _Resources 文件夹_中的资源。然而,更多资源可能最终出现在“resources.assets”文件中,因为它们是依赖项。(例如,Resources 文件夹中的材质可能引用 Resources 文件夹之外的纹理)
可通过调用 AssetBundle.Unload() 来卸载 AssetBundle 的资源。如果为 unloadAllLoadedObjects 参数传递 __true__,则 AssetBundle 内部保存的对象和使用 AssetBundle.LoadAsset() 从 AssetBundle 加载的对象都将被销毁并且捆绑包使用的内存将被释放。
有时可能更希望加载 AssetBundle,实例化所需的对象,并释放捆绑包使用的内存,同时保留对象。好处是可以释放内存来用于其他任务,例如加载另一个 AssetBundle。在这种情况下,可传递 false 作为参数。销毁资源包后,无法再加载其中的对象。
如果要在加载另一个关卡之前销毁使用 Resources.Load() 加载的场景对象,请对这些对象调用 Object.Destroy()。要释放资源,请使用 Resources.UnloadUnusedAssets()。