【Unity】편집기 확장으로 SortingLayer의 필드를 표시한다
13252 단어 Unity
이 메뉴를 내고 싶다
표준 편집기 확장 API에서는 Sorting Layer를 편집하는 팝업을 생성할 방법이 없습니다.
이것을 수동으로 낼 수 있도록 한다는 이야기입니다.
정책
실은 SortingLayer의 리스트를 표시하는 API가 EditorGUI.SortingLayerField() 로서 존재하고 있습니다만, internal
로 지정되어 있기 (위해)때문에 직접 사용할 수 없게 되어 있습니다.
당초는 그대로 복사하고 움직이려고 했는데, 결국 다른 internal 멤버에 액세스할 필요가 나왔기 때문에 EditorGUI.SortingLayerField()
를 직접 리플렉션으로 호출하기로 했습니다.
Unity에서 internal 멤버에 액세스하려면 asmref를 사용하는 방법 어쩐지 있습니다만, 이번은 상대가 UnityEditor.dll
그래서 사용할 수 없어. 솔직하게 반사를 사용합니다.
구현
에디터 드로잉 때마다 리플렉션 시키면 에디터의 퍼포먼스에 영향을 줄 것 같은 느낌이 들기 때문에, 첫회만 델리게이트를 동적 생성해 2회째 이후는 캐쉬를 사용합니다.
SortingLayerEditorUtility.csusing System;
using System.Reflection;
using UnityEditor;
using UnityEngine;
namespace Ruccho.Utilities
{
public static class SortingLayerEditorUtility
{
private static GUIStyle boldPopupStyle;
private static GUIStyle BoldPopupStyle
{
get
{
if (boldPopupStyle == null)
{
boldPopupStyle = new GUIStyle(EditorStyles.popup);
boldPopupStyle.fontStyle = FontStyle.Bold;
}
return boldPopupStyle;
}
}
private delegate void SortingLayerFieldDelegate(Rect position, GUIContent label, SerializedProperty layerID,
GUIStyle style, GUIStyle labelStyle);
private static SortingLayerFieldDelegate sortingLayerFieldDelegate = default;
private static bool HasPrefabOverride(SerializedProperty property)
{
return property != null && property.serializedObject.targetObjects.Length == 1 && property.isInstantiatedPrefab && property.prefabOverride;
}
public static void SortingLayerFieldLayout(GUIContent label, SerializedProperty layerID)
{
var hasPrefabOverride = HasPrefabOverride(layerID);
var style = hasPrefabOverride ? BoldPopupStyle : EditorStyles.popup;
var labelStyle = hasPrefabOverride ? EditorStyles.boldLabel : EditorStyles.label;
SortingLayerFieldLayout(label, layerID, style, labelStyle);
}
public static void SortingLayerFieldLayout(GUIContent label, SerializedProperty layerID, GUIStyle style, GUIStyle labelStyle)
{
Rect rect = EditorGUILayout.GetControlRect(false, EditorGUIUtility.singleLineHeight, style);
SortingLayerField(rect, label, layerID, style, labelStyle);
}
public static void SortingLayerField(Rect position, GUIContent label, SerializedProperty layerID)
{
var hasPrefabOverride = HasPrefabOverride(layerID);
var style = hasPrefabOverride ? BoldPopupStyle : EditorStyles.popup;
var labelStyle = hasPrefabOverride ? EditorStyles.boldLabel : EditorStyles.label;
SortingLayerField(position, label, layerID, style, labelStyle);
}
public static void SortingLayerField(Rect position, GUIContent label, SerializedProperty layerID,
GUIStyle style, GUIStyle labelStyle)
{
if (sortingLayerFieldDelegate == default)
{
var editorGuiType = typeof(EditorGUI);
var sortingLayerFieldMethod =
editorGuiType.GetMethod("SortingLayerField", BindingFlags.Static | BindingFlags.NonPublic);
if (sortingLayerFieldMethod == null) return;
sortingLayerFieldDelegate = (SortingLayerFieldDelegate)
Delegate.CreateDelegate(typeof(SortingLayerFieldDelegate), sortingLayerFieldMethod);
}
sortingLayerFieldDelegate?.Invoke(position, label, layerID, style, labelStyle);
}
}
}
여기까지 하면 SortingLayerEditorUtility.SortingLayerFieldLayout()
또는 SortingLayerEditorUtility.SortingLayerField()
로 호출이 가능합니다.
참고
neue cc - C #에서 동적 메소드 선택에서 정형 가속 패턴
Reference
이 문제에 관하여(【Unity】편집기 확장으로 SortingLayer의 필드를 표시한다), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/ruccho_vector/items/6a28e20b62121464e24a
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
실은 SortingLayer의 리스트를 표시하는 API가 EditorGUI.SortingLayerField() 로서 존재하고 있습니다만,
internal
로 지정되어 있기 (위해)때문에 직접 사용할 수 없게 되어 있습니다.당초는 그대로 복사하고 움직이려고 했는데, 결국 다른 internal 멤버에 액세스할 필요가 나왔기 때문에
EditorGUI.SortingLayerField()
를 직접 리플렉션으로 호출하기로 했습니다.Unity에서 internal 멤버에 액세스하려면 asmref를 사용하는 방법 어쩐지 있습니다만, 이번은 상대가
UnityEditor.dll
그래서 사용할 수 없어. 솔직하게 반사를 사용합니다.구현
에디터 드로잉 때마다 리플렉션 시키면 에디터의 퍼포먼스에 영향을 줄 것 같은 느낌이 들기 때문에, 첫회만 델리게이트를 동적 생성해 2회째 이후는 캐쉬를 사용합니다.
SortingLayerEditorUtility.csusing System;
using System.Reflection;
using UnityEditor;
using UnityEngine;
namespace Ruccho.Utilities
{
public static class SortingLayerEditorUtility
{
private static GUIStyle boldPopupStyle;
private static GUIStyle BoldPopupStyle
{
get
{
if (boldPopupStyle == null)
{
boldPopupStyle = new GUIStyle(EditorStyles.popup);
boldPopupStyle.fontStyle = FontStyle.Bold;
}
return boldPopupStyle;
}
}
private delegate void SortingLayerFieldDelegate(Rect position, GUIContent label, SerializedProperty layerID,
GUIStyle style, GUIStyle labelStyle);
private static SortingLayerFieldDelegate sortingLayerFieldDelegate = default;
private static bool HasPrefabOverride(SerializedProperty property)
{
return property != null && property.serializedObject.targetObjects.Length == 1 && property.isInstantiatedPrefab && property.prefabOverride;
}
public static void SortingLayerFieldLayout(GUIContent label, SerializedProperty layerID)
{
var hasPrefabOverride = HasPrefabOverride(layerID);
var style = hasPrefabOverride ? BoldPopupStyle : EditorStyles.popup;
var labelStyle = hasPrefabOverride ? EditorStyles.boldLabel : EditorStyles.label;
SortingLayerFieldLayout(label, layerID, style, labelStyle);
}
public static void SortingLayerFieldLayout(GUIContent label, SerializedProperty layerID, GUIStyle style, GUIStyle labelStyle)
{
Rect rect = EditorGUILayout.GetControlRect(false, EditorGUIUtility.singleLineHeight, style);
SortingLayerField(rect, label, layerID, style, labelStyle);
}
public static void SortingLayerField(Rect position, GUIContent label, SerializedProperty layerID)
{
var hasPrefabOverride = HasPrefabOverride(layerID);
var style = hasPrefabOverride ? BoldPopupStyle : EditorStyles.popup;
var labelStyle = hasPrefabOverride ? EditorStyles.boldLabel : EditorStyles.label;
SortingLayerField(position, label, layerID, style, labelStyle);
}
public static void SortingLayerField(Rect position, GUIContent label, SerializedProperty layerID,
GUIStyle style, GUIStyle labelStyle)
{
if (sortingLayerFieldDelegate == default)
{
var editorGuiType = typeof(EditorGUI);
var sortingLayerFieldMethod =
editorGuiType.GetMethod("SortingLayerField", BindingFlags.Static | BindingFlags.NonPublic);
if (sortingLayerFieldMethod == null) return;
sortingLayerFieldDelegate = (SortingLayerFieldDelegate)
Delegate.CreateDelegate(typeof(SortingLayerFieldDelegate), sortingLayerFieldMethod);
}
sortingLayerFieldDelegate?.Invoke(position, label, layerID, style, labelStyle);
}
}
}
여기까지 하면 SortingLayerEditorUtility.SortingLayerFieldLayout()
또는 SortingLayerEditorUtility.SortingLayerField()
로 호출이 가능합니다.
참고
neue cc - C #에서 동적 메소드 선택에서 정형 가속 패턴
Reference
이 문제에 관하여(【Unity】편집기 확장으로 SortingLayer의 필드를 표시한다), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/ruccho_vector/items/6a28e20b62121464e24a
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
using System;
using System.Reflection;
using UnityEditor;
using UnityEngine;
namespace Ruccho.Utilities
{
public static class SortingLayerEditorUtility
{
private static GUIStyle boldPopupStyle;
private static GUIStyle BoldPopupStyle
{
get
{
if (boldPopupStyle == null)
{
boldPopupStyle = new GUIStyle(EditorStyles.popup);
boldPopupStyle.fontStyle = FontStyle.Bold;
}
return boldPopupStyle;
}
}
private delegate void SortingLayerFieldDelegate(Rect position, GUIContent label, SerializedProperty layerID,
GUIStyle style, GUIStyle labelStyle);
private static SortingLayerFieldDelegate sortingLayerFieldDelegate = default;
private static bool HasPrefabOverride(SerializedProperty property)
{
return property != null && property.serializedObject.targetObjects.Length == 1 && property.isInstantiatedPrefab && property.prefabOverride;
}
public static void SortingLayerFieldLayout(GUIContent label, SerializedProperty layerID)
{
var hasPrefabOverride = HasPrefabOverride(layerID);
var style = hasPrefabOverride ? BoldPopupStyle : EditorStyles.popup;
var labelStyle = hasPrefabOverride ? EditorStyles.boldLabel : EditorStyles.label;
SortingLayerFieldLayout(label, layerID, style, labelStyle);
}
public static void SortingLayerFieldLayout(GUIContent label, SerializedProperty layerID, GUIStyle style, GUIStyle labelStyle)
{
Rect rect = EditorGUILayout.GetControlRect(false, EditorGUIUtility.singleLineHeight, style);
SortingLayerField(rect, label, layerID, style, labelStyle);
}
public static void SortingLayerField(Rect position, GUIContent label, SerializedProperty layerID)
{
var hasPrefabOverride = HasPrefabOverride(layerID);
var style = hasPrefabOverride ? BoldPopupStyle : EditorStyles.popup;
var labelStyle = hasPrefabOverride ? EditorStyles.boldLabel : EditorStyles.label;
SortingLayerField(position, label, layerID, style, labelStyle);
}
public static void SortingLayerField(Rect position, GUIContent label, SerializedProperty layerID,
GUIStyle style, GUIStyle labelStyle)
{
if (sortingLayerFieldDelegate == default)
{
var editorGuiType = typeof(EditorGUI);
var sortingLayerFieldMethod =
editorGuiType.GetMethod("SortingLayerField", BindingFlags.Static | BindingFlags.NonPublic);
if (sortingLayerFieldMethod == null) return;
sortingLayerFieldDelegate = (SortingLayerFieldDelegate)
Delegate.CreateDelegate(typeof(SortingLayerFieldDelegate), sortingLayerFieldMethod);
}
sortingLayerFieldDelegate?.Invoke(position, label, layerID, style, labelStyle);
}
}
}
neue cc - C #에서 동적 메소드 선택에서 정형 가속 패턴
Reference
이 문제에 관하여(【Unity】편집기 확장으로 SortingLayer의 필드를 표시한다), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/ruccho_vector/items/6a28e20b62121464e24a텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)