114 lines
4.2 KiB
C#
114 lines
4.2 KiB
C#
using AcDream.App.Rendering;
|
|
using AcDream.App.Rendering.Packs;
|
|
|
|
namespace AcDream.App.Tests.Rendering.Packs;
|
|
|
|
public sealed class AtmosphericAutoQualityControllerTests
|
|
{
|
|
[Fact]
|
|
public void Downgrade_requires_long_consecutive_over_budget_window()
|
|
{
|
|
var controller = new AtmosphericAutoQualityController(
|
|
AtmosphericQualityLevel.High);
|
|
var sample = new AtmosphericQualityMeasurement(
|
|
InclusivePackGpuMillisecondsP99: 7.0,
|
|
IncrementalCpuMillisecondsP99: 1.1,
|
|
ResidentGpuBytes: 250L * 1024 * 1024,
|
|
StableFrameBoundary: true);
|
|
|
|
for (int i = 0;
|
|
i < AtmosphericAutoQualityController.DowngradeHysteresisFrames - 1;
|
|
i++)
|
|
controller.Observe(in sample);
|
|
Assert.Equal(AtmosphericQualityLevel.High, controller.Snapshot.Current);
|
|
|
|
AtmosphericAutoQualitySnapshot changed = controller.Observe(in sample);
|
|
Assert.Equal(AtmosphericQualityLevel.Medium, changed.Current);
|
|
Assert.Equal(AtmosphericAutoQualityController.ChangeCooldownFrames,
|
|
changed.CooldownFramesRemaining);
|
|
}
|
|
|
|
[Fact]
|
|
public void Unstable_frames_never_advance_hysteresis()
|
|
{
|
|
var controller = new AtmosphericAutoQualityController(
|
|
AtmosphericQualityLevel.High);
|
|
var sample = new AtmosphericQualityMeasurement(20, 20, 0, false);
|
|
|
|
for (int i = 0; i < 1000; i++)
|
|
controller.Observe(in sample);
|
|
|
|
Assert.Equal(AtmosphericQualityLevel.High, controller.Snapshot.Current);
|
|
Assert.Equal(0, controller.Snapshot.ConsecutiveOverBudgetFrames);
|
|
}
|
|
|
|
[Fact]
|
|
public void Upgrade_requires_nine_hundred_headroom_frames()
|
|
{
|
|
var controller = new AtmosphericAutoQualityController(
|
|
AtmosphericQualityLevel.Low);
|
|
var sample = new AtmosphericQualityMeasurement(
|
|
InclusivePackGpuMillisecondsP99: 0.5,
|
|
IncrementalCpuMillisecondsP99: 0.1,
|
|
ResidentGpuBytes: 16L * 1024 * 1024,
|
|
StableFrameBoundary: true);
|
|
|
|
for (int i = 0;
|
|
i < AtmosphericAutoQualityController.UpgradeHysteresisFrames - 1;
|
|
i++)
|
|
controller.Observe(in sample);
|
|
Assert.Equal(AtmosphericQualityLevel.Low, controller.Snapshot.Current);
|
|
|
|
Assert.Equal(
|
|
AtmosphericQualityLevel.Medium,
|
|
controller.Observe(in sample).Current);
|
|
}
|
|
|
|
[Fact]
|
|
public void LowRequestsWholePackFallbackWithoutDroppingHeadlineSemantics()
|
|
{
|
|
var controller = new AtmosphericAutoQualityController(
|
|
AtmosphericQualityLevel.Low);
|
|
var sample = new AtmosphericQualityMeasurement(100, 100, long.MaxValue, true);
|
|
|
|
for (int i = 0;
|
|
i < AtmosphericAutoQualityController.DowngradeHysteresisFrames - 1;
|
|
i++)
|
|
controller.Observe(in sample);
|
|
|
|
Assert.Equal(AtmosphericQualityLevel.Low, controller.Snapshot.Current);
|
|
Assert.False(controller.Snapshot.SafeFallbackToRetailRequested);
|
|
|
|
AtmosphericAutoQualitySnapshot fallback = controller.Observe(in sample);
|
|
|
|
Assert.Equal(AtmosphericQualityLevel.Low, fallback.Current);
|
|
Assert.True(fallback.SafeFallbackToRetailRequested);
|
|
Assert.Equal(
|
|
DirectionalShadowSemantics.Headline,
|
|
DirectionalShadowQuality.For(DirectionalShadowPreset.Low).Semantics);
|
|
}
|
|
|
|
[Fact]
|
|
public void PackDeclaredBudgetsAreTheAutomaticQualityAuthority()
|
|
{
|
|
AtmosphericQualityBudget[] budgets =
|
|
[
|
|
new(0.5, 0.1, 16 * 1024 * 1024),
|
|
new(1.0, 0.2, 32 * 1024 * 1024),
|
|
new(1.5, 0.3, 64 * 1024 * 1024),
|
|
];
|
|
var controller = new AtmosphericAutoQualityController(
|
|
budgets,
|
|
AtmosphericQualityLevel.High);
|
|
var sample = new AtmosphericQualityMeasurement(
|
|
InclusivePackGpuMillisecondsP99: 1.6,
|
|
IncrementalCpuMillisecondsP99: 0.1,
|
|
ResidentGpuBytes: 8 * 1024 * 1024,
|
|
StableFrameBoundary: true);
|
|
|
|
for (int i = 0; i < AtmosphericAutoQualityController.DowngradeHysteresisFrames; i++)
|
|
controller.Observe(in sample);
|
|
|
|
Assert.Equal(AtmosphericQualityLevel.Medium, controller.Snapshot.Current);
|
|
}
|
|
}
|