Implement ADV text publication service
This commit is contained in:
@@ -53,4 +53,24 @@ public class AdvTextOpsTests
|
||||
Assert.Equal(new Age.Engine.Hosting.AdvWaitIndicatorConfig(1, 385, 140, 12, 0, 0, 30, 27, 12, 48),
|
||||
Assert.Single(host.WaitIndicators));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void WaitIndicatorToggleAndTextLayoutPublicationReachHost()
|
||||
{
|
||||
var table = OpcodeTableJson.Load(Paths.OpcodesJson);
|
||||
var script = ScriptAssembler.Assemble(table, "WAITMARK_SERVICE",
|
||||
new List<(int, Operand[])>
|
||||
{
|
||||
(0x1ce, new[] { new Operand(0, 1) }),
|
||||
(0x20a, new[] { new Operand(0, 4) }),
|
||||
(0x1ce, new[] { new Operand(0, 0) }),
|
||||
(0x2, Array.Empty<Operand>()),
|
||||
}, Array.Empty<string>());
|
||||
var host = new RecordingHost();
|
||||
|
||||
new VirtualMachine(script, table, host).Run();
|
||||
|
||||
Assert.Equal(new[] { true, false }, host.WaitIndicatorEnabledChanges);
|
||||
Assert.Equal(4, Assert.Single(host.PublishedAdvTextLayouts));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -295,6 +295,8 @@ public class HistoryInteractionOpsTests
|
||||
Assert.Equal(1, host.Waits); // the enclosing ADV page was never released or re-entered
|
||||
Assert.Equal(1, host.HistoryPresentationEnds);
|
||||
Assert.Empty(host.ActiveHistoryRenders);
|
||||
Assert.Contains(false, host.WaitIndicatorEnabledChanges);
|
||||
Assert.Contains(1, host.PublishedAdvTextLayouts);
|
||||
|
||||
var historyButtons = host.FirstHistoryFrame
|
||||
.Where(render => render.Handle >= 0xd2fa && render.Handle <= 0xd300)
|
||||
|
||||
@@ -102,5 +102,6 @@ public class HistoryPresentationOpsTests
|
||||
Assert.All(host.HistoryRenders.Where(render => render.Text.Length > 0),
|
||||
render => Assert.Equal(8, render.Style.LineSpacing));
|
||||
Assert.Contains(host.PresentedRanges, range => range == (0L, 60000L));
|
||||
Assert.Contains(false, host.WaitIndicatorEnabledChanges);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -24,6 +24,8 @@ internal class RecordingHost : IHost
|
||||
public readonly List<SurfaceRectFill> SurfaceFills = new();
|
||||
public readonly List<(long First, long Count)> PresentedRanges = new();
|
||||
public readonly List<AdvWaitIndicatorConfig> WaitIndicators = new();
|
||||
public readonly List<bool> WaitIndicatorEnabledChanges = new();
|
||||
public readonly List<int> PublishedAdvTextLayouts = new();
|
||||
public readonly List<long> SleptDurations = new();
|
||||
public readonly List<(long Resource, int Channel)> SfxLoads = new();
|
||||
public readonly List<long> Voices = new();
|
||||
@@ -62,6 +64,8 @@ internal class RecordingHost : IHost
|
||||
public void PresentObjectRange(GfxState gfx, long firstHandle, long count)
|
||||
=> PresentedRanges.Add((firstHandle, count));
|
||||
public void ConfigureAdvWaitIndicator(AdvWaitIndicatorConfig config) => WaitIndicators.Add(config);
|
||||
public void SetAdvWaitIndicatorEnabled(bool enabled) => WaitIndicatorEnabledChanges.Add(enabled);
|
||||
public void PublishAdvTextLayout(int layoutSlot) => PublishedAdvTextLayouts.Add(layoutSlot);
|
||||
public void SetAdvPagePresentationSuspended(bool suspended)
|
||||
=> AdvPagePresentationSuspended.Add(suspended);
|
||||
public void WaitForInput() => Waits++;
|
||||
|
||||
@@ -31,6 +31,10 @@ public interface IHost
|
||||
void FillSurfaceRect(SurfaceRectFill fill) { }
|
||||
void PresentObjectRange(GfxState gfx, long firstHandle, long count) { }
|
||||
void ConfigureAdvWaitIndicator(AdvWaitIndicatorConfig config) { }
|
||||
// Op 0x1ce explicitly starts/stops the same animated marker that op 0x72 starts for an ADV wait.
|
||||
void SetAdvWaitIndicatorEnabled(bool enabled) { }
|
||||
// Op 0x20a republishes one retained ADV text layout and includes the current marker frame when active.
|
||||
void PublishAdvTextLayout(int layoutSlot) { }
|
||||
// Op 0x199 temporarily yields the active ADV page into its registered hide-window coroutine.
|
||||
// The retained scene continues to render, but the text layout and its wait marker are suspended
|
||||
// until op 0x7c restores the saved page PC.
|
||||
|
||||
@@ -624,6 +624,14 @@ public sealed class VirtualMachine
|
||||
(int)Read(a[4]), (int)Read(a[5]), (int)Read(a[6]), (int)Read(a[7]),
|
||||
(int)Read(a[8]), Read(a[9])));
|
||||
return pc + 1;
|
||||
case "u0041B9F0":
|
||||
case "set-adv-wait-indicator-enabled": // 0x1ce: explicit marker service start/stop
|
||||
_host.SetAdvWaitIndicatorEnabled(Read(a[0]) != 0);
|
||||
return pc + 1;
|
||||
case "u00420CE0":
|
||||
case "publish-adv-text-layout": // 0x20a: publish layout and current marker frame if active
|
||||
_host.PublishAdvTextLayout((int)Read(a[0]));
|
||||
return pc + 1;
|
||||
case "draw-string": // 0x204 (surface slot, x, y, string)
|
||||
_host.DrawStringToSurface((int)Read(a[0]), (int)Read(a[1]), (int)Read(a[2]), ReadStr(a[3]),
|
||||
_advTextStyle);
|
||||
|
||||
Reference in New Issue
Block a user