2021.3.12更新tips:今天发现使用LitJson存字典的key值只能使用string型,想起来这边我还没有试过不同key类型,就测试了一波,发现这边就算把key值设为string,免去内部序列化的类型转化,还是不能被写入,看来序列化这一趴的坑点挺多的,mark一下准备找时间深入研究一下序列化方面的源码。
2021.3.4更新,之前研究了忘记同步上来了,上结论,不可以用dictionary以及list<list<>>这种嵌套的结构,不然不会被unity的setdirty方法所保存,但是可以使用系列化的类的嵌套,类中有单层的List<>是可以被序列化的。
2021.1.25更新,加入退出窗口时保存功能。

先说一下这个工具可以干神马呢~~~它可以让策划愉快的对游戏数据边调试边修改,方便他们调整数据用滴。也可以作为工程的自定义数据的存档,它会将数据存到.asset文件里面。
首先是自定义数据的数据结构,这里全部都可以自定义,但是类型最好用基础类型,数组或者list,因为本人踩了Dictionary的坑,貌似是无法识别到dictionary的改变导致不能储存,不知道有木有大神指点迷津= =
然后是最清晰明了的上图(如果偷懒不想改的话就按这个位置好了),灵活修改的部分已经在代码中标记出来了,直接删掉写入自己需要的排版和数据就完事了:
1.在resources下创建文件夹:
2.右键创建.asset文件:

3.不想找的话可以直接在edit栏找到对应的文件:

4.然后就可以添加对应的新信息:

5.点击对应的数据就可以在弹出的窗口中进行数据的修改了,新窗口就可以免得策划点来点去点没了。。。

