概要
- ScriptableObjectやPrefabなど特定のパスに置きたい場合があります
- そのチェックのためにEditor拡張を使ってアセットのパスを取得し、利用する方法です
ScriptableObectのサンプル
using UnityEngine;
# if UNITY_EDITOR
using UnityEditor;
# endif
//CreateAssetMenu属性をつけるとメニューからScriptableObjectを作成できるようになる
[CreateAssetMenu(menuName = "ScriptableObject/SamplePathScriptableObject", fileName = "SamplePathScriptableObject.asset")]
public class SamplePathScriptableObject : ScriptableObject
{
public string SampleString;
public int SampleInt;
}
# if UNITY_EDITOR
//CustomEditor属性でInspectorのEditor拡張が行える
[CustomEditor(typeof(SamplePathScriptableObject))]
public class SamplePathScriptableObjectInspector : Editor
{
public override void OnInspectorGUI()
{
//元のInspectorを表示する
base.OnInspectorGUI();
//InstanceIDからObjectを取得する
var obj = EditorUtility.InstanceIDToObject(target.GetInstanceID());
//取得したObjectからアセットのパスを取得する(拡張子あり)
var path = AssetDatabase.GetAssetPath(obj);
if (string.IsNullOrEmpty(path))
{
return;
}
//HelpBoxでパスを表示する
EditorGUILayout.HelpBox(path, MessageType.Info);
}
}
# endif
メニューからScriptableObjectを作成すると、ScriptableObjectのプロジェクト内でのパスがInspector内に表示することができます
Prefabのサンプル
using UnityEngine;
# if UNITY_EDITOR
using UnityEditor;
# endif
public class SamplePrefab : MonoBehaviour
{
[SerializeField]
string SampleString;
[SerializeField]
int SampleInt;
}
# if UNITY_EDITOR
[CustomEditor(typeof(SamplePrefab))]
public class SamplePrefabObjectInspector : Editor
{
public override void OnInspectorGUI()
{
base.OnInspectorGUI();
var obj = EditorUtility.InstanceIDToObject(target.GetInstanceID());
var path = AssetDatabase.GetAssetPath(obj);
if (string.IsNullOrEmpty(path))
{
return;
}
EditorGUILayout.HelpBox(path, MessageType.Info);
}
}
# endif
Prefabの場合も同じようにアセットのパスを表示することができます
応用篇 特定のパス以外に置いた場合に警告を出す
必ず特定の位置に設置したいアセットの場合、今回の機能を応用してチェック機構を実装することができます
using UnityEngine;
# if UNITY_EDITOR
using UnityEditor;
# endif
[CreateAssetMenu(menuName = "ScriptableObject/SamplePathScriptableObject", fileName = "SamplePathScriptableObject.asset")]
public class SamplePathScriptableObject : ScriptableObject
{
/// <summary>
/// アセットの正しい保存パス
/// </summary>
public const string ASSET_PATH = "Assets/Resources/ScriptableObject/SamplePathScriptableObject.asset";
public string SampleString;
public int SampleInt;
}
# if UNITY_EDITOR
[CustomEditor(typeof(SamplePathScriptableObject))]
public class SamplePathScriptableObjectInspector : Editor
{
public override void OnInspectorGUI()
{
base.OnInspectorGUI();
var obj = EditorUtility.InstanceIDToObject(target.GetInstanceID());
var path = AssetDatabase.GetAssetPath(obj);
if (string.IsNullOrEmpty(path))
{
return;
}
if(path != SamplePathScriptableObject.ASSET_PATH)
{
var message = $"アセットのパスが間違っています\n{SamplePathScriptableObject.ASSET_PATH}に保存してください";
EditorGUILayout.HelpBox(message, MessageType.Error);
}
}
}
# endif
今回の場合はInspectorにエラーを出すだけでしたが、もっと明確にエラーを出したい場合はダイアログを表示したりDebug.Assert
を使うのもいいでしょう。