美文网首页
CustomEditor+ScripableObject 简单用

CustomEditor+ScripableObject 简单用

作者: sky嗨嗨 | 来源:发表于2017-10-17 06:53 被阅读0次

    写在前面:

    看了一整天,算是明白了点,记录一下,要是不知道怎么入门可以看一下,希望能帮到您:)

    Ps:本文一律采用c#进行讲解

    用途

    自定义inspector(监视器)面板

    举个例子,你在ScriptableObejct里声明了一个string类型变量,利用CreateInstance()实例化出来几个.asset实例文件(这个步骤没接触过之后也会说)。这个string太长了,一个默认的EditorGUILayout.TextField里看不到全部内容很不爽,这时候你就需要利用CustomEditor自定义一个界面来重写OnInspectorGUI()

    图一。默认的ScripableObject实例出的.asset文件的inspector界面

    创建ScriptableObject

    新建一个.cs文件,命名成类名后面加上Object(当然不加也行只是个规范),如WeaponObject

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    
    [System.Serializable]
    public class WeaponObject : ScriptableObject {
        public string weaponName = "Weapon Name Here";
        public int cost;
        public string description;
        public int damage;
    }
    

    保存再新建一个.cs文件,命名成之前那个类的名字再在开头加一个"Make",比如MakeWeaponObject,又要说了,只是个命名习惯,方便管理。

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    using UnityEditor;
    
    public class MakeWeaponObject : MonoBehaviour {
        //在顶部MenuItem(菜单)/Assets/Create/New Weapon目录下新建一个按钮,点击就执行下面的方法
        [MenuItem("Assets/Create/New Weapon")]
        public static void Creat() {
            //新建一个weaponObject对象并实例它
            WeaponObject asset = ScriptableObject.CreateInstance<WeaponObject>();
            //将实例出来的对象做成一个.asset文件并存放在以下目录(可自定义)
            AssetDatabase.CreateAsset(asset, "Assets/WeaponShop/WeaponObjects/New Weapon.asset");
            //让unity自己的文件管理系统添加这个对象到目录下,貌似是为了生成一个meta文件
            AssetDatabase.SaveAssets();
            //接下来的写不写不影响,意思解释下就是让系统Focus到刚刚创建出来的文件
            EditorUtility.FocusProjectWindow();
            Selection.activeObject = asset;
        }
    }
    

    回到unity在顶部菜单找到assets/create/new weapon。新建出来
    到这里我们已经能看到图一。的效果了

    吃完饭再写

    添加WeaponObjectEditor类

    接下来需要写一个Editor类来自定义inspector面板

    包含事项:
    • 引用UnityEditor
    • 继承自Editor
    主要组成
    • OnEnable()
    • OnIspectorGUI()
    • 因为是入门教程写的先简单些,以后再更WWW
    好了开始写我们最后一个脚本

    写完就能吃饭了:D

    首先,让我们建立一个cs文件,命名为WeaponObjectEditor,不用说这命名方式只是习惯

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    using UnityEditor;
    //定义好给哪一类对象的视窗使用
    [CustomEditor(typeof(WeaponObject))]
    public class WeaponObjectEditor : Editor {
    
        //指定类型对象的inspector被调用时执行
        public void OnEnable() {
            
        }
    
        //重写指定类型对象的inspector视窗,在这里加入各种EditorGUI生成方法
        public override void OnInspectorGUI() {
            
        }
    }
    

    接着给每个板块填入想要实现的内容

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    using UnityEditor;
    //定义好给哪一类对象的视窗使用
    [CustomEditor(typeof(WeaponObject))]
    public class WeaponObjectEditor : Editor {
    
        WeaponObject w;
    
        //指定类型对象的inspector被调用时执行
        public void OnEnable() {
            w = (WeaponObject)target;
        }
    
        //重写指定类型对象的inspector视窗,在这里加入各种EditorGUI生成方法
        public override void OnInspectorGUI() {
            #region WeaponObject中声明的变量
            //需要修改的都写进这个方法,要不然在inspector看不见也就等于白声明了
            w.weaponName = EditorGUILayout.TextField("Weapon Name", w.weaponName);
            w.cost = EditorGUILayout.IntField("Cost", w.cost);
            w.damage = EditorGUILayout.IntSlider(new GUIContent("Damage"),w.damage,0,100);
    
            //EditorGUI.TagField(new Rect(20, 200, 50, 25), "Description");
            w.description = EditorGUILayout.TextArea("Description",w.description);
    
            #endregion
    
            #region Extra
    
            EditorGUILayout.HelpBox("Error", MessageType.Error);
            EditorGUILayout.HelpBox("Info", MessageType.Info);
            EditorGUILayout.HelpBox("None", MessageType.None);
            EditorGUILayout.HelpBox("Warning", MessageType.Warning);
    
            #endregion
    
        }
    }
    

    照理说这个教程就该结束了,然而回到unity一看textarea有神秘错误:

    未知错误我也很无奈啊评论区请大胆骂我然后告诉我原因
    无奈只能用了个小trick,把这个area设置成非layout也就是EditorGUI.TextArea()
    代码如下:
    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    using UnityEditor;
    //定义好给哪一类对象的视窗使用
    [CustomEditor(typeof(WeaponObject))]
    public class WeaponObjectEditor : Editor {
    
        WeaponObject w;
        static bool showObjectEditor = false;
    
        //指定类型对象的inspector被调用时执行
        public void OnEnable() {
            w = (WeaponObject)target;
        }
    
        //重写指定类型对象的inspector视窗,在这里加入各种EditorGUI生成方法
        public override void OnInspectorGUI() {
            #region WeaponObject中声明的变量
    
            //需要修改的都写进这个方法,要不然在inspector看不见也就等于白声明了
            w.weaponName = EditorGUILayout.TextField("Weapon Name", w.weaponName);
            w.cost = EditorGUILayout.IntField("Cost", w.cost);
            w.damage = EditorGUILayout.IntSlider(new GUIContent("Damage"),w.damage,0,100);
    
            showObjectEditor = EditorGUILayout.Foldout(showObjectEditor, "Description");
            if (showObjectEditor) {
                w.description = EditorGUI.TextArea(new Rect(20f, 220f, 200f, 200f), w.description);
                EditorGUILayout.HelpBox("Write Description in the area down below", MessageType.Info);
            } else {
                EditorGUILayout.HelpBox("Unfold this to write Description", MessageType.Warning);            
            }
    
            #endregion
        }
    }
    

    总结

    • 本教程只是入门教程,如有兴趣请去官网ref找相关文档说明。
    • 最后fold那个只是觉得这个功能很有用,比如策划要写每一个weapon的信息,folders提高了对策划友好度,所以其实并没有必要。。(逃
    • 冬天就要来了,卡村的朋友注意保暖~

    2018 03 08

    相关文章

      网友评论

          本文标题:CustomEditor+ScripableObject 简单用

          本文链接:https://www.haomeiwen.com/subject/ivsruxtx.html