当前位置: 首页 > article >正文

Unity中不使用场景和预制体保存关卡信息(附源文件)

在游戏中我们搭建关卡的时候一般有两种办法,一种是一个关卡创建一个场景,还有一种是将所有的关卡做成预制体,然后进入游戏加载对应的预制体。

但是上面两种方法或多或少会导致安装包体积增大,所有有什么更简便的方法吗?

其实关卡信息,无非就是一些场景物体的排列组合,我们只要把一个关卡的所有物体的位置,旋转,缩放用文本的形式记录下来,我们就能复刻出一个场景的原貌了。 

第一步:创建一个这样的场景(关卡1和关卡2是两个空对象,注意将坐标设为(0,0,0),不然保存的坐标会发生偏移,然后创建一些预制体放在Resources/Preform文件夹中,然后将预制体拖到场景中频成你想要的形状)

 

 第二步:创建一个空对象同样把坐标设为(0,0,0),编写HighSave脚本,并将脚本拖到这个空对象上

脚本: 

using System.IO;
using UnityEngine;

public class HighSave : MonoBehaviour
{
    public string levelName;
    public GameObject levelonj;
    void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            for (int i = 0; i < levelonj.transform.childCount; i++)
            {
                Transform childTransform = levelonj.transform.GetChild(i);
                Debug.Log(childTransform.name + " : " + childTransform.position + " : " + childTransform.rotation + " : " + childTransform.localScale + "\n");
            }
        }
        if (Input.GetKeyDown(KeyCode.A))
        {
            string content = null;
            string filePath = Application.persistentDataPath + levelonj.gameObject.name + ".txt";
            for (int i = 0; i < levelonj.transform.childCount; i++)
            {
                Transform childTransform = levelonj.transform.GetChild(i);
                content += childTransform.name + ":" + childTransform.position + ":" + childTransform.rotation + ":" + childTransform.localScale + "\n";
            }
            File.WriteAllText(filePath, content);
            Debug.Log("数据已保存");
        }

        if (Input.GetKeyDown(KeyCode.S))
        {
            string content = null;
            string filePath = null;

            if (levelName != null)
            {
                filePath = Application.persistentDataPath + levelName + ".txt";
            }
            else
            {
                Debug.Log("关卡名称为空");
                return;
            }

            if (!File.Exists(filePath))
            {
                Debug.Log("文件不存在");
                return;
            }

            content = File.ReadAllText(filePath);
            string[] lines = content.Split('\n');
            for (int i = 0; i < lines.Length - 1; i++)
            {
                string[] parts = lines[i].Split(':');
                if (parts.Length < 4)
                {
                    Debug.LogWarning($"格式不正确: {lines[i]}");
                    continue;
                }

                string objname = parts[0];
                string positionString = parts[1];
                string rotationString = parts[2];
                string scaleString = parts[3];

                GameObject obj = Resources.Load<GameObject>("Preform/" + objname);
                if (obj == null)
                {
                    Debug.LogWarning($"无法加载对象: {objname}");
                    continue;
                }

                GameObject instantiatedObj = Instantiate(obj, transform);
                Transform instantiatedTransform = instantiatedObj.transform;

                // 解析位置字符串
                positionString = positionString.Trim('(', ')'); // 去掉括号
                string[] positionCoordinates = positionString.Split(',');
                Vector3 position = new Vector3(
                    float.Parse(positionCoordinates[0].Trim()), // 解析 x 坐标
                    float.Parse(positionCoordinates[1].Trim()), // 解析 y 坐标
                    float.Parse(positionCoordinates[2].Trim())  // 解析 z 坐标
                );

                // 解析旋转字符串
                rotationString = rotationString.Trim('(', ')'); // 去掉括号
                string[] rotationCoordinates = rotationString.Split(',');
                Quaternion rotation = new Quaternion(
                    float.Parse(rotationCoordinates[0].Trim()), // 解析 x 坐标
                    float.Parse(rotationCoordinates[1].Trim()), // 解析 y 坐标
                    float.Parse(rotationCoordinates[2].Trim()), // 解析 z 坐标
                    float.Parse(rotationCoordinates[3].Trim())  // 解析 w 坐标
                );

                // 解析缩放字符串
                scaleString = scaleString.Trim('(', ')'); // 去掉括号
                string[] scaleCoordinates = scaleString.Split(',');
                Vector3 scale = new Vector3(
                    float.Parse(scaleCoordinates[0].Trim()), // 解析 x 坐标
                    float.Parse(scaleCoordinates[1].Trim()), // 解析 y 坐标
                    float.Parse(scaleCoordinates[2].Trim())  // 解析 z 坐标
                );

                instantiatedTransform.position = position; // 设置位置
                instantiatedTransform.rotation = rotation; // 设置旋转
                instantiatedTransform.localScale = scale; // 设置缩放

                Debug.Log(objname + " : " + position + " : " + rotation + " : " + scale);
            }
        }
    }
}

