diff --git a/Assets/Scripts/ServerShared/Scenarios/Broadside.cs b/Assets/Scripts/ServerShared/Scenarios/Broadside.cs deleted file mode 100644 index 8634b3394..000000000 --- a/Assets/Scripts/ServerShared/Scenarios/Broadside.cs +++ /dev/null @@ -1,37 +0,0 @@ -using static CultMath.math; -using static ItemRotation; - -public sealed class Broadside : Scenario -{ - public override string Name => "Broadside"; - public override string Brief => "A hull with a port gun and a starboard gun in separate groups, bare hulls abeam to port and starboard and one ahead. " + - "Verify: designate the starboard hull, aim ahead and fire the starboard group: it fires on the hull without the aim. " + - "Fire the port group: it holds, because nothing bears and the aim is outside its arc. Undesignate and aim to port: " + - "the port group fires free along the aim."; - public override uint Seed => 104; - public override bool Ambient => false; - - // Where the targets sit: the player is at the origin facing +z. - public static readonly CultMath.float2 Port = float2(-400, 0), Starboard = float2(400, 0), Ahead = float2(0, 400); - - public override Galaxy Generate(GalaxyStage stage) => stage.Prelude(); - - public override void Stage(ScenarioStage stage) - { - var broadside = stage.Fit("LonginusX", - ("Cockpit 2x2", int2(2, 6), None), - ("Traction", int2(2, 3), None), - ("Core Power", int2(2, 1), None), - ("GT 3K", int2(0, 5), CounterClockwise), - ("FastBlast+-", int2(4, 8), Clockwise), - ("Iapyx", int2(1, 2), CounterClockwise), - ("Iapyx", int2(4, 2), Clockwise), - ("not if i see you first", int2(3, 10), None), - ("Fire Control Array", int2(2, 5), None)); - - stage.Player(broadside, float2(0, 0), facing: float2(0, 1)); - stage.Place(stage.Bare("LonginusX"), Port); - stage.Place(stage.Bare("LonginusX"), Starboard); - stage.Place(stage.Bare("LonginusX"), Ahead); - } -} diff --git a/Assets/Scripts/ServerShared/Scenarios/Broadside.cs.meta b/Assets/Scripts/ServerShared/Scenarios/Broadside.cs.meta deleted file mode 100644 index 439908d94..000000000 --- a/Assets/Scripts/ServerShared/Scenarios/Broadside.cs.meta +++ /dev/null @@ -1,11 +0,0 @@ -fileFormatVersion: 2 -guid: 9fb4b5cf800b4ccdae5d6c15448df36e -MonoImporter: - externalObjects: {} - serializedVersion: 2 - defaultReferences: [] - executionOrder: 0 - icon: {instanceID: 0} - userData: - assetBundleName: - assetBundleVariant: diff --git a/Assets/Scripts/ServerShared/Scenarios/Scenarios.cs b/Assets/Scripts/ServerShared/Scenarios/Scenarios.cs index 935aa103f..31890d789 100644 --- a/Assets/Scripts/ServerShared/Scenarios/Scenarios.cs +++ b/Assets/Scripts/ServerShared/Scenarios/Scenarios.cs @@ -6,6 +6,6 @@ public static class Scenarios public static readonly Scenario[] Tests = { - new DjinniShakedown(), new StarvedReactor(), new Arcs(), new Broadside(), new Duel(), new LauncherAngles(), new LongHaul() + new DjinniShakedown(), new StarvedReactor(), new Arcs(), new Duel(), new LauncherAngles(), new LongHaul() }; } diff --git a/tests/Aetheria.Shared.Tests/FireControlCut5Tests.cs b/tests/Aetheria.Shared.Tests/FireControlCut5Tests.cs index d27857104..6134b777b 100644 --- a/tests/Aetheria.Shared.Tests/FireControlCut5Tests.cs +++ b/tests/Aetheria.Shared.Tests/FireControlCut5Tests.cs @@ -364,6 +364,7 @@ public sealed class FireControlCut5Tests : IDisposable var settings = TestSettings(); settings.FiringArc = 60; // narrow -- an abeam target is well outside it var e = BuildBeam(settings, float3(100, 0, 0)); // directly abeam + e.Shooter.Aim = float3(0, 0, -1); // astern, outside the arc: nothing bears and the aim is not free e.Weapon.Activate(); Assert.True(e.Weapon.Firing); // Activate() sets _firing unconditionally, same as InstantWeapon.Trigger @@ -466,6 +467,7 @@ public sealed class FireControlCut5Tests : IDisposable shooter.Position = float3.zero; target.Position = float3(100, 0, 0); // directly abeam shooter.SetTarget(target); + shooter.Aim = float3(0, 0, -1); // astern, outside the arc: only a solution can fire the gun var weapon = (Weapon) weaponItem.Behaviors.Single(b => b is Weapon); Assert.False(weapon.ArcAllowsFire); @@ -489,6 +491,7 @@ public sealed class FireControlCut5Tests : IDisposable e.Shooter.Position = float3.zero; e.Target.Position = float3(100, 0, 0); // abeam -- outside the narrow 60-degree arc e.Shooter.SetTarget(e.Target); + e.Shooter.Aim = float3(0, 0, -1); // astern, outside the arc: nothing bears and the aim is not free var resolvedCount = 0; e.Zone.ShotResolved.Subscribe(_ => resolvedCount++); diff --git a/tests/Aetheria.Shared.Tests/ScenarioTests.cs b/tests/Aetheria.Shared.Tests/ScenarioTests.cs index f24cc8d38..cfd5cc174 100644 --- a/tests/Aetheria.Shared.Tests/ScenarioTests.cs +++ b/tests/Aetheria.Shared.Tests/ScenarioTests.cs @@ -500,32 +500,6 @@ public sealed partial class RunStartTests Assert.False(player.IsHostileTo(bow) || player.IsHostileTo(stern), "the bare hulls are neutral"); } - // Broadside's geometry: the player carries guns on both sides in separate groups. Each side's gun bears on the hull - // abeam on its side and on nothing else, and the hull ahead bears for neither. - [Fact] - public void BroadsideGeometry() - { - var staged = Stage(Arena(false), new Broadside()); - var player = staged.Player; - var port = staged.Entities[0]; - var starboard = staged.Entities[1]; - var ahead = staged.Entities[2]; - Assert.Equal((Broadside.Port, Broadside.Starboard, Broadside.Ahead), (port.Position.xz, starboard.Position.xz, ahead.Position.xz)); - - var groups = player.WeaponGroups.Where(group => group.items.Count > 0).ToList(); - Assert.True(groups.Count >= 2, "the guns must sit in separate groups"); - var portGun = Assert.Single(groups.SelectMany(group => group.items).Where(item => item.EquippableItem.Rotation == ItemRotation.CounterClockwise && item.Behaviors.OfType().Any())); - var starboardGun = Assert.Single(groups.SelectMany(group => group.items).Where(item => item.EquippableItem.Rotation == ItemRotation.Clockwise && item.Behaviors.OfType().Any())); - Assert.NotEqual(groups.Single(group => group.items.Contains(portGun)).items, groups.Single(group => group.items.Contains(starboardGun)).items); - - Assert.True(FireControl.InArc(portGun, port.Position - player.Position)); - Assert.False(FireControl.InArc(portGun, starboard.Position - player.Position)); - Assert.False(FireControl.InArc(portGun, ahead.Position - player.Position)); - Assert.True(FireControl.InArc(starboardGun, starboard.Position - player.Position)); - Assert.False(FireControl.InArc(starboardGun, port.Position - player.Position)); - Assert.False(FireControl.InArc(starboardGun, ahead.Position - player.Position)); - } - // Q3 (operator, 2026-09-30): a design no product sells is a scenario test design and nothing else. A test design // is one some scenario's staged entities carry, fitted or in cargo. These are the unsold designs none carries. private List UnsoldAndUnplaced(IEnumerable runs)