From 6a5f111c826762429f24d9caecdbecf5b3285e96 Mon Sep 17 00:00:00 2001 From: AlienXAXS Date: Thu, 18 Jul 2024 16:17:36 +0100 Subject: [PATCH 1/3] Enemy Relay Direction Sync --- .../DFRelayDirectionStateChangePacket.cs | 26 ++++++ .../DFRelayDirectionStateChangeProcessor.cs | 49 +++++++++++ .../EnemyDFRelayComponent_Transplier.cs | 86 +++++++++++++++++++ 3 files changed, 161 insertions(+) create mode 100644 NebulaModel/Packets/Combat/DFRelay/DFRelayDirectionStateChangePacket.cs create mode 100644 NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs create mode 100644 NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs diff --git a/NebulaModel/Packets/Combat/DFRelay/DFRelayDirectionStateChangePacket.cs b/NebulaModel/Packets/Combat/DFRelay/DFRelayDirectionStateChangePacket.cs new file mode 100644 index 000000000..c22efbb91 --- /dev/null +++ b/NebulaModel/Packets/Combat/DFRelay/DFRelayDirectionStateChangePacket.cs @@ -0,0 +1,26 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace NebulaModel.Packets.Combat.DFRelay +{ + public class DFRelayDirectionStateChangePacket + { + public DFRelayDirectionStateChangePacket() { } + + public DFRelayDirectionStateChangePacket(in int relayId, in int hiveAstroId, in int stage, in int newDirection) + { + HiveAstroId = hiveAstroId; + RelayId = relayId; + Stage = stage; + NewDirection = newDirection; + } + + public int HiveAstroId { get; set; } + public int RelayId { get; set; } + public int Stage { get; set; } + public int NewDirection { get; set; } + } +} diff --git a/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs b/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs new file mode 100644 index 000000000..66f60ad32 --- /dev/null +++ b/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs @@ -0,0 +1,49 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using NebulaAPI.Packets; +using NebulaModel.Logger; +using NebulaModel.Networking; +using NebulaModel.Packets; +using NebulaModel.Packets.Combat.DFRelay; +using UnityEngine; + +namespace NebulaNetwork.PacketProcessors.Combat.DFRelay +{ + [RegisterPacketProcessor] + public class DFRelayDirectionStateChangeProcessor : PacketProcessor + { + protected override void ProcessPacket(DFRelayDirectionStateChangePacket packet, NebulaConnection conn) + { + var hiveSystem = GameMain.spaceSector.GetHiveByAstroId(packet.HiveAstroId); + if (hiveSystem == null) return; + + var dfRelayComponent = hiveSystem.relays.buffer[packet.RelayId]; + if (dfRelayComponent?.id != packet.RelayId) return; + + Log.Debug($"Relay {dfRelayComponent.id} direction:{dfRelayComponent.direction} will be sent home with a new direction: {packet.NewDirection}"); + + switch (packet.NewDirection) + { + case -1: //Relay is being sent home + dfRelayComponent.targetAstroId = 0; + dfRelayComponent.targetLPos = Vector3.zero; + dfRelayComponent.targetYaw = 0f; + dfRelayComponent.baseState = 0; + dfRelayComponent.baseId = 0; + dfRelayComponent.baseTicks = 0; + dfRelayComponent.baseEvolve = default(EvolveData); + dfRelayComponent.baseRespawnCD = 0; + dfRelayComponent.direction = -1; + dfRelayComponent.param0 = 0f; + + dfRelayComponent.stage = packet.Stage; + + Log.Debug($"Relay {dfRelayComponent.id} returning home"); + break; + } + } + } +} diff --git a/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs b/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs new file mode 100644 index 000000000..5a85feaac --- /dev/null +++ b/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs @@ -0,0 +1,86 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Reflection; +using HarmonyLib; +using System.Reflection.Emit; +using NebulaModel.Logger; +using NebulaModel.Packets.Combat.DFRelay; +using NebulaWorld; + +namespace NebulaPatcher.Patches.Transpilers +{ + [HarmonyPatch(typeof(DFRelayComponent))] + internal class EnemyDFRelayComponent_Transplier + { + [HarmonyTranspiler] + [HarmonyPatch(nameof(DFRelayComponent.RelaySailLogic))] + public static IEnumerable RelaySailLogic_Transpiler(IEnumerable instructions) + { + try + { + // Attempt to match anywhere where `direction = -1` is set. + // Change to: + // direction = -1 + // call UpdateRelayDirectionState(relayId, hive) + + var codeMatcher = new CodeMatcher(instructions); + codeMatcher.MatchForward(true, + new CodeMatch(OpCodes.Ldarg_0), + new CodeMatch(OpCodes.Ldc_I4_M1), + new CodeMatch(i => i.opcode == OpCodes.Stfld && ((FieldInfo)i.operand).Name == "direction")); + + if (codeMatcher.IsInvalid) + { + Log.Error("Transpiler DFRelayComponent.RelaySailLogic matcher is not valid. Mod version not compatible with game version."); + return instructions; + } + + codeMatcher.Repeat(matcher => + { + matcher.InsertAndAdvance( + // Relay ID argument + new CodeInstruction(OpCodes.Ldarg_0), + new CodeInstruction(OpCodes.Ldfld, + AccessTools.Field(typeof(DFRelayComponent), nameof(DFRelayComponent.id))), + + // Hive Astro ID argument + new CodeInstruction(OpCodes.Ldarg_0), + new CodeInstruction(OpCodes.Ldfld, + AccessTools.Field(typeof(DFRelayComponent), nameof(DFRelayComponent.stage))), + + // Hive Astro ID argument + new CodeInstruction(OpCodes.Ldarg_0), + new CodeInstruction(OpCodes.Ldfld, + AccessTools.Field(typeof(DFRelayComponent), nameof(DFRelayComponent.hiveAstroId))), + + //Call our method + new CodeInstruction(OpCodes.Call, + AccessTools.Method(typeof(EnemyDFRelayComponent_Transplier), + nameof(RelaySendBackToHiveDock)))); + } + ); + + return codeMatcher.InstructionEnumeration(); + } + catch (Exception e) + { + Log.Error("Transpiler DFRelayComponent.RelaySailLogic failed. Mod version not compatible with game version."); + Log.Error(e); + return instructions; + } + } + + static void RelaySendBackToHiveDock(int relayId, int stage, int hiveAstroId) + { + // This is only called when the RelaySailTick has told the relay to return back to the hive and dock. + Log.Debug($"RelaySendBackToHiveDock called for relay ID {relayId} belonging to hive {hiveAstroId}"); + + if (!Multiplayer.IsActive) return; + if (!Multiplayer.Session.IsClient) + { + Multiplayer.Session.Network.SendPacket(new DFRelayDirectionStateChangePacket(relayId, hiveAstroId, stage, -1)); + } + } + } +} From f44dd53cfd4f1d28ee74e90fc1309be1d2df9428 Mon Sep 17 00:00:00 2001 From: AlienXAXS Date: Thu, 18 Jul 2024 16:20:09 +0100 Subject: [PATCH 2/3] Typo --- .../Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs b/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs index 5a85feaac..9d13ad061 100644 --- a/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs +++ b/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs @@ -44,7 +44,7 @@ public static IEnumerable RelaySailLogic_Transpiler(IEnumerable new CodeInstruction(OpCodes.Ldfld, AccessTools.Field(typeof(DFRelayComponent), nameof(DFRelayComponent.id))), - // Hive Astro ID argument + // Relay sail stage argument new CodeInstruction(OpCodes.Ldarg_0), new CodeInstruction(OpCodes.Ldfld, AccessTools.Field(typeof(DFRelayComponent), nameof(DFRelayComponent.stage))), From ee6f00bbf1ff8660c363b19bec0db4ddeb194fe5 Mon Sep 17 00:00:00 2001 From: AlienXAXS Date: Thu, 18 Jul 2024 18:53:15 +0100 Subject: [PATCH 3/3] Cleanup and name change --- .../DFRelay/DFRelayDirectionStateChangeProcessor.cs | 9 +-------- .../Transpilers/EnemyDFRelayComponent_Transplier.cs | 10 +++------- 2 files changed, 4 insertions(+), 15 deletions(-) diff --git a/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs b/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs index 66f60ad32..dde994e3f 100644 --- a/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs +++ b/NebulaNetwork/PacketProcessors/Combat/DFRelay/DFRelayDirectionStateChangeProcessor.cs @@ -1,9 +1,4 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; -using NebulaAPI.Packets; +using NebulaAPI.Packets; using NebulaModel.Logger; using NebulaModel.Networking; using NebulaModel.Packets; @@ -23,8 +18,6 @@ protected override void ProcessPacket(DFRelayDirectionStateChangePacket packet, var dfRelayComponent = hiveSystem.relays.buffer[packet.RelayId]; if (dfRelayComponent?.id != packet.RelayId) return; - Log.Debug($"Relay {dfRelayComponent.id} direction:{dfRelayComponent.direction} will be sent home with a new direction: {packet.NewDirection}"); - switch (packet.NewDirection) { case -1: //Relay is being sent home diff --git a/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs b/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs index 9d13ad061..c70b416bc 100644 --- a/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs +++ b/NebulaPatcher/Patches/Transpilers/EnemyDFRelayComponent_Transplier.cs @@ -57,9 +57,8 @@ public static IEnumerable RelaySailLogic_Transpiler(IEnumerable //Call our method new CodeInstruction(OpCodes.Call, AccessTools.Method(typeof(EnemyDFRelayComponent_Transplier), - nameof(RelaySendBackToHiveDock)))); - } - ); + nameof(ReplicateRelayDirectionChange)))); + }); return codeMatcher.InstructionEnumeration(); } @@ -71,11 +70,8 @@ public static IEnumerable RelaySailLogic_Transpiler(IEnumerable } } - static void RelaySendBackToHiveDock(int relayId, int stage, int hiveAstroId) + static void ReplicateRelayDirectionChange(int relayId, int stage, int hiveAstroId) { - // This is only called when the RelaySailTick has told the relay to return back to the hive and dock. - Log.Debug($"RelaySendBackToHiveDock called for relay ID {relayId} belonging to hive {hiveAstroId}"); - if (!Multiplayer.IsActive) return; if (!Multiplayer.Session.IsClient) {