Unity 6.3
0 онлайн 38 гостей 3 в системе
Вход

Создать пользовательский Inspector

Версия: 2022.3+

Хотя для ваших MonoBehaviour и ScriptableObject есть инспектор по умолчанию, вы можете написать для них собственный инспектор. Пользовательские инспекторы работают только с типами, производными от MonoBehaviour или ScriptableObject. Если у вас обычный сериализуемый класс (например, используемый внутри массива или списка), применяйте вместо этого пользовательский отрисовщик свойств. Дополнительные сведения см. в Создание пользовательского ящика свойств. Пользовательские Inspector может помочь вам сделать следующее:

  • Создание более удобного для пользователя представления свойств скрипта.
  • Организация и группировка свойств.
  • Показать или скрыть разделы UI в зависимости от выбора пользователя.
  • Предоставление дополнительных сведений о значении отдельных параметров и свойств.

Примерный обзор

В этом примере создаётся пользовательский инспектор для класса MonoBehaviour. Интерфейс строится и скриптами C#, и средствами UI Builder. В инспекторе также используется пользовательский отрисовщик свойств.

Настраиваемый Inspector отображает свойства Car класс, включая марку, год выпуска, цвет и список шин. Инспектор использует элемент PropertyField, чтобы отобразить свойства Car класс и пользовательский отрисовщик свойств, отображающий свойства Tire class.

Вы можете найти завершенные файлы, созданные этим примером, в хранилище GitHub.

Предварительные условия

Это руководство предназначено для разработчиков, знакомых со скриптами Unity Editor, UI Toolkit и C#. Перед началом работы ознакомьтесь со следующим:

Создать новый MonoBehaviour

Чтобы создать пользовательский инспектор, сначала объявите собственный класс, наследующий MonoBehaviour. Пользовательский класс представляет простой автомобиль с несколькими свойствами.

  1. Создайте проект в Unity с любым шаблоном.

  2. В окне Project создайте папку create-a-custom-inspector для хранения всех ваших файлов.

  3. Создайте скрипт C# с именем Car.cs со следующим содержанием:

    using UnityEngine;
    
    public class Car : MonoBehaviour
    {
         public string make = "Toyota";
         public int yearBuilt = 1980;
         public Color color = Color.black;
    }
    
  4. Создайте новый GameObject в сцене и прикрепите к нему компонент скрипта Car.

    По умолчанию Inspector для объекта Car
    По умолчанию Inspector для объекта Car

Создание пользовательского скрипта Inspector

Чтобы создать пользовательский инспектор для любого сериализованного объекта, объявите класс, производный от Editor базовый класс и добавьте CustomEditor атрибут к нему. Этот атрибут сообщает Unity, какой класс представляет данный пользовательский инспектор.

Примечание: Пользовательский скрипт Inspector должен находиться в папке Editor или определении сборки только для редактора. Это происходит потому, что пространство имен UnityEditor, которое необходимо для создания пользовательских инспекторов, недоступно за пределами этих областей. Если вы попытаетесь создать автономные сборки без соблюдения этого требования, процесс сборки завершится неудачей.

  1. Создайте папку с именем Editor внутри папки create-a-custom-inspector.

  2. Создайте скрипт C# с именем Car_Inspector.cs в папке Editor со следующим содержимым:

    using UnityEditor;
    using UnityEditor.UIElements;
    using UnityEngine.UIElements;
    
    [CustomEditor(typeof(Car))]
    public class Car_Inspector : Editor
    {
    }
    
  3. Выберите GameObject, к которому прикреплен компонент Car. По умолчанию отображается Inspector.

  4. Чтобы заменить по умолчанию Inspector, внутри Car_Inspector класс, добавьте следующий код, чтобы переопределить CreateInspectorGUI() и возвращает новый визуальный элемент, содержащий UI:

    public override VisualElement CreateInspectorGUI()
    {
         // Create a new VisualElement to be the root of our Inspector UI.
         VisualElement myInspector = new VisualElement();
    
         // Add a simple label.
         myInspector.Add(new Label("This is a custom Inspector"));
    
         // Return the finished Inspector UI.
         return myInspector;
    }
    
  5. Выберите GameObject, к которому прикреплен компонент Car. Inspector теперь отображает метку This is a custom Inspector вместо Inspector по умолчанию.

    Пользовательские Inspector с меткой
    Пользовательские Inspector с меткой

Создать пользовательский Inspector UI с UI Builder

Вы можете создать пользовательский Inspector UI с UI Builder, и использовать C# скрипт для загрузки и инстанции UI из UXML файла.

  1. Чтобы открыть UI Builder, выберите Окно > UI Toolkit > UI Builder.

  2. Выберите Файл > Новый, чтобы создать новое визуальное дерево ассетов.

    Пользовательские Inspector с меткой
    Пользовательские Inspector с меткой
  3. Чтобы включить элементы управления только для редактора в UI Builder, выберите <unsaved file>*.uxml в представлении Hierarchy, а затем установите флажок Создание расширения редактора.

    Пользовательские Inspector с меткой
    Пользовательские Inspector с меткой
  4. Перетащите контроль метки из Библиотека к Генеральной Ассамблее Hierarchy. Это добавляет управление меткой в визуальное дерево.

    Пользовательские Inspector с меткой
    Пользовательские Inspector с меткой
  5. В панели Inspector управления меткой обновите текст метки.

    Пользовательские Inspector с меткой
    Пользовательские Inspector с меткой
  6. Выберите Файл > Сохранить и сохранить визуальное дерево как Car_Inspector_UXML.uxml в папку Assets/create-a-custom-inspector.

Используйте UXML внутри пользовательского Inspector

Для использования файла UXML, созданного в вашем пользовательском Inspector, назначите этот файл пользовательскому Inspector, загрузите и клонируйте его в функции CreateInspectorGUI() и добавьте его в визуальное дерево. Для этого вы можете использовать методы CloneTree. Вы можете передать любой VisualElement в качестве параметра, чтобы он действовал как родитель для созданных элементов.

  1. В Car_Inspector.cs, создайте открытую переменную для VisualTreeAsset в вашем сценарии и назначить Car_Inspector_UXML.uxml к нему.

    public VisualTreeAsset inspectorUXML;
    
  2. Обновите метод CreateInspectorGUI(), чтобы загрузить файл UXML и клонировать его в визуальное дерево. Полученный файл Car_Inspector.cs выглядит следующим образом:

     using UnityEditor;
     using UnityEditor.UIElements;
     using UnityEngine.UIElements;
         
     [CustomEditor(typeof(Car))]
     public class Car_Inspector : Editor
     {
         public VisualTreeAsset inspectorUXML;
         public override VisualElement CreateInspectorGUI()
         {
              // Create a new VisualElement to be the root of our Inspector UI.
             VisualElement myInspector = new VisualElement();
         
             // Add a simple label.
             myInspector.Add(new Label("This is a custom Inspector"));
         
             // Load the UXML file and clone its tree into the inspector.
             if (inspectorUXML != null)
             {
                 VisualElement uxmlContent = inspectorUXML.CloneTree();
                 myInspector.Add(uxmlContent);
             }
         
             // Return the finished Inspector UI.
             return myInspector;
         }
     }
         
    
  3. В течение Inspector окно Car_Inspector.cs, назначить Car_Inspector_UXML.uxml файл к Inspector UXML поле.

  4. Выберите GameObject, к которому прикреплен компонент Car. Inspector для компонента Car теперь отображает две метки: одну через скрипт и одну через UI Builder/UXML.

    Пользовательские Inspector с двумя этикетками этикетки
    Пользовательские Inspector с двумя этикетками этикетки

Привязка текстового поля

Этот пользовательский Inspector отображает все свойства Car класс. Когда вы обновляете элементы управления интерфейса, значения внутри экземпляра Car класса меняются. Для этого добавьте элементы управления в визуальное дерево и привяжите их к отдельным свойствам класса.

Чтобы привязать контроллер к серийному свойству, назначьте это свойство в поле binding-path контроллера. При создании настраиваемого инспектора привязка выполняется автоматически. CreateInspectorGUI() выполняет неявную привязку после возвращения визуального дерева. Дополнительные сведения см. в разделе Привязка данных SerializedObject.

  1. Дважды щелкните Car_Inspector_UXML.uxml, чтобы открыть его в UI Builder.

  2. Добавить контроль TextField.

    Добавить текстовое поле в UI
    Добавить текстовое поле в UI
  3. В панели Inspector TextField установите текст метки на Make of the car.

  4. Установите путь привязки в make.

    Привязка свойства к элементу управления в UI Builder
    Привязка свойства к элементу управления в UI Builder
  5. Добавление класса стиля unity-base-field__aligned к Генеральной Ассамблее Список классов стилей текстовое поле выравнивается с другими полями в таблице. Inspector окно. Для получения дополнительной информации см. BaseField.

    Add a style class to the text field
    Добавление стилевого класса в текстовое поле
  6. В UI Builder выберите Файл > Сохранить.

  7. Выберите GameObject, который имеет Car Inspector для подключения к Car компонент теперь отображает Make of the car текстовое поле. Текстовое поле привязано к make свойства Car class.

    Настраиваемый Inspector показывает текстовое поле
    Настраиваемый Inspector показывает текстовое поле

Привязка поля свойства

Чтобы отобразить свойства Car класс, добавьте элемент управления для каждого поля. Элемент должен соответствовать типу свойства. Например, вы должны привязать int в поле Целое число или Слайдер Целое число.

Вместо добавления конкретного контроля, основанного на типе свойства, можно использовать общий контроль PropertyField. Этот контроль работает для большинства типов серийных свойств и генерирует по умолчанию Inspector UI для данного типа свойства.

