diff --git a/csharp-guests.sln b/csharp-guests.sln index 7c9556f..f063b41 100644 --- a/csharp-guests.sln +++ b/csharp-guests.sln @@ -3,7 +3,7 @@ Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio Version 17 VisualStudioVersion = 17.0.31903.59 MinimumVisualStudioVersion = 10.0.40219.1 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "dotnet-guest-test", "guests/csharp/dotnet-guest-test\dotnet-guest-test.csproj", "{68F96E6F-472F-409E-B36E-9C5E7206CCDE}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "dotnet-guest-test", "guests\csharp\dotnet-guest-test\dotnet-guest-test.csproj", "{68F96E6F-472F-409E-B36E-9C5E7206CCDE}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution diff --git a/guests/csharp/dotnet-guest-test/ExampleWorldImpl.cs b/guests/csharp/dotnet-guest-test/ExampleWorldImpl.cs index c9c51c7..0d72826 100644 --- a/guests/csharp/dotnet-guest-test/ExampleWorldImpl.cs +++ b/guests/csharp/dotnet-guest-test/ExampleWorldImpl.cs @@ -1,7 +1,7 @@ namespace ExampleWorld; using ExampleWorld.wit.imports.lyra.api; - +using LyraApi.Asset; using LyraApi.Ecs; using LyraApi.Engine; using LyraApi.Math; @@ -19,9 +19,31 @@ public class ExampleWorldImpl : IExampleWorld Console.WriteLine("C#: Found entity at ({0}, {1}, {2})", comp.X, comp.Y, comp.Z); } - DeltaTime? dt = world.GetResource(); + /* DeltaTime? dt = world.GetResource(); if (dt != null) { Console.WriteLine($"C#: Delta time: {dt?.Seconds:0.##}"); + } */ + + AssetManager? man = world.GetAssetManager(); + if (man != null) + { + Handle han = man.Request("test_assets/white.png"); + Console.WriteLine($"C#: Asset uuid: {han.Uuid}"); + + // wait for asset to load before trying to get the data + han.WaitForLoadRecursive(); + if (!han.IsLoaded) + { + Console.WriteLine("C#: Asset is still not loaded, even after waiting!"); + } + + // will be null if the image hasn't loaded yet + ImageHandle? img = han.GetData(); + Console.WriteLine($"C#: Size of image: ({img?.Width}, {img?.Height})"); + } + else + { + Console.WriteLine("C#: No manager found"); } } diff --git a/guests/csharp/dotnet-guest-test/LyraApi/Asset/AssetManager.cs b/guests/csharp/dotnet-guest-test/LyraApi/Asset/AssetManager.cs new file mode 100644 index 0000000..171a482 --- /dev/null +++ b/guests/csharp/dotnet-guest-test/LyraApi/Asset/AssetManager.cs @@ -0,0 +1,39 @@ +using LyraApi.Ecs; +using ExampleWorld.wit.imports.lyra.api; + +namespace LyraApi.Asset; + +public class AssetManager(IAsset.AssetManager assetManager) : IResource +{ + internal IAsset.AssetManager inner = assetManager; + + public static ulong TypeId => 567234789345; + + public static object? FromWasmResult(IEcs.WorldResourceResult result) + { + switch (result.Tag) + { + case IEcs.WorldResourceResult.NONE: + return null; + case IEcs.WorldResourceResult.WASM_RESOURCE_REP: + Console.WriteLine($"Got the resource rep: {result.AsWasmResourceRep}"); + var handle = new IAsset.AssetManager.THandle((int)result.AsWasmResourceRep); + var inner = new IAsset.AssetManager(handle); + return new AssetManager(inner); + case IEcs.WorldResourceResult.BYTES: + return null; + default: + return null; + } + } + + public UntypedHandle Request(string path) + { + return new UntypedHandle(inner.Request(path)); + } + + public Handle Request(string path) where T : IAssetHandle + { + return Request(path).AsHandle(); + } +} \ No newline at end of file diff --git a/guests/csharp/dotnet-guest-test/LyraApi/Asset/Handle.cs b/guests/csharp/dotnet-guest-test/LyraApi/Asset/Handle.cs new file mode 100644 index 0000000..7cdbe58 --- /dev/null +++ b/guests/csharp/dotnet-guest-test/LyraApi/Asset/Handle.cs @@ -0,0 +1,34 @@ +namespace LyraApi.Asset; + +public class Handle(UntypedHandle handle) where T : IAssetHandle +{ + internal UntypedHandle inner = handle; + + public bool Watched { get => inner.Watched; set => inner.Watched = value; } + public ulong Version { get => inner.Version; } + public Guid Uuid { get => inner.Uuid; } + public string Path { get => inner.Path; } + public bool IsLoaded { get => inner.IsLoaded; } + + public void WaitForLoad() + { + inner.WaitForLoad(); + } + + public void WaitForLoadRecursive() + { + inner.WaitForLoadRecursive(); + } + + public T? GetData() + { + if (IsLoaded) + { + return (T?)T.FromRawHandle(inner); + } + else + { + return default; + } + } +} \ No newline at end of file diff --git a/guests/csharp/dotnet-guest-test/LyraApi/Asset/IAssetHandle.cs b/guests/csharp/dotnet-guest-test/LyraApi/Asset/IAssetHandle.cs new file mode 100644 index 0000000..3968a9c --- /dev/null +++ b/guests/csharp/dotnet-guest-test/LyraApi/Asset/IAssetHandle.cs @@ -0,0 +1,6 @@ +namespace LyraApi.Asset; + +public interface IAssetHandle +{ + public abstract static object? FromRawHandle(UntypedHandle untypedHandle); +} \ No newline at end of file diff --git a/guests/csharp/dotnet-guest-test/LyraApi/Asset/ImageHandle.cs b/guests/csharp/dotnet-guest-test/LyraApi/Asset/ImageHandle.cs new file mode 100644 index 0000000..e7c0254 --- /dev/null +++ b/guests/csharp/dotnet-guest-test/LyraApi/Asset/ImageHandle.cs @@ -0,0 +1,28 @@ +using ExampleWorld.wit.imports.lyra.api; + +namespace LyraApi.Asset; + +public class ImageHandle(IAsset.ImageHandle handle) : IAssetHandle +{ + internal IAsset.ImageHandle inner = handle; + + public uint? Height => inner.Height(); + public uint? Width => inner.Width(); + + public static object? FromRawHandle(UntypedHandle untypedHandle) + { + var handle = IAsset.ImageHandle.FromRawHandle(untypedHandle.inner); + return handle != null ? new ImageHandle(handle) : null; + } + + /// + /// Get the image's pixels as native endian bytes. + /// + /// + /// Keep in mind that this does copy the image's pixels from the host. + /// This is pretty slow. + public byte[]? GetImageBytes() + { + return inner.GetBytes(); + } +} \ No newline at end of file diff --git a/guests/csharp/dotnet-guest-test/LyraApi/Asset/UntypedHandle.cs b/guests/csharp/dotnet-guest-test/LyraApi/Asset/UntypedHandle.cs new file mode 100644 index 0000000..ae49dc7 --- /dev/null +++ b/guests/csharp/dotnet-guest-test/LyraApi/Asset/UntypedHandle.cs @@ -0,0 +1,29 @@ +using ExampleWorld.wit.imports.lyra.api; + +namespace LyraApi.Asset; + +public class UntypedHandle(IAsset.AssetHandle handle) +{ + internal IAsset.AssetHandle inner = handle; + + public bool Watched { get => inner.IsWatched(); set => inner.SetWatched(value); } + public ulong Version { get => inner.Version(); } + public Guid Uuid { get => Guid.Parse(inner.Uuid()); } + public string Path { get => inner.Path(); } + public bool IsLoaded { get => inner.IsLoaded(); } + + public void WaitForLoad() + { + inner.WaitForLoad(); + } + + public void WaitForLoadRecursive() + { + inner.WaitRecurseDependenciesLoad(); + } + + public Handle AsHandle() where T : IAssetHandle + { + return new Handle(this); + } +} \ No newline at end of file diff --git a/guests/csharp/dotnet-guest-test/LyraApi/Ecs/World.cs b/guests/csharp/dotnet-guest-test/LyraApi/Ecs/World.cs index f8ed547..d6600b5 100644 --- a/guests/csharp/dotnet-guest-test/LyraApi/Ecs/World.cs +++ b/guests/csharp/dotnet-guest-test/LyraApi/Ecs/World.cs @@ -2,15 +2,16 @@ namespace LyraApi.Ecs; using ExampleWorld.wit.imports.lyra.api; using LyraApi; +using LyraApi.Asset; public class World(IEcs.EcsWorld world) { - private IEcs.EcsWorld Inner { get; set; } = world; + internal IEcs.EcsWorld inner = world; private Entity Spawn(List infos, params object[] comps) { byte[] bytes = comps.SelectMany(c => MarshalUtils.GetBytes(c)).ToArray(); - return new Entity(Inner.Spawn(bytes, infos)); + return new Entity(inner.Spawn(bytes, infos)); } public Entity Spawn(T1 c1) where T1 : IComponent @@ -24,13 +25,27 @@ public class World(IEcs.EcsWorld world) List comps = [Component.FromComponent()]; List infos = comps.Select(c => c.GetComponentInfo().info).ToList(); - IEcs.EcsDynamicView dynamicView = Inner.View(infos); + IEcs.EcsDynamicView dynamicView = inner.View(infos); return new ViewResult(comps, dynamicView).Get(); } public T? GetResource() where T : IResource { - IEcs.WorldResourceResult result = Inner.GetResource(Utils.ToWasmTypeId(T.TypeId)); - return (T?) T.FromWasmResult(result); + IEcs.WorldResourceResult result = inner.GetResource(Utils.ToWasmTypeId(T.TypeId)); + return (T?)T.FromWasmResult(result); + } + + public AssetManager? GetAssetManager() + { + IAsset.AssetManager? assetManager = IAsset.AssetManager.FromWorld(inner); + + if (assetManager != null) + { + return new AssetManager(assetManager); + } + else + { + return null; + } } } \ No newline at end of file diff --git a/guests/csharp/dotnet-guest-test/dotnet-guest-test.csproj b/guests/csharp/dotnet-guest-test/dotnet-guest-test.csproj index 757eff2..193df5d 100644 --- a/guests/csharp/dotnet-guest-test/dotnet-guest-test.csproj +++ b/guests/csharp/dotnet-guest-test/dotnet-guest-test.csproj @@ -18,13 +18,17 @@ - + + + + +