- Home /
Custom Property Drawer arrays issue
Hey, I'm trying to learn how to make custom inspector windows with custom property drawers to improve workflow and automate some tasks for a script I'm writing. For the most part, I've been able to work it out on my own, but I have run into a bit of an issue I can't seem to solve.
The script that I am working on essentially requires me to store an array of Vector3 arrays which represent in game coordinates. below are some pictures outlining what is currently happening with the arrays;
the inspector lays out each item from the parent array as shown above, but when I try to open the child array this happens;
The array opens and is fully editable, but as you can see it ends up overlapping with the others. This problem persists even when I don't use the fancy layout for the parent array(ie I render it all through DrawDefaultInspector)
I will post the scripts below;
Custom Data Type:
using UnityEngine;
using System;
[Serializable]
public class CoverData
{
public Vector3[] points;
public Vector3[] directions;
public Color gizmoColor;
}
Custom Inspector Script:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEditor;
[CustomEditor(typeof(CoverEditor))]
public class CoverEditorInspector : Editor
{
CoverEditor script;
void OnEnable() { EditorApplication.update += Update; }
void OnDisable() { EditorApplication.update -= Update; }
public override void OnInspectorGUI()
{
serializedObject.Update();
Editor_List.Show(serializedObject.FindProperty("coverData"), EditorListOptions.Buttons);
script = (CoverEditor)target;
if (GUILayout.Button("Edit Points"))
{
script.ToggleEdit();
}
serializedObject.ApplyModifiedProperties();
}
void Update()
{
if (script != null)
{
if (script.IsEditing())
{
if (Selection.activeGameObject != null)
{
if (Selection.activeGameObject.GetComponent<EditVertex>())
{ Debug.Log("Vertex"); }
}
}
}
}
}
Property Drawer Script:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEditor;
[CustomPropertyDrawer(typeof(CoverData),true)]
public class CoverDataPointDrawer : PropertyDrawer
{
public override float GetPropertyHeight(SerializedProperty property, GUIContent label)
{
return label != GUIContent.none && Screen.width < 333 ? (16f + 18f) : 16f;
}
public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
{
EditorGUI.BeginProperty(position, label, property);
int indent = EditorGUI.indentLevel;
EditorGUI.indentLevel = 0;
Rect pos = new Rect(position.x, position.y, 100, position.height);
Rect color = new Rect(position.x + 250, position.y, 50, position.height);
Rect contentPosition = EditorGUI.PrefixLabel(position, label);
if (position.height > 16f)
{
position.height = 16f;
EditorGUI.indentLevel += 1;
contentPosition = EditorGUI.IndentedRect(position);
contentPosition.y += 18f;
}
contentPosition.width *= 0.75f;
EditorGUI.indentLevel = 0;
//EditorGUI.PropertyField(position, property, GUIContent.none);
EditorGUI.PropertyField(position, property.FindPropertyRelative("points"), new GUIContent("Vertecies"),true);
EditorGUI.indentLevel = indent;
EditorGUI.EndProperty();
}
}
Inspector List Display Script(The one that lays out all the parts of the parent array) But do note that even when I do not use this script to render the first array I have the same problem:
using UnityEditor;
using UnityEngine;
using System;
[Flags]
public enum EditorListOptions
{
None = 0,
ListSize = 1,
ListLabel = 2,
ElementLabels = 4,
Buttons = 8,
Default = ListSize | ListLabel | ElementLabels,
NoElementLabels = ListSize | ListLabel,
All = Default | Buttons
}
public static class Editor_List
{
private static GUIContent
selectButtonContent = new GUIContent("\u2611", "Select"),
duplicateButtonContent = new GUIContent("+", "Duplicate"),
deleteButtonContent = new GUIContent("-", "Delete"),
addButtonContent = new GUIContent("+", "Add Element");
private static GUILayoutOption miniButtonWidth = GUILayout.Width(20f);
public static void Show(SerializedProperty list, EditorListOptions options = EditorListOptions.Default)
{
if (!list.isArray)
{
EditorGUILayout.HelpBox(list.name + " is neither an array nor a list!", MessageType.Error);
return;
}
bool
showListLabel = (options & EditorListOptions.ListLabel) != 0,
showListSize = (options & EditorListOptions.ListSize) != 0;
if (showListLabel)
{
EditorGUILayout.PropertyField(list);
EditorGUI.indentLevel += 1;
}
if (!showListLabel || list.isExpanded)
{
SerializedProperty size = list.FindPropertyRelative("Array.size");
if (showListSize)
{
EditorGUILayout.PropertyField(size);
}
if (size.hasMultipleDifferentValues)
{
EditorGUILayout.HelpBox("Not showing lists with different sizes.", MessageType.Info);
}
else
{
ShowElements(list, options);
}
}
if (showListLabel)
{
EditorGUI.indentLevel -= 1;
}
}
private static void ShowElements(SerializedProperty list, EditorListOptions options)
{
bool
showElementLabels = (options & EditorListOptions.ElementLabels) != 0,
showButtons = (options & EditorListOptions.Buttons) != 0;
for (int i = 0; i < list.arraySize; i++)
{
if (showButtons)
{
EditorGUILayout.BeginHorizontal();
}
if (showElementLabels)
{
EditorGUILayout.PropertyField(list.GetArrayElementAtIndex(i));
}
else
{
EditorGUILayout.PropertyField(list.GetArrayElementAtIndex(i), GUIContent.none);
}
if (showButtons)
{
ShowButtons(list, i);
EditorGUILayout.EndHorizontal();
}
}
if (showButtons && list.arraySize == 0 && GUILayout.Button(addButtonContent, EditorStyles.miniButton))
{
list.arraySize += 1;
}
}
private static void ShowButtons(SerializedProperty list, int index)
{
if (GUILayout.Button(selectButtonContent, EditorStyles.miniButtonLeft, miniButtonWidth))
{
list.MoveArrayElement(index, index + 1);
}
if (GUILayout.Button(duplicateButtonContent, EditorStyles.miniButtonMid, miniButtonWidth))
{
list.InsertArrayElementAtIndex(index);
}
if (GUILayout.Button(deleteButtonContent, EditorStyles.miniButtonRight, miniButtonWidth))
{
int oldSize = list.arraySize;
list.DeleteArrayElementAtIndex(index);
if (list.arraySize == oldSize)
{
list.DeleteArrayElementAtIndex(index);
}
}
}
}
Thanks for the help, and let me know if you need any clarification.
Answer by qtoompuu · Jan 12, 2021 at 06:57 AM
Ok so it turns out I'm just terrible at late night debugging.
I was using EditorGUI when I should have been using EditorGUILayout in the property drawer script. I'll leave this here though incase anyone else is equally blind as I am :|.