Преимуществом PropertyField является то, что Inspector UI автоматически настраивается при изменении типа переменной в вашем скрипте. Однако, вы не можете получить предварительный просмотр управления внутри UI Builder, потому что тип управления неизвестен до тех пор, пока визуальное дерево не будет привязано к серийному объекту.

  1. Дважды щелкните Car_Inspector_UXML.uxml, чтобы открыть его в UI Builder.

  2. Добавить PropertyField контроль для yearBuilt свойства Car класс и задайте путь привязки и текст метки.

    Добавить поле свойства в UI Builder
    Добавить поле свойства в UI Builder
  3. Добавление класса стиля unity-base-field__aligned к Генеральной Ассамблее Список классов стилей.

  4. Добавить PropertyField контроль для color свойства Car класс и задайте путь привязки и текст метки.

  5. Добавление класса стиля unity-base-field__aligned к Генеральной Ассамблее Список классов стилей.

  6. В UI Builder выберите Файл > Сохранить.

  7. Выберите GameObject, к которому прикреплен компонент Car. Inspector для компонента Car теперь отображает поля свойств Year Built и Paint Color.

    Пользовательские Inspector с полями свойств
    Пользовательские Inspector с полями свойств

Создание пользовательского ящика свойств

В отличие от пользовательских инспекторов, отрисовщики свойств работают с любым классом [Serializable], а не только с типами MonoBehaviour и ScriptableObject.

Пользовательский отрисовщик свойств — это собственный интерфейс инспектора для пользовательского сериализуемого класса. Если такой класс входит в другой сериализованный объект, этот интерфейс отображает соответствующее свойство в Inspector. В UI Toolkit PropertyField control отображает настраиваемый ящик свойств для поля, если таковой существует.

  1. В папке create-a-custom-inspector создайте новый скрипт под названием Tire.cs со следующим содержимым:

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
        
    [System.Serializable]
    public class Tire
    {
        public float airPressure = 21.5f;
        public int profileDepth = 4;
    }
        
    
  2. В Car.cs, добавить список Tire к Генеральной Ассамблее Car класс. Готовый Car.cs файл выглядит следующим образом:

    using UnityEngine;
        
    public class Car : MonoBehaviour
    {
        public string make = "Toyota";
        public int yearBuilt = 1980;
        public Color color = Color.black;
        
        // This car has four tires.
        public Tire[] tires = new Tire[4];
    }
    
  3. Контроллер PropertyField работает со всеми стандартными типами свойств и также поддерживает пользовательские сериализированные классы и массивы. Чтобы отобразить свойства шин автомобиля, добавьте еще один PropertyField в Car_Inspector_UXML.uxml и привязайте его к tires. Готовый файл Car_Inspector_UXML.uxml выглядит следующим образом:

    <ui:UXML xmlns:ui="UnityEngine.UIElements" xmlns:uie="UnityEditor.UIElements" editor-extension-mode="True">
        <ui:TextField picking-mode="Ignore" label="Make of the car" value="filler text" binding-path="make" class="unity-base-field__aligned" />
        <uie:PropertyField binding-path="yearBuilt" label="Year Built" class="unity-base-field__aligned" />
        <uie:PropertyField binding-path="color" label="Paint Color" class="unity-base-field__aligned" />
        <uie:PropertyField label="Tires" binding-path="tires" class="unity-base-field__aligned" />
    </ui:UXML>
        
    
  4. Выберите GameObject с прикрепленным к нему компонентом Car. Inspector для компонента Car теперь отображает поле свойства Tires.

    Используйте PropertyField для отображения массива
    Используйте PropertyField для отображения массива

Создать UI для ящика пользовательских свойств

Вы можете создать пользовательский ящик свойств, чтобы настроить внешний вид индивидуального Tire Вместо того, чтобы исходить из того, что Editor базового класса, а пользовательские отрисовщики свойств наследуют PropertyDrawer class.

Интерфейс свойства можно создать скриптом C# или средствами UXML. В этом примере используется скрипт C#. Чтобы построить интерфейс для пользовательского свойства, переопределите CreatePropertyGUI метод.

  1. В папке Editor Создайте новый скрипт под названием Tire_PropertyDrawer.cs со следующим содержимым:

    using UnityEditor;
    using UnityEditor.UIElements;
    using UnityEngine.UIElements;
        
    [CustomPropertyDrawer(typeof(Tire))]
    public class Tire_PropertyDrawer : PropertyDrawer
    {
        public override VisualElement CreatePropertyGUI(SerializedProperty property)
        {
            // Create drawer UI using C#.
            var popup = new UnityEngine.UIElements.PopupWindow();
            popup.text = "Tire Details";
            popup.Add(new PropertyField(property.FindPropertyRelative("airPressure"), "Air Pressure (psi)"));
            popup.Add(new PropertyField(property.FindPropertyRelative("profileDepth"), "Profile Depth (mm)"));
        
            // Return the finished UI.
            return popup;
        }
    }
    
  2. Выберите GameObject, к которому прикреплен компонент Car. Inspector для компонента Car теперь отображает поле свойств Tires с пользовательским ящиком свойств.

    Inspector с использованием пользовательского ящика свойств
    Inspector с использованием пользовательского ящика свойств

Дополнительные ресурсы