feat(render): implement Campaign AR and terrain fidelity
This commit is contained in:
parent
99cf26e00c
commit
7a5f96ede5
368 changed files with 50611 additions and 950 deletions
|
|
@ -1,6 +1,7 @@
|
|||
using System.Text.Json;
|
||||
using AcDream.App.Diagnostics;
|
||||
using AcDream.App.Rendering;
|
||||
using AcDream.App.Rendering.Packs;
|
||||
using AcDream.App.Rendering.Residency;
|
||||
using AcDream.App.Rendering.Scene;
|
||||
using AcDream.App.Streaming;
|
||||
|
|
@ -82,6 +83,70 @@ public sealed class WorldLifecycleAutomationControllerTests
|
|||
}
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ScreenshotCapture_WritesRenderPackChoiceAndAtmosphereMetadata()
|
||||
{
|
||||
string directory = NewDirectory();
|
||||
var diagnostics = new RenderPackDiagnosticsSnapshot(
|
||||
RenderPackActivationState.Active,
|
||||
"acdream.atmospheric",
|
||||
"1.0.0",
|
||||
"high",
|
||||
"medium",
|
||||
FailureReason: null,
|
||||
ActivationGeneration: 7,
|
||||
RetainedGpuBytes: 64,
|
||||
TransientGpuBytes: 32,
|
||||
ImageCount: 5,
|
||||
BufferCount: 2,
|
||||
DrawCalls: 12,
|
||||
DispatchCalls: 4,
|
||||
ShadowCasterCount: 22,
|
||||
CascadeDrawCount: 44,
|
||||
CpuClassificationCalls: 1,
|
||||
SunElevationDegrees: 14.5,
|
||||
ActiveDayGroup: 2,
|
||||
Weather: "Clear",
|
||||
WeatherIntensity: 0.25,
|
||||
Outdoor: true,
|
||||
DirectionalShadowStrength: 0.8,
|
||||
Passes: [])
|
||||
{
|
||||
SharedWorldTransformUsedInstances = 68_395,
|
||||
};
|
||||
var controller = new FrameScreenshotController(
|
||||
(_, _) => [255, 255, 255, 255],
|
||||
directory,
|
||||
renderPackMetadata: () => diagnostics);
|
||||
Assert.Contains(
|
||||
"worldTransforms=68395used",
|
||||
RenderPackDiagnosticsFormatter.Format(diagnostics),
|
||||
StringComparison.Ordinal);
|
||||
|
||||
try
|
||||
{
|
||||
Assert.True(controller.TryRequest("enhanced", out string error), error);
|
||||
Assert.True(controller.CapturePending(1, 1));
|
||||
|
||||
using JsonDocument metadata = JsonDocument.Parse(
|
||||
File.ReadAllText(Path.Combine(directory, "enhanced.metadata.json")));
|
||||
JsonElement root = metadata.RootElement;
|
||||
Assert.Equal(1, root.GetProperty("SchemaVersion").GetInt32());
|
||||
JsonElement pack = root.GetProperty("RenderPack");
|
||||
Assert.Equal("acdream.atmospheric", pack.GetProperty("PackId").GetString());
|
||||
Assert.Equal("medium", pack.GetProperty("EffectiveQuality").GetString());
|
||||
Assert.Equal(14.5, pack.GetProperty("SunElevationDegrees").GetDouble());
|
||||
Assert.True(pack.GetProperty("Outdoor").GetBoolean());
|
||||
Assert.Equal(
|
||||
68_395u,
|
||||
pack.GetProperty("SharedWorldTransformUsedInstances").GetUInt32());
|
||||
}
|
||||
finally
|
||||
{
|
||||
Directory.Delete(directory, recursive: true);
|
||||
}
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData("")]
|
||||
[InlineData("../escape")]
|
||||
|
|
@ -377,6 +442,7 @@ public sealed class WorldLifecycleAutomationControllerTests
|
|||
var screenshots = new FrameScreenshotController(
|
||||
(_, _) => [0, 0, 0, 255],
|
||||
Path.Combine(directory, "screenshots"));
|
||||
int clientCloseRequests = 0;
|
||||
var controller = new WorldLifecycleAutomationController(
|
||||
() => reveal,
|
||||
() => new RuntimeWorldEnvironmentOwnershipSnapshot(
|
||||
|
|
@ -395,13 +461,18 @@ public sealed class WorldLifecycleAutomationControllerTests
|
|||
() => 3,
|
||||
_ => resources,
|
||||
screenshots,
|
||||
directory);
|
||||
directory,
|
||||
requestClientClose: () => clientCloseRequests++);
|
||||
|
||||
try
|
||||
{
|
||||
Assert.True(controller.IsWorldReady);
|
||||
Assert.True(controller.IsWorldViewportVisible);
|
||||
Assert.Equal(3, controller.PortalMaterializationCount);
|
||||
Assert.True(
|
||||
controller.TryRequestClientClose(out string closeError),
|
||||
closeError);
|
||||
Assert.Equal(1, clientCloseRequests);
|
||||
Assert.True(controller.TryRequestCheckpoint(
|
||||
"dungeon",
|
||||
out IRetailUiAutomationCheckpoint? request,
|
||||
|
|
@ -591,6 +662,115 @@ public sealed class WorldLifecycleAutomationControllerTests
|
|||
}
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RenderPackPerformanceReset_IsNoOpOnlyAfterFailedToRetail()
|
||||
{
|
||||
string directory = NewDirectory();
|
||||
bool failedToRetail = true;
|
||||
int resetCalls = 0;
|
||||
var controller = new WorldLifecycleAutomationController(
|
||||
() => default,
|
||||
() => default,
|
||||
() => default,
|
||||
() => 0,
|
||||
_ => EmptyResources(),
|
||||
new FrameScreenshotController((_, _) => [], directory),
|
||||
directory,
|
||||
getRenderPackPerformanceSampleCount: () => 0,
|
||||
resetRenderPackPerformance: () =>
|
||||
{
|
||||
resetCalls++;
|
||||
return (true, string.Empty);
|
||||
},
|
||||
getRenderPackFailedToRetail: () => failedToRetail);
|
||||
|
||||
try
|
||||
{
|
||||
Assert.True(controller.RenderPackFailedToRetail);
|
||||
Assert.True(controller.TryResetRenderPackPerformance(out string fallbackError));
|
||||
Assert.Empty(fallbackError);
|
||||
Assert.Equal(0, resetCalls);
|
||||
|
||||
failedToRetail = false;
|
||||
Assert.True(controller.TryResetRenderPackPerformance(out string activeError));
|
||||
Assert.Empty(activeError);
|
||||
Assert.Equal(1, resetCalls);
|
||||
}
|
||||
finally
|
||||
{
|
||||
controller.Dispose();
|
||||
Directory.Delete(directory, recursive: true);
|
||||
}
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void TransitionAutomationDelegatesPreserveExactDisableReenableAndResizeOwnership()
|
||||
{
|
||||
string directory = NewDirectory();
|
||||
var status = new RetailUiAutomationRenderPackStatus(
|
||||
RetailUiAutomationRenderPackState.Active,
|
||||
"acdream.atmospheric",
|
||||
"medium",
|
||||
ActivationGeneration: 1,
|
||||
FailureReason: null);
|
||||
var framebuffer = (Width: 1280, Height: 720);
|
||||
var calls = new List<string>();
|
||||
var controller = new WorldLifecycleAutomationController(
|
||||
() => default,
|
||||
() => default,
|
||||
() => default,
|
||||
() => 0,
|
||||
_ => EmptyResources(),
|
||||
new FrameScreenshotController((_, _) => [], directory),
|
||||
directory,
|
||||
getRenderPackStatus: () => status,
|
||||
selectRenderPack: preset =>
|
||||
{
|
||||
calls.Add($"select:{preset}");
|
||||
return (true, string.Empty);
|
||||
},
|
||||
disableRenderPack: () =>
|
||||
{
|
||||
calls.Add("disable-exact");
|
||||
return (true, string.Empty);
|
||||
},
|
||||
reenableRenderPack: () =>
|
||||
{
|
||||
calls.Add("reenable-exact");
|
||||
return (true, string.Empty);
|
||||
},
|
||||
getFramebufferSize: () => framebuffer,
|
||||
resizeFramebuffer: (width, height) =>
|
||||
{
|
||||
calls.Add($"resize:{width}x{height}");
|
||||
framebuffer = (width, height);
|
||||
return (true, string.Empty);
|
||||
});
|
||||
|
||||
try
|
||||
{
|
||||
Assert.Equal(status, controller.RenderPackStatus);
|
||||
Assert.True(controller.TrySelectRenderPack("high", out string selectError));
|
||||
Assert.Empty(selectError);
|
||||
Assert.True(controller.TryDisableRenderPack(out string disableError));
|
||||
Assert.Empty(disableError);
|
||||
Assert.True(controller.TryReenableRenderPack(out string reenableError));
|
||||
Assert.Empty(reenableError);
|
||||
Assert.True(controller.TryResizeFramebuffer(1024, 768, out string resizeError));
|
||||
Assert.Empty(resizeError);
|
||||
Assert.Equal(1024, controller.FramebufferWidth);
|
||||
Assert.Equal(768, controller.FramebufferHeight);
|
||||
Assert.Equal(
|
||||
["select:high", "disable-exact", "reenable-exact", "resize:1024x768"],
|
||||
calls);
|
||||
}
|
||||
finally
|
||||
{
|
||||
controller.Dispose();
|
||||
Directory.Delete(directory, recursive: true);
|
||||
}
|
||||
}
|
||||
|
||||
private static WorldLifecycleAutomationController CreateController(
|
||||
string directory,
|
||||
Func<RenderFrameOutcome, WorldLifecycleResourceSnapshot> capture) =>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue