Unity——工程与资源

本文将详细介绍Unity工程的文件夹结构,以及动态加载资源的技术要点


一、Unity项目的文件夹结构

1.工程文件夹

在新建工程时,Unity会创建所有必要的文件夹。第一级文件夹有Assets,Library,Logs,Packages,ProjectSettings。

 

  • Assets:最主要的文件夹,保存着所有游戏用到的资产
  • Library:用于存放引擎必须的程序集和缓存资源。Library不存在时会自动生成,不需要也不建议上传到版本仓库(如SVN或Git仓库)中去
  • Logs:用于存放使用时产生的日志
  • Packages:目前大部分Unity的官方功能扩展都通过扩展包提供,Packages文件夹虽与扩展包有关,但里面只保存配置文件
  • ProjectSettings:所有的工程设置,包括共工程对应的Unity版本都在ProjectSettings文件夹中。不能直接改动该文件夹中的内容,不然会造成版本兼容性问题
  • (Temp):如果该工程正在被编辑,则会多出一个Temp(临时)文件夹,一旦工程关闭,该文件夹会自动消失

2.资产文件夹

由于Asset和Resource的含义相近,而且它们在Unity中都有特定的含义,因此翻译时将Asset称为资产,Resource称为资源,以示区分。

在Unity中,Asset(资源)和Resource(资源包)是两个不同的概念。

Asset(资源)是指在Unity项目中使用的各种资源文件,比如模型、纹理、材质、音频等。这些资源可以通过Unity编辑器导入到项目中,然后在代码中进行引用和使用。Assets文件夹是存放这些资源文件的默认文件夹。

Resource(资源包)是一个特定的文件夹,用于存放可在运行时加载的资源。可以将资源文件放在Resource文件夹中,并使用Resources类提供的方法在运行时加载这些资源。Resource文件夹可以位于Assets文件夹中的任意位置。

区别在于,Asset是在编辑器中管理和引用的资源,而Resource是在运行时动态加载的资源。Asset可以提前导入并在代码中直接引用,而Resource需要在代码中进行加载操作。另外,Asset在项目构建时会被打包到最终的应用程序中,而Resource则不会被自动打包,需要在运行时按需加载。

需要注意的是,Unity官方推荐使用AssetBundle来管理和加载运行时资源,因为它提供了更灵活和高效的资源管理方式。而Resource文件夹的使用在某些情况下可能会导致资源加载效率较低或管理不便。

Assets文件夹下所有的文件都是资产的一部分,但某一些资产不会被“打包”到最终发布的程序中,而其他资产则会被“打包”

要理解Assets文件夹的结构,首先要了解Assets文件夹下的几个特殊文件夹

 

文件夹是否被打包说明
Editor存放Unity编辑器专用的脚本和资源,如开发期用的扩展工具
Plugins存放第三方程序库
Resources全部资源文件夹。该文件夹下所有资源都会被压缩并打包。只有此文件夹下的内容才可以用Resource.Load加载
Streaming Assets全部该文件下的所有资源会被打包到最终的发布版中,但会保持原样,不会被压缩和加密。不需要让Unity处理的文件(如一些数据配置文件)适合放在此文件夹

除了以上特殊文件夹,在其他非特殊文件夹中的资产,Unity会根据是否引用了该资源而决定是否打包。

所有非编辑器专用的脚本资产文件都会被打包。这是由于非组件脚本也可能会被引用,不能依据是否挂载到物体上来确定一个脚本是否被用到。

被打包的资产都可以看作是发布的程序的一部分,但它们都是只读的,不能在运行时改写。换句话说,以上文件夹都不能用于做热更新。

二、META文件

在游戏的开发阶段会存在大量原始的资源和素材,如何管理它们是引擎需要考虑的。市面上的游戏引擎对原始资源的管理由以下两种主流方案。

  1. 引擎统一打包和管理所有资产。添加新资源时,通过统一的导入流程打包到专门的文件中,原始文件不再使用。
  2. 虽然引擎管理所有资产,但依旧会使用原始资源文件。一些必要信息(如模型的导入设置)会写在另外的配置文件中。

