From 7dc33471810037cf5e89b28f0d1873eef271d52f Mon Sep 17 00:00:00 2001 From: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> Date: Wed, 13 Sep 2023 22:06:15 +1000 Subject: [PATCH] Fix planet docking (#20104) --- .../Tests/PostMapInitTest.cs | 1 + .../Tests/Shuttle/DockTest.cs | 46 +++++++++++++++++++ .../Shuttles/Systems/DockingSystem.Shuttle.cs | 39 ++++++++++++++-- .../Shuttles/Systems/DockingSystem.cs | 4 ++ 4 files changed, 85 insertions(+), 5 deletions(-) diff --git a/Content.IntegrationTests/Tests/PostMapInitTest.cs b/Content.IntegrationTests/Tests/PostMapInitTest.cs index 6f3bdcc524..b444aa43c7 100644 --- a/Content.IntegrationTests/Tests/PostMapInitTest.cs +++ b/Content.IntegrationTests/Tests/PostMapInitTest.cs @@ -185,6 +185,7 @@ namespace Content.IntegrationTests.Tests var grids = mapManager.GetAllMapGrids(mapId).ToList(); var gridUids = grids.Select(o => o.Owner).ToList(); + targetGrid = gridUids.First(); foreach (var grid in grids) { diff --git a/Content.IntegrationTests/Tests/Shuttle/DockTest.cs b/Content.IntegrationTests/Tests/Shuttle/DockTest.cs index d08d0a74c2..3404c9fbbb 100644 --- a/Content.IntegrationTests/Tests/Shuttle/DockTest.cs +++ b/Content.IntegrationTests/Tests/Shuttle/DockTest.cs @@ -1,9 +1,12 @@ using System.Collections.Generic; +using System.Linq; using System.Numerics; using Content.Server.Shuttles.Systems; using Content.Tests; +using Robust.Server.GameObjects; using Robust.Shared.GameObjects; using Robust.Shared.Map; +using Robust.Shared.Map.Components; using Robust.Shared.Maths; namespace Content.IntegrationTests.Tests.Shuttle; @@ -80,4 +83,47 @@ public sealed class DockTest : ContentUnitTest await pair.CleanReturnAsync(); } + + [Test] + public async Task TestPlanetDock() + { + await using var pair = await PoolManager.GetServerClient(); + var server = pair.Server; + + var map = await pair.CreateTestMap(); + var otherMap = await pair.CreateTestMap(); + + var entManager = server.ResolveDependency(); + var mapManager = server.ResolveDependency(); + var dockingSystem = entManager.System(); + var xformSystem = entManager.System(); + var mapSystem = entManager.System(); + + var mapGrid = entManager.AddComponent(map.MapUid); + var shuttle = EntityUid.Invalid; + + // Spawn shuttle and affirm no valid docks. + await server.WaitAssertion(() => + { + entManager.DeleteEntity(map.GridUid); + Assert.That(entManager.System().TryLoad(otherMap.MapId, "/Maps/Shuttles/emergency.yml", out var rootUids)); + shuttle = rootUids[0]; + + var dockingConfig = dockingSystem.GetDockingConfig(shuttle, map.MapUid); + Assert.That(dockingConfig, Is.EqualTo(null)); + }); + + // Spawn dock and affirm it docks with no blockers / doesn't dock with blockers + await server.WaitAssertion(() => + { + mapSystem.SetTile(map.MapUid, mapGrid, Vector2i.Zero, new Tile(1)); + var airlockEnt = entManager.SpawnEntity("AirlockShuttle", new EntityCoordinates(map.MapUid, Vector2.One / 2f)); + Assert.That(entManager.GetComponent(airlockEnt).Anchored); + + var dockingConfig = dockingSystem.GetDockingConfig(shuttle, map.MapUid); + Assert.That(dockingConfig, Is.Not.EqualTo(null)); + }); + + await pair.CleanReturnAsync(); + } } diff --git a/Content.Server/Shuttles/Systems/DockingSystem.Shuttle.cs b/Content.Server/Shuttles/Systems/DockingSystem.Shuttle.cs index c393da69fa..6ad113f3da 100644 --- a/Content.Server/Shuttles/Systems/DockingSystem.Shuttle.cs +++ b/Content.Server/Shuttles/Systems/DockingSystem.Shuttle.cs @@ -46,6 +46,7 @@ public sealed partial class DockingSystem Angle targetGridRotation, FixturesComponent shuttleFixtures, MapGridComponent grid, + bool isMap, out Matrix3 matty, out Box2 shuttleDockedAABB, out Angle gridRotation) @@ -75,7 +76,7 @@ public sealed partial class DockingSystem var gridXformMatrix = Matrix3.CreateTransform(gridDockXform.LocalPosition, gridDockAngle); Matrix3.Multiply(in stationDockMatrix, in gridXformMatrix, out matty); - if (!ValidSpawn(grid, matty, offsetAngle, shuttleFixtures)) + if (!ValidSpawn(grid, matty, offsetAngle, shuttleFixtures, isMap)) return false; shuttleDockedAABB = matty.TransformBox(shuttleAABB); @@ -136,6 +137,8 @@ public sealed partial class DockingSystem var shuttleFixturesComp = Comp(shuttleUid); var shuttleAABB = Comp(shuttleUid).LocalAABB; + var isMap = HasComp(targetGrid); + var validDockConfigs = new List(); if (shuttleDocks.Count > 0) { @@ -155,6 +158,7 @@ public sealed partial class DockingSystem targetGridAngle, shuttleFixturesComp, targetGridGrid, + isMap, out var matty, out var dockedAABB, out var targetAngle)) @@ -205,6 +209,7 @@ public sealed partial class DockingSystem shuttleAABB, targetGridAngle, shuttleFixturesComp, targetGridGrid, + isMap, out _, out var otherdockedAABB, out var otherTargetAngle)) @@ -255,9 +260,9 @@ public sealed partial class DockingSystem } /// - /// Checks whether the emergency shuttle can warp to the specified position. + /// Checks whether the shuttle can warp to the specified position. /// - private bool ValidSpawn(MapGridComponent grid, Matrix3 matty, Angle angle, FixturesComponent shuttleFixturesComp) + private bool ValidSpawn(MapGridComponent grid, Matrix3 matty, Angle angle, FixturesComponent shuttleFixturesComp, bool isMap) { var transform = new Transform(matty.Transform(Vector2.Zero), angle); @@ -268,8 +273,32 @@ public sealed partial class DockingSystem var aabb = polyShape.ComputeAABB(transform, 0); aabb = aabb.Enlarged(-0.01f); - if (grid.GetLocalTilesIntersecting(aabb).Any()) - return false; + // If it's a map check no hard collidable anchored entities overlap + if (isMap) + { + foreach (var tile in grid.GetLocalTilesIntersecting(aabb)) + { + var anchoredEnumerator = grid.GetAnchoredEntitiesEnumerator(tile.GridIndices); + + while (anchoredEnumerator.MoveNext(out var anc)) + { + if (!_physicsQuery.TryGetComponent(anc, out var physics) || + !physics.CanCollide || + !physics.Hard) + { + continue; + } + + return false; + } + } + } + // If it's not a map check it doesn't overlap the grid. + else + { + if (grid.GetLocalTilesIntersecting(aabb).Any()) + return false; + } } return true; diff --git a/Content.Server/Shuttles/Systems/DockingSystem.cs b/Content.Server/Shuttles/Systems/DockingSystem.cs index a00a9e0f58..ba75ef3284 100644 --- a/Content.Server/Shuttles/Systems/DockingSystem.cs +++ b/Content.Server/Shuttles/Systems/DockingSystem.cs @@ -32,9 +32,13 @@ namespace Content.Server.Shuttles.Systems private const string DockingJoint = "docking"; private const float DockingRadius = 0.20f; + private EntityQuery _physicsQuery; + public override void Initialize() { base.Initialize(); + _physicsQuery = GetEntityQuery(); + SubscribeLocalEvent(OnStartup); SubscribeLocalEvent(OnShutdown); SubscribeLocalEvent(OnAnchorChange); -- 2.51.2