Unity处理材质球过期属性工具
程序员文章站
2022-06-11 07:53:52
...
Unity中的材质属性被序列化以后,就会一直存储在资源中,即使该属性删除后,它的序列化值以及引用关系也不会被丢掉,所以我们经常会发现,当我们使用一个和之前命名相同的属性时,原来的属性值或资源就会被自动赋值,这是因为材质中一直保持这种关系;但是,有些时候我们为了优化或者其它需求,想要去清理掉这些引用关系,如下,给出了清理某个文件夹下所有材质过期属性的一个工具;
参考:游戏资源工具(一):Unity中处理材质球过期属性工具
using UnityEngine;
using UnityEditor;
public class MatObseletePropertyWindow : EditorWindow
{
public static string assetFolderPath = "Assets/Scenes";
[MenuItem ("Tools/移除材质中的废弃属性")]
public static void ShowWindow () {
EditorWindow thisWindow = EditorWindow.GetWindow(typeof(MatObseletePropertyWindow));
thisWindow.titleContent = new GUIContent("统计并移除材质中的无用属性");
thisWindow.position = new Rect(Screen.width/2, Screen.height/2, 600, 1000);
}
public static void ClearMatObseleteProperty()
{
Debug.Log(Application.dataPath);
string projectPath = Application.dataPath.Replace("Assets", "");
assetFolderPath = assetFolderPath.Replace(projectPath, "");
var matList = AssetDatabase.FindAssets("t:Material", new[] {assetFolderPath});
foreach(var i in matList)
{
// EditorUtility.DisplayProgressBar("材质属性移除统计文件", "正在写入统计文件中...", ix/shaderList.Length);
var path = AssetDatabase.GUIDToAssetPath(i);
Material mat = AssetDatabase.LoadAssetAtPath(path, typeof(Material)) as Material;
Debug.Log(mat.name);
SerializedObject so = new SerializedObject(mat);
SerializedProperty m_SavedProperties = so.FindProperty("m_SavedProperties");
RemoveElement(mat, "m_TexEnvs", m_SavedProperties);
RemoveElement(mat, "m_Floats", m_SavedProperties);
RemoveElement(mat, "m_Colors", m_SavedProperties);
so.ApplyModifiedProperties();
}
AssetDatabase.SaveAssets();
AssetDatabase.Refresh();
}
private static void RemoveElement(Material mat, string spName, SerializedProperty saveProperty){
SerializedProperty property = saveProperty.FindPropertyRelative(spName);
for(int i = property.arraySize - 1; i >= 0; i--){
var prop = property.GetArrayElementAtIndex(i);
string propertyName = prop.displayName;
if (!mat.HasProperty(propertyName))
{
property.DeleteArrayElementAtIndex(i);
Debug.Log("移除属性名称" + propertyName);
}
}
}
void OnGUI()
{
EditorGUILayout.BeginHorizontal();
EditorGUILayout.LabelField("选择文件夹");
EditorGUILayout.TextField(assetFolderPath);
if (GUILayout.Button("选择"))
{
assetFolderPath = EditorUtility.OpenFolderPanel("选择文件夹", assetFolderPath, "");
}
EditorGUILayout.EndHorizontal();
if (GUILayout.Button("确定") && assetFolderPath != null)
{
ClearMatObseleteProperty();
}
}
}