窗口样式自己按需排版就完事了
修改数据之后直接就可以实时保存,也写了提示窗口,避免点错带来删库跑路的后果~接下来就是代码了。
LevelData:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
[CreateAssetMenu(fileName = "GameDataAsset", menuName = "Creat GameData Asset")]
public class LevelData : ScriptableObject
{[Header("关卡字典")][HideInInspector][SerializeField] public List<InsideData> preinstallLevels;/// <summary>/// 找数据/// </summary>/// <param name="id">关卡id</param>/// <param name="data">数据</param>/// <returns></returns>public static bool FindData(int id,out InsideData data){LevelData datas = Resources.Load("LevelDataAssest/LevelData") as LevelData;if (datas.preinstallLevels == null || datas.preinstallLevels.Count < 1){//Debug.LogError("没数据");data = null;return false;}foreach (var v in datas.preinstallLevels){if(v.levelID == id){data = v;return true;}}//Debug.LogError("没这个ID的数据");data = null;return false;}}
/// <summary>
/// 关卡信息,根据需要修改
/// ps.注意不可以用dictionary以及list<list<>>这种嵌套的结构,不然不会被unity的setdirty方法所保存,可以用序列化过的类嵌套
/// </summary>
[System.Serializable]
public class InsideData {[SerializeField] public int levelID;//章节ID//这里写入需要存的数据结构
}

然后是放在Editor下的LevelDataEditor:

using System.Collections;
using System.Collections.Generic;
using UnityEditor;
using UnityEditorInternal;
using UnityEngine;
[CustomEditor(typeof(LevelData))]
public class LevelDataEditor : Editor
{public LevelData data;public LevelDataWindow addWindow;SerializedProperty dataProperty;ReorderableList nowList;private void OnEnable(){data = target as LevelData;if (data.preinstallLevels == null || data.preinstallLevels.Count < 1){//Debug.Log("没数据");}dataProperty = serializedObject.FindProperty("preinstallLevels");nowList = new ReorderableList(serializedObject, dataProperty, false, true, true, true);nowList.drawElementCallback = (Rect rect, int index, bool isActive, bool isFocused) =>{var element = dataProperty.GetArrayElementAtIndex(index);rect.height -= 4;rect.y += 2;GUIContent content = new GUIContent();content.text = "Level" + (index + 1);EditorGUI.PropertyField(rect, element, content);};nowList.onAddCallback = (ReorderableList l) =>{if (addWindow != null)addWindow.Close();addWindow = (LevelDataWindow)EditorWindow.GetWindow(typeof(LevelDataWindow), true, "LevelDataWindow");addWindow.minSize = new Vector2(200, 800);addWindow.Init(this);addWindow.Show();};nowList.onRemoveCallback = (ReorderableList l) =>{if (addWindow != null)addWindow.Close();if (EditorUtility.DisplayDialog("删除关卡信息", "你想删除选中的关卡信息吗?", "是", "否")){data.preinstallLevels.RemoveAt(l.index);}};nowList.drawHeaderCallback = (rect) =>EditorGUI.LabelField(rect, "关卡数据");nowList.onSelectCallback = (ReorderableList l) =>{if (addWindow != null)addWindow.Close();addWindow = (LevelDataWindow)EditorWindow.GetWindow(typeof(LevelDataWindow), true, "LevelDataWindow");addWindow.minSize = new Vector2(200, 800);addWindow.Init(this, data.preinstallLevels[l.index]);addWindow.Show();};}public override void OnInspectorGUI(){base.OnInspectorGUI();if (GUILayout.Button("新增关卡信息", GUILayout.Height(25))){if (addWindow != null)addWindow.Close();addWindow = (LevelDataWindow)EditorWindow.GetWindow(typeof(LevelDataWindow), true, "LevelDataWindow");addWindow.minSize = new Vector2(200, 800);addWindow.Init(this);addWindow.Show();}if (data.preinstallLevels == null || data.preinstallLevels.Count < 1){EditorGUILayout.HelpBox("没有数据", MessageType.Warning);return;}nowList.DoLayoutList();if (GUILayout.Button("清除所有信息", GUILayout.Height(25))){if (EditorUtility.DisplayDialog("删除关卡信息", "你想删除所有的关卡信息吗?", "是", "否")){data.preinstallLevels.Clear();Save();}           }serializedObject.Update();if (GUI.changed){Save();}}public void Save(){EditorUtility.SetDirty(target);serializedObject.ApplyModifiedProperties();EditorUtility.SetDirty(data);}[MenuItem("Edit/Level data")]private static void SelectLevelData(){Selection.activeObject = Resources.Load("LevelDataAssest/LevelData") as LevelData;}
}

以及修改数据的弹窗:LevelDataWindow

using System.Collections;
using System.Collections.Generic;
using UnityEditor;
using UnityEngine;public class LevelDataWindow : EditorWindow
{private LevelData datas;//存档数据集private InsideData data;//新加的数据private LevelDataEditor now;private void OnEnable(){datas = Resources.Load("LevelDataAssest/LevelData") as LevelData;minSize = new Vector2(0, 700f);        }private void OnGUI(){//这里加入GUI排版以及数据赋值if (GUI.changed){if (IsAlreadyHaveID(data.levelID)){for(int i = 0; i < datas.preinstallLevels.Count; i++){if (datas.preinstallLevels[i].levelID == data.levelID){datas.preinstallLevels[i] = data;}}}else{datas.preinstallLevels.Add(data);}now.Save();Undo.RecordObject(datas, "保存数据");EditorUtility.SetDirty(datas);}}private void OnDisable(){now.Save();Undo.RecordObject(datas, "保存数据");EditorUtility.SetDirty(datas);AssetDatabase.SaveAssets();}public void Init(LevelDataEditor now,InsideData data = null){this.now = now;if (data != null){this.data = data;}      }public bool IsAlreadyHaveID(int id){foreach(var v in datas.preinstallLevels){if(id == v.levelID){return true;}}return false;}
}

最后再附上一个实用滴样式查找工具,同样是放在Editor下的GUIStyleViewer:

using UnityEngine;
using UnityEditor;public class GUIStyleViewer : EditorWindow {private Vector2 scrollVector2 = Vector2.zero;private string search = "";[MenuItem("Tools/GUIStyle查看器")]public static void InitWindow(){EditorWindow.GetWindow(typeof(GUIStyleViewer));}void OnGUI(){GUILayout.BeginHorizontal("HelpBox");GUILayout.Space(30);search = EditorGUILayout.TextField("", search, "SearchTextField", GUILayout.MaxWidth(position.x / 3));GUILayout.Label("", "SearchCancelButtonEmpty");GUILayout.EndHorizontal();scrollVector2 = GUILayout.BeginScrollView(scrollVector2);foreach (GUIStyle style in GUI.skin.customStyles){if (style.name.ToLower().Contains(search.ToLower())){DrawStyleItem(style);}}GUILayout.EndScrollView();}void DrawStyleItem(GUIStyle style){GUILayout.BeginHorizontal("box");GUILayout.Space(40);EditorGUILayout.SelectableLabel(style.name);GUILayout.FlexibleSpace();EditorGUILayout.SelectableLabel(style.name, style);GUILayout.Space(40);EditorGUILayout.SelectableLabel("", style, GUILayout.Height(40), GUILayout.Width(40));GUILayout.Space(50);if (GUILayout.Button("复制GUIStyle名字")){TextEditor textEditor = new TextEditor();textEditor.text = style.name;textEditor.OnFocus();textEditor.Copy();}GUILayout.EndHorizontal();GUILayout.Space(10);}
}

冲~

Unity自定义信息储存工具(存档工具,可按照需求拓展为关卡编辑器),编辑器拓展样式查找工具相关推荐

  1. 工具推荐:ST-MCU-FINDER(ST意法半导体MCU选型,产品查找工具)

    官网链接:https://www.st.com/zh/development-tools/st-mcu-finder-pc.html 该工具可以根据产品的需求来选择ST的芯片,例如开发某个产品的基本要 ...

  2. Unity 自定义Editor 地图编辑工具_使用说明

    Unity 自定义Editor 地图编辑工具: 自定义六边形网格数据并生成平面地图 1.打开自定义编辑编辑器 2.设置参数生成网格: 设置参数,点击Create Grid 2.编辑网格类型: !!!S ...

  3. Unity自定义工具之引用查找

    目录 前言: 准备 知识点 完整代码 效果 前言: 我们在游戏开发过程中,有时会需要查找一个资源的所有引用的地方,比如查找一个小prefab在那些大prefabs中使用,或者某个建筑物在那些场景中使用 ...

  4. Unity编译器拓展学习总结(一):常用工具API

    Unity编译器拓展学习总结(一):常用工具API 文章目录 Unity编译器拓展学习总结(一):常用工具API 前言 一.常用工具API 1.PrefabUtility 2.AssetDatabas ...

  5. 常用工具:IDEA、vs code、Navicat、Postman、HBuilderX、微信开发者工具

    IDEA 1. 更好的项目管理方式 IDEA中的Project类似于eclipse中的workspace,而Module类似于eclipse中的project.这里可不仅仅是名称简单更改了一下,IDE ...

  6. Unity自定义UI组件(七)渐变工具、渐变色图片、渐变遮罩

    欢迎阅读Unity自定义UI组件(七)渐变工具.渐变色图片.渐变遮罩 前言 在Unity中UGUI只为我们提供了最为基础的Image和RawImage两种可展示图片的组件,但是这两种组件要展示一些特殊 ...

  7. Unity自定义UI组件(六)日历、日期拾取器

    前言 考虑到工业项目中可能会利用到类似日历的工具,就比如选取某个时间节点,所以我结合UGUI源码开发了日历工具和日期拾取器工具,简单易用,接口齐全,可中文显示,外观可自定义.只需要导入脚本,即可在Hi ...

  8. 网络拓扑图画图工具_写了100多篇原创文章,我常用的在线工具网站推荐给大家!...

    不知不觉写博客已经一年多了,累计写了100多篇原创文章,今天给大家分享下我经常使用的在线工具网站,希望对大家有所帮助! Markdown Nice 支持自定义样式的在线Markdown编辑器,编辑完成 ...

  9. 开源linux 二进制工具,又一款开源好物:逐字节分析的二进制数据分析工具bitinsight...

    项目名称:bitinsight 项目作者:compilelife 开源许可协议:GPL-3.0 项目地址:https://gitee.com/compilelife/bitinsight 项目简介 b ...

最新文章

  1. java http连接_Java中通过方法创建一个http连接并请求(服务器间进行通信)
  2. liferay 如何在页面实现添加多个portlet
  3. springboot报错---@RunWith(SpringRunner.class)
  4. 玩C一定用得到的19款Java开源Web爬虫
  5. css摇曳的_HTML5+CSS3实现树被风吹动摇晃
  6. linux screen 命令是 ssh 的有效补充
  7. Spring : @EnableAutoConfiguration注解
  8. ----函数句柄/时间表
  9. 除了工作怎么交朋友_老梁:交朋友要交比自己强的,结交和自己相似的人,不如没有朋友...
  10. PLSql不用安装Oracle客户端,实现远程连接
  11. 证件阅读设备一般可以识别哪些证件
  12. 1、AD创建模板和导入
  13. 一种深度学习方法---迁移学习
  14. 离线使用yum·无法使用yum的情况下安装软件·最简单的方法
  15. php如何做left,php函数substr实现asp中left和right应用
  16. w10桌面计算机图标箭头去除,如何让win10桌面图标箭头取消除 笔记本电脑去掉快捷小箭头软件-♚付涛纪实阁♚...
  17. actions vuex 请求_vue中vuex的actions里面请求接口,提交给mutations报错
  18. 使用react制作点赞组件
  19. ps 制作虚线框背景
  20. easyrecovery2023最新版本电脑数据恢复软件特点介绍

热门文章

  1. foreign oracle,FOREIGN KEY 在ORACLE中的使用
  2. php下一页的代码,PHP简单实现上一页下一页功能示例
  3. java正则表达式基础 关于特殊字符、捕获组和非捕获匹配
  4. 高德免费基站定位(智能硬件定位)查询
  5. metasploit制作木马程序
  6. 自动新闻抓取系统-开发有感(转载)
  7. 全能PDF:Pdfium.Net SDK 2023-03-18 Crack
  8. 计算机论文图片大小,对一副大小为256*256的bmp格式256色的灰度图象进行霍夫曼和字典编码压缩处理...
  9. 第4节 批处理文件及示例
  10. css选择器获取文本,如何获取文本的CSS选择器