mirror of
https://github.com/Mukheem/TwinTurbine.git
synced 2025-02-01 04:44:19 +01:00
171 lines
6.7 KiB
C#
171 lines
6.7 KiB
C#
// Enable this to add editor menu items that can generate
|
|
// ProximaReflection.Generated.cs based on the contents of UnityComponents.json.
|
|
#if false
|
|
|
|
using System;
|
|
using System.Linq;
|
|
using System.Collections.Generic;
|
|
using UnityEditor;
|
|
using UnityEngine;
|
|
using System.Reflection;
|
|
|
|
namespace Proxima
|
|
{
|
|
internal static class ProximaCodeGen
|
|
{
|
|
private static Dictionary<string, string[]> GetUnityComponents()
|
|
{
|
|
var components = new Dictionary<string, string[]>();
|
|
var json = AssetDatabase.LoadAssetAtPath<TextAsset>("Assets/Proxima/Runtime/UnityComponents.json");
|
|
var jsonText = json.text.Replace(" ", "").Replace("\r", "").Replace("\t", "").Replace("\n", "");
|
|
var index = 0;
|
|
while (true)
|
|
{
|
|
var q1 = jsonText.IndexOf('"', index);
|
|
var q2 = jsonText.IndexOf('"', q1 + 1);
|
|
var a1 = jsonText.IndexOf('[', q2 + 1);
|
|
var a2 = jsonText.IndexOf(']', a1 + 1);
|
|
|
|
if (q1 == -1 || q2 == -1 || a1 == -1 || a2 == -1)
|
|
{
|
|
break;
|
|
}
|
|
|
|
var name = jsonText.Substring(q1 + 1, q2 - q1 - 1);
|
|
var properties = jsonText.Substring(a1 + 1, a2 - a1 - 1).Split(',').Select(x => x.Trim('"')).ToArray();
|
|
components.Add(name, properties);
|
|
index = a2 + 1;
|
|
}
|
|
|
|
return components;
|
|
}
|
|
|
|
private static Type GetType(string name)
|
|
{
|
|
foreach (Assembly a in AppDomain.CurrentDomain.GetAssemblies())
|
|
{
|
|
foreach (var type in a.GetTypes())
|
|
{
|
|
if (type.IsSubclassOf(typeof(UnityEngine.Component)) &&
|
|
(type.FullName == name || type.FullName.EndsWith("." + name)))
|
|
{
|
|
return type;
|
|
}
|
|
}
|
|
}
|
|
|
|
throw new Exception("Unknown Type: " + name);
|
|
}
|
|
|
|
private static string GeneratePropertyInfo(Type componentType, string prop, string name)
|
|
{
|
|
string define = null;
|
|
var split = prop.Split(':');
|
|
if (split.Length > 1)
|
|
{
|
|
define = split[0];
|
|
prop = split[1];
|
|
}
|
|
|
|
var s = "";
|
|
if (define != null)
|
|
{
|
|
s += $" #if {define}" + System.Environment.NewLine;
|
|
}
|
|
|
|
Debug.Log($"Generating {prop} for {name}");
|
|
var propertyInfo = componentType.GetProperty(prop);
|
|
var fieldInfo = componentType.GetField(prop);
|
|
var propertyType = propertyInfo?.PropertyType ?? fieldInfo.FieldType;
|
|
var propertyTypeName = propertyType.FullName;
|
|
if (propertyType.IsGenericType)
|
|
{
|
|
Type genericType = propertyType.GetGenericTypeDefinition();
|
|
string typeArgument = propertyType.GetGenericArguments()[0].FullName;
|
|
propertyTypeName = genericType.FullName.Split('`')[0] + "<" + typeArgument + ">";
|
|
}
|
|
|
|
propertyTypeName = propertyTypeName.Replace("+", ".");
|
|
|
|
s += $" new UnityProperty {{ Name = \"{prop}\", PropertyType = typeof({propertyTypeName}), Setter = (o, v) => (({name})o).{prop} = ({propertyTypeName})v, Getter = (o) => (({name})o).{prop}, ";
|
|
|
|
if (propertyType.IsEnum)
|
|
{
|
|
s += $"Updater = (object o, ref object v) => {{ var x = (int)(({name})o).{prop}; if (!x.Equals((int)v)) {{ v = x; return true; }} return false; }} ";
|
|
}
|
|
else if (propertyType.IsValueType)
|
|
{
|
|
s += $"Updater = (object o, ref object v) => {{ var x = (({name})o).{prop}; if (!x.Equals(({propertyTypeName})v)) {{ v = x; return true; }} return false; }} ";
|
|
}
|
|
else if (prop == "sharedMaterials") // Unity always returns a copy, so we only care if the size changes.
|
|
{
|
|
s += $"Updater = (object o, ref object v) => {{ var x = (({name})o).{prop}; if (x.Length != (({propertyTypeName})v).Length) {{ v = x; return true; }} else {{ v = x; return false; }}}} ";
|
|
}
|
|
|
|
s += "}," + System.Environment.NewLine;
|
|
|
|
if (define != null)
|
|
{
|
|
s += $" #endif" + System.Environment.NewLine;
|
|
}
|
|
return s;
|
|
}
|
|
|
|
[MenuItem("Proxima/Generate Reflection File")]
|
|
private static void GenerateReflectionFile()
|
|
{
|
|
var preserveTemplate = AssetDatabase.LoadAssetAtPath<TextAsset>("Assets/Proxima/Runtime/Generated/ProximaReflection.Template.cs");
|
|
var text = preserveTemplate.text;
|
|
var components = GetUnityComponents();
|
|
|
|
var code = string.Join(System.Environment.NewLine + System.Environment.NewLine,
|
|
components.Select(kv => {
|
|
var name = kv.Key;
|
|
var split = name.Split(':');
|
|
string define = null;
|
|
if (split.Length > 1)
|
|
{
|
|
define = split[0];
|
|
name = split[1];
|
|
}
|
|
|
|
var s = "";
|
|
if (define != null)
|
|
{
|
|
s += $" #if {define}" + System.Environment.NewLine;
|
|
}
|
|
|
|
var componentType = GetType(name);
|
|
s += $" {{ \"{componentType.FullName}\", new UnityProperty[] {{" + System.Environment.NewLine;
|
|
var enabled = componentType.GetProperty("enabled");
|
|
foreach (var prop in kv.Value)
|
|
{
|
|
if (prop.EndsWith(":enabled")) enabled = null; // Enabled added in some version
|
|
s += GeneratePropertyInfo(componentType, prop, name);
|
|
}
|
|
|
|
if (enabled != null)
|
|
{
|
|
s += GeneratePropertyInfo(componentType, "enabled", name);
|
|
}
|
|
|
|
s += " }}," + System.Environment.NewLine;
|
|
|
|
if (define != null)
|
|
{
|
|
s += $" #endif" + System.Environment.NewLine;
|
|
}
|
|
|
|
return s;
|
|
}));
|
|
|
|
text = text.Replace("_Template", "_Generated");
|
|
text = text.Replace(" // <Auto-generated>" + System.Environment.NewLine, code);
|
|
var preservePath = "Assets/Proxima/Runtime/Generated/ProximaReflection.Generated.cs";
|
|
System.IO.File.WriteAllText(preservePath, text);
|
|
AssetDatabase.Refresh();
|
|
}
|
|
}
|
|
}
|
|
|
|
#endif |