Unity有個(gè)很煩人的規(guī)則:只要繼承于MonoBehaviour類的腳本必須要達(dá)成文件名與類名相等,然而在Unity編輯器中重命名一個(gè)集成與MonoBehaviour的腳本并不會(huì)重命名腳本里的class name。于是我們經(jīng)常重命名完一個(gè)腳本的文件名,Unity編譯一次;然后進(jìn)入腳本編輯軟件把該腳本的class name重命名保存,Unity再編譯一次。
This is such a waste of time and human resources!
所以我今天忍不住寫了一段一鍵重命名的Editor小腳本分享給大家。
腳本的限制:
a. 該腳本只重命名與文件名相同的類名。
b. 重命名一個(gè)腳本并不會(huì)更新其它腳本對(duì)該腳本名稱的引用。
using UnityEngine;
using UnityEditor;
using System.Text.RegularExpressions;
using System.IO;
[CustomEditor(typeof(MonoScript))]
public class ScriptRenameEditor : Editor
{
private string fileName = "";
public override void OnInspectorGUI()
{
base.OnInspectorGUI();
var t = target as MonoScript;
EditorGUILayout.BeginHorizontal();
var width = Screen.width * 2f / 3f;
//顯示文本框讓用戶輸入新的文件名
fileName = EditorGUILayout.TextField("New Filename", fileName, GUILayout.Width(width));
if (GUILayout.Button("Rename"))
{
//匹配文件名和父類的名字
var match = Regex.Match(t.text, @"class\s*(?<filename>" + t.name + @")\s*(\s*:\s*(?<basetype>[a-zA-Z0-9\_]+))?\s*\{");
if (match.Success)
{
var name = t.name;
var index = match.Groups["filename"].Index;
var finalText = t.text.Substring(0, index) + fileName + t.text.Substring(index + name.Length);
var filePath = AssetDatabase.GetAssetPath(t);
Debug.Log("renaming " + filePath);
//如果不存在父類,或者父類的名字不叫MonoBehaviour就彈窗警告用戶.
if (match.Groups["basetype"] == null || match.Groups["basetype"].Value != "MonoBehaviour")
{
if (!EditorUtility.DisplayDialog("This script is not derived by MonoBehaviour", "do you really want to rename it?", "yes", "no"))
{
return;
}
}
using (var fs = File.Open(filePath, FileMode.Truncate))
using (var wr = new StreamWriter(fs, System.Text.Encoding.UTF8))
{
wr.Write(finalText);
}
var fi = new FileInfo(filePath);
File.Move(filePath, fi.DirectoryName + Path.DirectorySeparatorChar + fileName + fi.Extension);
AssetDatabase.Refresh();
Selection.activeObject = AssetDatabase.LoadAssetAtPath<Object>(filePath.Replace(name, fileName));
}
else
{
Debug.Log("no class named \"" + t.name + "\" was found.");
}
}
EditorGUILayout.EndHorizontal();
//顯示文件的預(yù)覽內(nèi)容
if (t != null)
{
var text = t.text;
if (text.Length > 1000)
text = text.Substring(0, 1000) + "\n\n\n ...";
GUILayout.TextArea(text);
}
}
private void OnEnable()
{
var t = target as MonoScript;
fileName = t.name;
}
}
最終的效果如下:

Paste_Image.png