参数说明

 

第三步: 运行游戏,生成对应的关卡文本

先后将关卡1和关卡2拖到对应的位置然后按下A,就会看到打印出了保存成功就说明OK了。

 然后在C:\Users\用户名\AppData\LocalLow\DefaultCompany。这个文件夹的路径下找到保存的关卡信息

 可以看到数据通过文本的信息保存了下来。

第4步:将关卡1和关卡2删掉,然后运行游戏读取关卡(填写你需要读取的关卡名字,必须是之前保存了的),运行游戏按下S就能读取之前保存的关卡数据了

 注意事项:

1:关卡的中的所有物体必须要有对应的预制体,或者由预制体变换得来,不然加载的时候会报错,最好是把所有预制体做好了再拖动搭建关卡。

2.Resources其实也挺占用资源的,实际中可以把预制体改为AB包加载。

3.这里是将生成的文本保存在了本地,然后加载的时候也是读取的本地文本,这样在别人电脑上就不好使了,可以将生成好的文本也做成AB包之后通过AB包加载。

项目源文件

https://github.com/laozhupeiqia/HighSave.git 

如果这篇文章对你有帮助欢迎点赞支持哦。

 


http://www.kler.cn/a/511500.html

相关文章:

  • Java基础——概念和常识(语言特点、JVM、JDK、JRE、AOT/JIT等介绍)
  • CSS 合法颜色值
  • Spring Boot + Apache POI 实现 Excel 导出:BOM物料清单生成器(支持中文文件名、样式美化、数据合并)
  • 二进制/源码编译安装mysql 8.0
  • LabVIEW 蔬菜精密播种监测系统
  • TiDB 和 MySQL 的关系:这两者到底有什么不同和联系?
  • Gitblit 一些使用说明记录
  • 【React】静态组件动态组件
  • Jetpack 介绍
  • 删除字符串中的所有相邻重复项(力扣1047)
  • 怎么投稿各大媒体网站?如何快速辨别一家媒体是否适合自己?
  • 2025年01月17日Github流行趋势
  • 资源管理模块集成Spring Cache
  • 【Linux系统编程】—— 深度解析进程等待与终止:系统高效运行的关键
  • TCP状态转移图详解
  • 【数据结构-堆】【hard】力扣502. IPO
  • 【opencv】第10章 角点检测
  • Kinova仿生机械臂Gen3搭载BOTA 力矩传感器SeneOne:彰显机器人触觉 AI 与六维力传感的融合力量
  • StarRocks 怎么让特定的SQL路由到FE master节点的
  • 推荐sdkman管理sdk和jdk
  • Java 基于 SpringBoot+Vue 的停车场管理系统(附源码,部署,文档)
  • 神经网络常见面试题
  • MySQL 主从复制原理及其工作过程的配置
  • Flowable 管理各业务流程:流程设计器 (获取流程模型 XML)、流程部署、启动流程、流程审批、流程挂起和激活、任务分配
  • 本地部署 Calcium 网页计算器并实现外部访问
  • MySQL数据库的数据文件保存在哪?MySQL数据存在哪里