1
0
Fork 0
mirror of https://github.com/beefytech/Beef.git synced 2025-06-17 23:56:05 +02:00

Allow boxed types to utilize comptime methods

This commit is contained in:
Brian Fiete 2021-12-16 07:28:03 -05:00
parent 8bc5d09787
commit 2932fceae4
7 changed files with 114 additions and 29 deletions

View file

@ -174,7 +174,60 @@ namespace Tests
public float mY;
public float mZ;
}
class SerializationContext
{
public String mStr = new String() ~ delete _;
public void Serialize<T>(String name, T val) where T : struct
{
mStr.AppendF($"{name} {val}\n");
}
}
interface ISerializable
{
void Serialize(SerializationContext ctx);
}
[AttributeUsage(.Enum | .Struct | .Class, .NotInherited | .ReflectAttribute | .DisallowAllowMultiple)]
struct SerializableAttribute : Attribute, IComptimeTypeApply
{
[Comptime]
public void ApplyToType(Type type)
{
const String SERIALIZE_NAME = "void ISerializable.Serialize(SerializationContext ctx)\n";
String serializeBuffer = new .();
Compiler.Assert(!type.IsUnion);
for (let field in type.GetFields())
{
if (!field.IsInstanceField || field.DeclaringType != type)
continue;
serializeBuffer.AppendF($"\n\tctx.Serialize(\"{field.Name}\", {field.Name});");
}
Compiler.EmitTypeBody(type, scope $"{SERIALIZE_NAME}{{{serializeBuffer}\n}}\n");
}
}
[Serializable]
struct Foo : this(float x, float y), ISerializable
{
}
public class ComponentHandler<T>
where T : struct
{
uint8* data;
protected override void GCMarkMembers()
{
T* ptr = (T*)data;
GC.Mark!((*ptr));
}
}
[Test]
public static void TestBasics()
{
@ -209,6 +262,12 @@ namespace Tests
4 mY
8 mZ
""");
Foo bar = .(10, 2);
ISerializable iSer = bar;
SerializationContext serCtx = scope .();
iSer.Serialize(serCtx);
Test.Assert(serCtx.mStr == "x 10\ny 2\n");
}
}
}