51Testing软件测试论坛

 找回密码
 (注-册)加入51Testing

QQ登录

只需一步,快速开始

微信登录,快人一步

手机号码,快捷登录

查看: 1329|回复: 1
打印 上一主题 下一主题

自定义Inspector检视面板

[复制链接]

该用户从未签到

跳转到指定楼层
1#
发表于 2018-4-17 14:04:23 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
Unity中的Inspector面板可以显示的属性包括以下两类:
(1)C#以及Unity提供的基础类型;
(2)自定义类型,并使用[System.Serializable]关键字序列化,比如:
[System.Serializable]
  1. public class TestClass
  2. {
  3.     public Vector3 vec = Vector3.zero;
  4.     public Color clr = Color.green;
  5. }
  6.   也可以使用[System.NonSerialized]标记不需要显示的属性,比如:

  7. public class TestClass
  8. {
  9.     [System.NonSerialized]
  10.     public Vector3 vec = Vector3.zero;
  11. }
复制代码

  有的时候对于U3D默认的Inspector不能满足需求,则可以对特定类型的Inspector面板进行自定义:编写
一个对应的Editor类,然后重写其OnInspector方法,比如我们有如下类型:

复制代码
  1. using UnityEngine;
  2. using System.Collections;

  3. [System.Serializable]
  4. public class TestClass
  5. {
  6.     public Vector3 vec = Vector3.zero;
  7.     [System.NonSerialized]
  8.     public Color clr = Color.green;
  9. }

  10. [ExecuteInEditMode()]
  11. [RequireComponent(typeof(TestComponent))]
  12. public class TestInspector : MonoBehaviour
  13. {
  14.     public Vector3 lookAtPoint = Vector3.zero;
  15.     public Vector3 pos = Vector3.zero;
  16.     public TestClass testObj = new TestClass();

  17.     void Update()
  18.     {
  19.         transform.LookAt(lookAtPoint);
  20.         transform.position = pos;
  21.     }
  22. }
复制代码

复制代码
  然后在Editor目录下添加如下脚本:

复制代码
  1. using UnityEngine;
  2. using UnityEditor;
  3. using System.Collections;

  4. [CustomEditor(typeof(TestInspector))]
  5. public class TestInspectorEditor : Editor
  6. {
  7.     private SerializedObject obj;
  8.     private SerializedProperty lookAtPoint;
  9.     private SerializedProperty pos;
  10.     private SerializedProperty testObj;

  11.     // 添加TestInspector组件的GameObject被选中时触发该函数
  12.     void OnEnable()
  13.     {
  14.         obj = new SerializedObject(target);
  15.         lookAtPoint = obj.FindProperty("lookAtPoint");
  16.         pos = obj.FindProperty("pos");
  17.         testObj = obj.FindProperty("testObj");
  18.     }

  19.     // 重写Inspector检视面板
  20.     public override void OnInspectorGUI()
  21.     {
  22.         obj.Update();

  23.         EditorGUILayout.PropertyField(lookAtPoint);
  24.         EditorGUILayout.PropertyField(pos);
  25.         EditorGUILayout.PropertyField(testObj, true);   // 第二个参数表示有子节点需要显示

  26.         obj.ApplyModifiedProperties();
  27.     }

  28. }
复制代码

复制代码
  在OnInspector函数中就可以实现你想要的效果。

  上面的代码中有几点需要注意:

  (1)[ExecuteInEditMode()]这个函数可以使代码在编辑模式下运行,不需要运行游戏;

  (2)TestInspectorEditor类必须继承自Editor,CustomEditor告诉U3D哪个组建类型需要自定义,OnI
nspectorGUI在显示组件的Inspector面板时调用;

  (3)SerializedObject序列化物体、SerializedProperty序列化属性和Editor这三者一起使用,用来访问
和更新组件的属性,SeriailzedProperty能够以通用的方式访问所有的基础类型,包括对数组的控制等;

  (4)可以在OnInspectorGUI中调用DrawDefaultInspector函数用来显示默认的监事面板内容;

  (5)EditorGUILayout.PropertyField(testObj, true);如果该类型有子节点,第二个参数需要设置为true
才能正确的展开;

   (6)[HideInInspector]也可用于隐藏属性显示。

******************************************************************************************

  除了自定义Inspector检视面板,我们还可以类似的方法自定义场景视图中对物体的控制,方法是重定
义Editor的OnSceneGUI()函数,比如:

复制代码
  1. using UnityEngine;
  2. using UnityEditor;
  3. using System.Collections;

  4. [CustomEditor(typeof(TestInspector))]
  5. public class TestInspectorEditor : Editor
  6. {

  7.     private SerializedObject obj;
  8.     private SerializedProperty lookAtPoint;
  9.     private SerializedProperty pos;
  10.     private SerializedProperty testObj;

  11.     // 添加TestInspector组件的GameObject被选中时触发该函数
  12.     void OnEnable()
  13.     {
  14.         obj = new SerializedObject(target);
  15.         lookAtPoint = obj.FindProperty("lookAtPoint");
  16.         pos = obj.FindProperty("pos");
  17.         testObj = obj.FindProperty("testObj");
  18.     }

  19.     // 重写Inspector检视面板
  20.     public override void OnInspectorGUI()
  21.     {
  22.         obj.Update();

  23.         EditorGUILayout.PropertyField(lookAtPoint);
  24.         EditorGUILayout.PropertyField(pos);
  25.         EditorGUILayout.PropertyField(testObj, true);   // 第二个参数表示有子节点需要显示

  26.         obj.ApplyModifiedProperties();
  27.     }

  28.     void OnSceneGUI()
  29.     {
  30.         // 绘制一条由target到世界坐标原点的直线,颜色为黄色
  31.         Handles.color = Color.yellow;
  32.         Handles.DrawLine((target as TestInspector).transform.position, Vector3.zero);
  33.         // 创建一个位置控制柄
  34.         Handles.PositionHandle(Vector3.zero, Quaternion.identity);
  35.         // 创建一个滑动控制柄,可以沿某个方向滑动target
  36.         Handles.Slider((target as TestInspector).transform.position, Vector3.zero);

  37.         (target as TestInspector).transform.position = Handles.FreeMoveHandle((target as TestInspector).transform.position, Quaternion.identity, 2.0f, Vector3.zero, Handles.DrawRectangle);
  38.       
  39.         if (GUI.changed)
  40.         {
  41.             EditorUtility.SetDirty(target);
  42.         }
  43.     }

  44. }
复制代码


分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏
回复

使用道具 举报

本版积分规则

关闭

站长推荐上一条 /1 下一条

小黑屋|手机版|Archiver|51Testing软件测试网 ( 沪ICP备05003035号 关于我们

GMT+8, 2024-11-17 22:16 , Processed in 0.068542 second(s), 22 queries .

Powered by Discuz! X3.2

© 2001-2024 Comsenz Inc.

快速回复 返回顶部 返回列表