无论哪种方案,都必须对所有资产统一管理,而不能使用未处理、无记录的原始资源。

Unity采用的方案明显是第二种,它会对Assets文件夹下的所有文件生成一个名称相同,扩展名为meta的文件,包括文件夹也会生成对应的META文件。META文件是一个文本文件,里面记录了很多必要的信息,包括资产唯一标识符GUID、引用关系和资源导入设置的信息等。

其中资产唯一标识符GUID非常重要,它在资源初次导入时生成,有了它就能准确定位资源文件,文件的改名、移动和内容修改都不会使GUID变化。

脚本的META文件内容通常比较简单,只有十几行,而某些资源(如3D模型动画)往往有上千行,里面记录了必要的设置信息。

理解了META文件的重要性,在实际中还要注意以下几点:

  1. META文件与原始资源文件要一起管理。例如,新增Assets文件或文件夹时,一定要联通生成的META文件一同提交到版本仓库
  2. 重命名和移动文件要在Unity内进行,这样可以保证相应的META文件自动完成相应操作
  3. 不能直接复制META文件,否则会导致GUID重复。复制资产时应尽量在Unity内用复制命令(Ctrl+D)进行,这样会自动生成GUID不同的META文件
  4. 用脚本操作资产时要注意META文件的同步,尽量使用Unity提供的API,而不要使用原始的文件进行读写操作。这一点主要针对编辑器脚本,因为编辑器脚本有时会修改源文件的内容

三、动态加载和释放资源

一般简单的方法时使用公开变量加拖曳的方法引用资源,实际上动态加载资源的方法适用范围更广,也方便在运行时切换不同的资源。

1、动态加载资源

位于Resources文件夹下的资源都可以动态加载。动态加载资源的方法主要有Resources.Load()和Resources.LoadAll()两种,前者用于加载单个文件,而后者可以加载一个文件夹内的所有资源,结果以数组形式返回。

值得一提的是,重复加载相同的文件不会导致文件被多次加载,引擎可以判断哪些资源已经被加载过了。

2、卸载资源

加载的资源会占用内存空间,不再使用资源的时候应当卸载,卸载方法有以下两个。

//卸载一个资源
public static void UnloadAsset(Objetc assetToUnload);
//自动卸载所有未使用的资源
public static AsyncOperation UnloadUnusedAssets();

UnloadAsset()用于强制卸载一个资源,不管它是不是正在被使用。如果卸载了正在使用的资源,则会直接影响当前场景的表现。

UnloadUnusedAssets()方法会用异步方法自动卸载未被使用的资源。但问题是,如果脚本中有一个变量正在引用着某个资源,或是场景中某个忘记销毁的物体饮用者某个资源,则该资源会印在使用中而不会被自动卸载。

可以看出,写在背后隐含的问题要比加载多得多,对编程方法提出了更高的要求

3、代码示例

