Skip to content

Instantly share code, notes, and snippets.

@MisterKidX
Created July 15, 2024 13:49
Show Gist options
  • Save MisterKidX/44d122ba9473c6f1633ffa84eda3b17b to your computer and use it in GitHub Desktop.
Save MisterKidX/44d122ba9473c6f1633ffa84eda3b17b to your computer and use it in GitHub Desktop.
using System;
using System.IO;
using System.Reflection;
using System.Text;
using Unity.Entities;
using UnityEditor;
/// <summary>
/// will create a new authring script based on an IComponentData
/// </summary>
public class AuthoringGenerator
{
[MenuItem("Assets/Create Authoring")]
private static void CreateAuthoring()
{
var selection = Selection.activeObject;
if (selection.GetType() != typeof(MonoScript))
return;
var script = Selection.activeObject as MonoScript;
var type = script.GetClass();
if (type.GetInterface(nameof(IComponentData)) == null)
return;
Generate(type);
}
[MenuItem("Assets/Create Authoring", true)]
private static bool CreateAuthoringValidator()
{
var selection = Selection.activeObject;
if (selection.GetType() != typeof(MonoScript))
return false;
var script = Selection.activeObject as MonoScript;
var type = script.GetClass();
if (type.GetInterface(nameof(IComponentData)) == null)
return false;
return true;
}
private static void Generate(Type type)
{
const string accessibilityLevel = "public";
StringBuilder generatedFields = new();
StringBuilder assignedFields = new();
var fields = type.GetFields();
for (int i = 0; i < fields.Length; i++)
{
FieldInfo field = fields[i];
if (i != 0)
generatedFields.Append("\t\t");
generatedFields.Append(accessibilityLevel);
generatedFields.Append(" ");
generatedFields.Append(GetFieldShortName(field));
generatedFields.Append(" ");
generatedFields.Append(field.Name);
generatedFields.Append(";");
generatedFields.AppendLine();
if (i != 0)
assignedFields.Append("\t\t\t\t\t");
assignedFields.Append(field.Name);
assignedFields.Append(" = ");
assignedFields.Append("authoring.");
assignedFields.Append(field.Name);
if (i != fields.Length - 1)
{
assignedFields.Append(",");
assignedFields.AppendLine();
}
}
var fileName = $"{type.Name}_Authoring";
string @namespace = string.IsNullOrEmpty(type.Namespace) ? "Authoring" : type.Namespace + ".Authoring";
string source = $@"// <auto-generated/>
using Unity.Entities;
using UnityEngine;
namespace {@namespace}
{{
public partial class {fileName} : MonoBehaviour
{{
{generatedFields.ToString()}
private partial class Baker : Baker<{fileName}>
{{
public override void Bake({fileName} authoring)
{{
Entity e = GetEntity(TransformUsageFlags.Dynamic);
AddComponent(e, new {type.Name}()
{{
{assignedFields.ToString()}
}});
}}
}}
}}
}}
";
var path = UnityEngine.Application.dataPath + $"/{fileName}.cs";
if (!File.Exists(path))
{
var fs = File.Create(path);
fs.Dispose();
AssetDatabase.SaveAssets();
AssetDatabase.Refresh();
}
File.WriteAllText(path, source);
AssetDatabase.SaveAssets();
AssetDatabase.Refresh();
}
private static string GetFieldShortName(FieldInfo field)
{
switch (field.FieldType)
{
case Type t when t == typeof(Boolean):
return "bool";
case Type t when t == typeof(Int32):
return "int";
case Type t when t == typeof(Single):
return "float";
case Type t when t == typeof(Double):
return "double";
case Type t when t == typeof(String):
return "string";
default:
return field.FieldType.FullName;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment