feat(a2b): implement 0x208 get-texture-size (geometry keystone)
Promote 0x208 from stub to a real VM op that writes the loaded texture's width/height into its two output globals, via new IHost.GetTextureSize. This is the single native primitive the CG-load subroutine (SC0000 label_12649) needs; all downstream centering/anchor geometry is already computed in bytecode. Non-Godot hosts return (0,0) so trace/selftest parity holds (engine 9/9 incl. TraceDiffTests). Godot host gets a temporary (0,0) stub; real impl in the compositor task. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -84,4 +84,5 @@ sealed class AudioTraceHost : IHost
|
||||
public void CreateTexture(int slot, int width, int height) { }
|
||||
public void SetTexture(long resourceId, int slot) { }
|
||||
public void DrawTexture(int slot, int srcX, int srcY, int width, int height, int dstX, int dstY) { }
|
||||
public (int Width, int Height) GetTextureSize(int slot) => (0, 0);
|
||||
}
|
||||
|
||||
46
engine/Age.Engine.Tests/TextureGeometryTests.cs
Normal file
46
engine/Age.Engine.Tests/TextureGeometryTests.cs
Normal file
@@ -0,0 +1,46 @@
|
||||
using System.Collections.Generic;
|
||||
using Age.Engine.Hosting;
|
||||
using Age.Engine.Model;
|
||||
using Age.Engine.Sys4;
|
||||
using Age.Engine.Vm;
|
||||
using Xunit;
|
||||
|
||||
public class TextureGeometryTests
|
||||
{
|
||||
private sealed class FakeSizeHost : IHost
|
||||
{
|
||||
public void ShowText(int o, string t) { }
|
||||
public void CallScript(long id) { }
|
||||
public void OnStub(int op) { }
|
||||
public void WaitForInput() { }
|
||||
public void CreateTexture(int slot, int w, int h) { }
|
||||
public void SetTexture(long resId, int slot) { }
|
||||
public void DrawTexture(int slot, int sx, int sy, int w, int h, int dx, int dy) { }
|
||||
public void PlayBgm(long id) { }
|
||||
public void PlayVoice(long id) { }
|
||||
public (int Width, int Height) GetTextureSize(int slot) => (0x140, 0xC8);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void GetTextureSizeWritesHostDimsIntoOutputGlobals()
|
||||
{
|
||||
var table = OpcodeTableJson.Load(Paths.OpcodesJson);
|
||||
// 0x208 (global-int 50)(global-int 60)(global-int 61): slot=50, out_w=G[60], out_h=G[61]
|
||||
const int T_GINT = 3;
|
||||
var ins = new Instruction(0, 0x208, new[]
|
||||
{
|
||||
new Operand(T_GINT, 50), new Operand(T_GINT, 60), new Operand(T_GINT, 61),
|
||||
});
|
||||
var script = new Script
|
||||
{
|
||||
Header = new ScriptHeader(0, 0, 0, 0, 0, 0),
|
||||
Instructions = new[] { ins },
|
||||
IndexByOffset = new Dictionary<int, int> { { 0, 0 } },
|
||||
Strings = new Dictionary<int, string>(),
|
||||
};
|
||||
var vm = new VirtualMachine(script, table, new FakeSizeHost());
|
||||
vm.Run();
|
||||
Assert.Equal(0x140, vm.Globals[60]);
|
||||
Assert.Equal(0xC8, vm.Globals[61]);
|
||||
}
|
||||
}
|
||||
@@ -18,6 +18,7 @@ public class TextureOpsTests
|
||||
public void CreateTexture(int slot, int w, int h) => Creates++;
|
||||
public void SetTexture(long resId, int slot) => Sets.Add((resId, slot));
|
||||
public void DrawTexture(int slot, int srcX, int srcY, int w, int h, int dstX, int dstY) => Draws.Add((slot, w, h));
|
||||
public (int Width, int Height) GetTextureSize(int slot) => (0, 0);
|
||||
public void PlayBgm(long id) { }
|
||||
public void PlayVoice(long id) { }
|
||||
}
|
||||
|
||||
@@ -17,6 +17,7 @@ public class WaitForInputTests
|
||||
public void CreateTexture(int slot, int w, int h) { }
|
||||
public void SetTexture(long resId, int slot) { }
|
||||
public void DrawTexture(int slot, int srcX, int srcY, int w, int h, int dstX, int dstY) { }
|
||||
public (int Width, int Height) GetTextureSize(int slot) => (0, 0);
|
||||
public void PlayBgm(long id) { }
|
||||
public void PlayVoice(long id) { }
|
||||
}
|
||||
|
||||
@@ -11,6 +11,7 @@ public sealed class CaptureHost : IHost
|
||||
public void CreateTexture(int slot, int width, int height) { }
|
||||
public void SetTexture(long resourceId, int slot) { }
|
||||
public void DrawTexture(int slot, int srcX, int srcY, int width, int height, int dstX, int dstY) { }
|
||||
public (int Width, int Height) GetTextureSize(int slot) => (0, 0);
|
||||
public void PlayBgm(long id) { }
|
||||
public void PlayVoice(long id) { }
|
||||
}
|
||||
|
||||
@@ -8,6 +8,7 @@ public interface IHost
|
||||
void CreateTexture(int slot, int width, int height);
|
||||
void SetTexture(long resourceId, int slot);
|
||||
void DrawTexture(int slot, int srcX, int srcY, int width, int height, int dstX, int dstY);
|
||||
(int Width, int Height) GetTextureSize(int slot);
|
||||
void PlayBgm(long id);
|
||||
void PlayVoice(long id);
|
||||
}
|
||||
|
||||
@@ -175,6 +175,12 @@ public sealed class VirtualMachine
|
||||
case "draw-texture": // (handle, slot, srcX, srcY, w, h, dstX, dstY)
|
||||
_host.DrawTexture((int)Read(a[1]), (int)Read(a[2]), (int)Read(a[3]), (int)Read(a[4]),
|
||||
(int)Read(a[5]), (int)Read(a[6]), (int)Read(a[7])); return pc + 1;
|
||||
case "get-texture-size": // 0x208 (slot) (out_w) (out_h)
|
||||
{
|
||||
var (gw, gh) = _host.GetTextureSize((int)Read(a[0]));
|
||||
Write(a[1], gw); Write(a[2], gh);
|
||||
return pc + 1;
|
||||
}
|
||||
case "play-bgm": _host.PlayBgm(Read(a[0])); return pc + 1;
|
||||
case "play-voice": _host.PlayVoice(Read(a[0])); return pc + 1;
|
||||
default:
|
||||
|
||||
Reference in New Issue
Block a user