以下用一段简单的代码演示加载和卸载资源的编程方法

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TestResources : MonoBehaviour
{
 
    void Start()
    {
        //加载资源//
        //与之资源用GameObject表示,路径不包含Resources和扩展名
        GameObejct go = Resources.Load<GameObject>("Prefab/Cube");
        //资源加载和实例化是不同的
        GameObject go2 = Instantiate(go);

        //加载其他类型的资源
        Texture2D image= Resources.Load<Texture2D>("Images/1");
        Debug.Log(image.name);

        //卸载资源//
        //强制卸载
        TestResources.UnloadAsset(image);
        //销毁物体
        Destroy(go2);
    }

 
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/101258.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C++之map,set,multimap,multiset的使用

map&#xff0c;set&#xff0c;multimap&#xff0c;multiset的使用 关联式容器键值对树形结构的关联式容器setset介绍set的使用set定义方式set各种操作函数 multiset mapmap的介绍map的使用insert函数find函数erase函数[ ]运算符重载map的迭代器遍历 multimap 关联式容器 在…

VC++使用Microsoft Speech SDK进行文字TTS朗读

Microsoft Speech SDK下载地址 https://www.microsoft.com/en-us/download/details.aspx?id10121 需要msttss22L.exe、SpeechSDK51.exe、SpeechSDK51LangPack.exe三个&#xff0c;下载后全部安装 使用VS2005建立一个win32控制台项目 朗读"hello word"、中文“你好”…

弯道超车必做好题集锦三(C语言编程题)

目录 前言&#xff1a; 1.单词倒排 方法1&#xff1a;scanf匹配特定字符法 方法2&#xff1a; 双指针法 2.统计每个月兔子的总数 方法1&#xff1a;斐波那契数列 方法2&#xff1a;斐波那契的递归 3.珠玑妙算 方法&#xff1a;遍历 4.寻找奇数&#xff08;单身狗&#…

Linux - Docker 安装使用 常用命令 教程

Docker 官方文档地址: Get Started | Docker 中文参考手册: https://docker_practice.gitee.io/zh-cn/ 1.什么是 Docker 1.1 官方定义 最新官网首页 # 1.官方介绍 - We have a complete container solution for you - no matter who you are and where you are on your contain…

VMware 安装 Centos7 超详细过程

CentOS系统&#xff0c;安装教程可参考以下&#xff1a; 哪些模型需要在Linux下运行&#xff0c;需提前预装Linux系统呢&#xff0c;评论区讨论吧 比如Noah-MP 5.0模型 1.软硬件准备 软件&#xff1a;推荐使用 VMware&#xff0c;我用的是 VMware 12 镜像&#xff1a;CentO…

15. 查看开源项目

15.1 parser.add_argument ① 像运行Tensorboar一样&#xff0c;在Terminal终端&#xff0c;可以命令运行.py文件。 ② 如下图所示&#xff0c;Terminal终端运行.py文件时&#xff0c;--变量 后面的值是给变量进行赋值&#xff0c;赋值后再在.py文件中运行。例如 ./datasets/…

【炼气境】HashMap原理以及如何使用

系列文章目录 文章目录 系列文章目录前言1、数据结构2、工作原理3、当两个对象的 hashCode 相同会发生什么&#xff1f;4、你知道 hash 的实现吗&#xff1f;为什么要这样实现&#xff1f;5、为什么要用异或运算符&#xff1f;6、HashMap 的 table 的容量如何确定&#xff1f;l…

WPF实战项目十三(API篇):备忘录功能api接口、优化待办事项api接口

1、新建MenoDto.cs /// <summary>/// 备忘录传输实体/// </summary>public class MemoDto : BaseDto{private string title;/// <summary>/// 标题/// </summary>public string Title{get { return title; }set { title value; OnPropertyChanged();…

3.(Python数模)整数规划问题

Python解决整数规划问题 在实际生活中&#xff0c;线性规划中的变量不可能都是连续的值&#xff0c;比如不可能计算出0.5个人&#xff0c;0.5只牛羊&#xff0c;往往需要根据题目需要或者实际问题来调整决策变量的变量类型 Continuous’ 表示连续变量&#xff08;默认值&…

Java的23种设计模式

Java的23种设计模式 一、创建型设计模式1.单例模式 singleton1.1.静态属性单例模式1.2 静态属性变种1.3 基础的懒汉模式1.4 线程安全的懒加载单例1.5 线程安全的懒加载 单例-改进1.6 双重检查锁1.7 静态内部类1.8 枚举单例1.9 注册表单例 2.工厂方法模式 factory3.抽象工厂模式…

工具分享 | PDF文档解析工具PyMuPDF

1 需求描述 最近工作需要从PDF文档中按照章节解析出对应的文本和图片(后续可能还会有表格)&#xff0c;经过调研&#xff0c;找到了一个功能强大的解析工具MuPDF&#xff0c;对应的Python包是PyMuPDF。本篇博客记录使用它来实现具体功能。 官方文档&#xff1a;https://pymupd…

Git企业开发控制理论和实操-从入门到深入(四)|Git的远程操作|Gitee

前言 那么这里博主先安利一些干货满满的专栏了&#xff01; 首先是博主的高质量博客的汇总&#xff0c;这个专栏里面的博客&#xff0c;都是博主最最用心写的一部分&#xff0c;干货满满&#xff0c;希望对大家有帮助。 高质量博客汇总 然后就是博主最近最花时间的一个专栏…

ubuntu入门01——windows上直接部署linux(WSL)

win10安装参考如下教程&#xff1a; 旧版 WSL 的手动安装步骤 | Microsoft Learn 说明&#xff1a;该文档是我按如上教程安装使用Ubuntu写的回顾&#xff0c;家人们参考官方教程更妙。 1.启用适用于Linux的wundows子系统 2.启用虚拟机功能 dism.exe /online /enable-feat…

开源电子合同签署平台小程序源码 在线签署电子合同小程序源码 合同在线签署源码

聚合市场上各类电子合同解决方案商&#xff0c;你无需一个一个的对接电子合同厂商&#xff0c;费时&#xff0c;费力&#xff0c;因为这个工作我们已经做了适配&#xff0c;你只需要一个接口就能使用我们的所有服务商&#xff0c;同时你还可以享受我们的接口渠道价格。 Mini-C…

LeetCode 23 合并 K 个升序链表

LeetCode 23 合并 K 个升序链表 来源&#xff1a;力扣&#xff08;LeetCode&#xff09; 链接&#xff1a;https://leetcode.cn/problems/merge-k-sorted-lists/description/ 博主Github&#xff1a;https://github.com/GDUT-Rp/LeetCode 题目&#xff1a; 给你一个链表数组…

A 股个股资金流 API 数据接口

A 股个股资金流 API 数据接口 全量股票资金流数据&#xff0c;全量A股数据&#xff0c;最长30日历史数据 1. 产品功能 支持所有A股资金流数据查询&#xff1b;每日定时更新数据&#xff1b;支持多达 30 日历史数据查询&#xff1b;超高的查询效率&#xff0c;数据秒级返回&am…

【LeetCode75】第四十一题 二叉搜索树中的搜索

目录 题目&#xff1a; 示例&#xff1a; 分析&#xff1a; 代码&#xff1a; 题目&#xff1a; 示例&#xff1a; 分析&#xff1a; 题目给我们一个搜索二叉树&#xff0c;让我们找出节点值等于目标的节点并返回出去。 首先我们可以直接遍历整棵二叉树&#xff0c;找到值…

基于大语言模型知识问答应用落地实践 – 知识库构建(下)

上篇介绍了构建知识库的大体流程和一些优化经验细节&#xff0c;但并没有结合一个具体的场景给出更细节的实战经验以及相关的一些 benchmark 等&#xff0c;所以本文将会切入到一个具体场景进行讨论。 目标场景&#xff1a;对于 PubMed 医疗学术数据中的 1w 篇文章进行知识库构…

PO设计模式是selenium自动化测试中最佳的设计模式之一

Page Object Model&#xff1a;PO设计模式是selenium自动化测试中最佳的设计模式之一&#xff0c;主要体现在对界面交互细节的封装&#xff0c;也就是在实际测试中只关注业务流程就OK了传统的设计中&#xff0c;在新增测试用例之后&#xff0c;代码会有以下几个问题&#xff1a…

python爬虫实战(5)--获取小破站热榜

1. 分析地址 打开小破站热榜首页&#xff0c;查看响应找到如下接口地址 2. 编码 定义请求头 拿到标头 复制粘贴&#xff0c;处理成json 处理请求头代码如下: def format_headers_to_json():f open("data.txt", "r", encoding"utf-8") # 读…