From 061e7e6d8d2935261fa55e2d534baebcb84cf349 Mon Sep 17 00:00:00 2001 From: Aaro Varis Date: Sat, 1 Mar 2025 00:15:23 +0200 Subject: [PATCH] Bunch of changes --- BoneSync/BoneSync.csproj | 50 +----- BoneSync/MelonLoaderMod.cs | 4 +- .../Networking/Messages/LobbyInfoMessage.cs | 6 +- .../Messages/ObjectDamageMessage.cs | 9 +- BoneSync/Networking/NetworkMessage.cs | 11 +- BoneSync/Networking/Packet.cs | 5 +- BoneSync/Patching/CallPatchedMethod.cs | 12 +- BoneSync/Patching/InteractableHostPatches.cs | 7 +- BoneSync/Patching/ObjectHealthPatches.cs | 11 +- BoneSync/Patching/PoolPatches.cs | 163 ++++++++++++++---- BoneSync/Sync/Components/SyncableBase.cs | 48 +++--- .../Sync/Components/SyncableNetworking.cs | 21 ++- BoneSync/Sync/Components/SyncablePhysics.cs | 9 + BoneSync/Sync/ObjectSync.cs | 65 ++++--- BoneSync/Sync/ObjectSyncCache.cs | 14 +- BoneSync/packages.config | 16 -- 16 files changed, 271 insertions(+), 180 deletions(-) delete mode 100644 BoneSync/packages.config diff --git a/BoneSync/BoneSync.csproj b/BoneSync/BoneSync.csproj index 8ff8c19..e72b72e 100644 --- a/BoneSync/BoneSync.csproj +++ b/BoneSync/BoneSync.csproj @@ -1,7 +1,5 @@  - - Debug @@ -45,7 +43,7 @@ False - ..\..\..\..\..\..\Program Files (x86)\Steam\steamapps\common\BONEWORKS\BONEWORKS\MelonLoader\0Harmony.dll + A:\SteamLibrary\steamapps\common\BONEWORKS\BONEWORKS\MelonLoader\0Harmony.dll ..\..\..\..\..\..\Program Files (x86)\Steam\steamapps\common\BONEWORKS\BONEWORKS\MelonLoader\Managed\Assembly-CSharp.dll @@ -57,24 +55,9 @@ False ..\..\..\..\..\..\Program Files (x86)\Steam\steamapps\common\BONEWORKS\BONEWORKS\MelonLoader\MelonLoader.dll - - ..\packages\Microsoft.TestPlatform.ObjectModel.17.12.0\lib\net462\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\packages\Microsoft.TestPlatform.ObjectModel.17.12.0\lib\net462\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\packages\Microsoft.TestPlatform.ObjectModel.17.12.0\lib\net462\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\packages\System.Collections.Immutable.1.5.0\lib\netstandard2.0\System.Collections.Immutable.dll - - - ..\packages\System.Reflection.Metadata.1.6.0\lib\netstandard2.0\System.Reflection.Metadata.dll - @@ -99,18 +82,6 @@ False ..\..\..\..\..\..\Program Files (x86)\Steam\steamapps\common\BONEWORKS\BONEWORKS\MelonLoader\Managed\UnityEngine.PhysicsModule.dll - - ..\packages\xunit.abstractions.2.0.3\lib\net35\xunit.abstractions.dll - - - ..\packages\xunit.assert.2.9.3\lib\netstandard1.1\xunit.assert.dll - - - ..\packages\xunit.extensibility.core.2.9.3\lib\net452\xunit.core.dll - - - ..\packages\xunit.extensibility.execution.2.9.3\lib\net452\xunit.execution.desktop.dll - @@ -288,30 +259,13 @@ - - - - - - - - - xcopy /Y "$(TargetPath)" "C:\Program Files (x86)\Steam\steamapps\common\BONEWORKS\BONEWORKS\Mods\" + xcopy /Y "$(TargetPath)" "A:\SteamLibrary\steamapps\common\BONEWORKS\BONEWORKS\Mods\" - - - This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. - - - - - - \ No newline at end of file diff --git a/BoneSync/MelonLoaderMod.cs b/BoneSync/MelonLoaderMod.cs index 0ee9f2b..686cb68 100644 --- a/BoneSync/MelonLoaderMod.cs +++ b/BoneSync/MelonLoaderMod.cs @@ -27,8 +27,6 @@ namespace BoneSync { SteamClient.Init(823500, true); - PatchAll(); - SteamLobbyManager steamLobbyManager = new SteamLobbyManager(); lobby = steamLobbyManager; @@ -36,6 +34,8 @@ namespace BoneSync SceneSync.Initialize(); NetworkMessage.RegisterPacketTypes(); + + PatchAll(); } public static void PatchAll() diff --git a/BoneSync/Networking/Messages/LobbyInfoMessage.cs b/BoneSync/Networking/Messages/LobbyInfoMessage.cs index 2b57acc..cb9f8f3 100644 --- a/BoneSync/Networking/Messages/LobbyInfoMessage.cs +++ b/BoneSync/Networking/Messages/LobbyInfoMessage.cs @@ -3,7 +3,10 @@ using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; + +#if TEST using Xunit; +#endif namespace BoneSync.Networking.Messages { @@ -40,7 +43,7 @@ namespace BoneSync.Networking.Messages throw new NotImplementedException(); } } - +#if TEST public class LobbyInfoMessageTests { [Fact] @@ -58,4 +61,5 @@ namespace BoneSync.Networking.Messages Assert.Equal(5, newMessage.CurrentPlayers); } } +#endif } diff --git a/BoneSync/Networking/Messages/ObjectDamageMessage.cs b/BoneSync/Networking/Messages/ObjectDamageMessage.cs index 4a0acf9..b5b277d 100644 --- a/BoneSync/Networking/Messages/ObjectDamageMessage.cs +++ b/BoneSync/Networking/Messages/ObjectDamageMessage.cs @@ -1,4 +1,5 @@ -using StressLevelZero.Combat; +using BoneSync.Sync; +using StressLevelZero.Combat; using System; using System.Collections.Generic; using System.Linq; @@ -40,7 +41,7 @@ namespace BoneSync.Networking.Messages public ObjectHealthInfo objectHealthInfo; } - [PacketType(PacketType.ObjectEvent), PacketReliability(PacketReliability.Reliable)] + [PacketType(PacketType.ObjectEvent), PacketReliability(PacketReliability.UnreliableNoDelay)] public class ObjectDamageMessage : NetworkMessage { public ObjectDamageInfo objectEventInfo => _objectEventInfo; @@ -57,6 +58,7 @@ namespace BoneSync.Networking.Messages byteEncoder.WriteVector3(_objectEventInfo.objectHealthInfo.normal); byteEncoder.WriteFloat(_objectEventInfo.objectHealthInfo.damage); byteEncoder.WriteBool(_objectEventInfo.objectHealthInfo.crit); + byteEncoder.WriteByte((byte)_objectEventInfo.objectHealthInfo.attackType); } public ObjectDamageMessage(Packet packet) @@ -70,11 +72,12 @@ namespace BoneSync.Networking.Messages _objectEventInfo.objectHealthInfo.normal = byteEncoder.ReadVector3(); _objectEventInfo.objectHealthInfo.damage = byteEncoder.ReadFloat(); _objectEventInfo.objectHealthInfo.crit = byteEncoder.ReadBool(); + _objectEventInfo.objectHealthInfo.attackType = (AttackType)byteEncoder.ReadByte(); } public override void Execute() { - + ObjectSync.OnObjectDamageMessage(this); } } } diff --git a/BoneSync/Networking/NetworkMessage.cs b/BoneSync/Networking/NetworkMessage.cs index c3534f7..95f5b66 100644 --- a/BoneSync/Networking/NetworkMessage.cs +++ b/BoneSync/Networking/NetworkMessage.cs @@ -7,7 +7,9 @@ using System.Linq; using System.Reflection; using System.Text; using System.Threading.Tasks; +#if TEST using Xunit; +#endif namespace BoneSync.Networking { @@ -98,7 +100,7 @@ namespace BoneSync.Networking } public static NetworkMessage ParsePacket(Packet packet) { - MelonLogger.Msg("Received packet of type " + packet.Info.packetType + " from " + packet.Info.senderId + " Length: " + packet.Data.Length); + //MelonLogger.Msg("Received packet of type " + packet.Info.packetType + " from " + packet.Info.senderId + " Length: " + packet.Data.Length); // find a class that can parse this packet using Reflection // and return it if (!PacketTypeMap.ContainsKey(packet.Info.packetType)) @@ -126,6 +128,11 @@ namespace BoneSync.Networking { Send(TransportBase.BORADCAST_ID); } + + public void SendToHost() + { + Send(BoneSync.lobby.GetHostId()); + } public void Send(ulong receiverId) { if (BoneSync.lobby.IsConnected() == false) @@ -145,6 +152,7 @@ namespace BoneSync.Networking } } + #if TEST public class NetworkMessageTests { [Fact] @@ -154,4 +162,5 @@ namespace BoneSync.Networking Assert.NotEmpty(NetworkMessage.PacketTypeMap); } } + #endif } diff --git a/BoneSync/Networking/Packet.cs b/BoneSync/Networking/Packet.cs index 244190d..9c14d51 100644 --- a/BoneSync/Networking/Packet.cs +++ b/BoneSync/Networking/Packet.cs @@ -5,7 +5,9 @@ using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; +#if TEST using Xunit; +#endif namespace BoneSync.Networking { @@ -98,7 +100,7 @@ namespace BoneSync.Networking return new Random().Next(); } } - +#if TEST public class PacketTests { [Fact] @@ -127,4 +129,5 @@ namespace BoneSync.Networking Assert.NotEqual(bytes, randomDataBytes); } } + #endif } diff --git a/BoneSync/Patching/CallPatchedMethod.cs b/BoneSync/Patching/CallPatchedMethod.cs index 7ab2d0f..1b58945 100644 --- a/BoneSync/Patching/CallPatchedMethod.cs +++ b/BoneSync/Patching/CallPatchedMethod.cs @@ -31,13 +31,17 @@ namespace BoneSync.Patching allowPatchedMethodCall = false; } - public static GameObject PoolSpawn(Pool __instance, Vector3 position, Quaternion rotation, Vector3 scale) + public static Poolee InstantiatePoolee(Pool pool, Vector3 position, Quaternion rotation, Vector3 scale) { allowPatchedMethodCall = true; - Il2CppSystem.Nullable scaleNullable = new Il2CppSystem.Nullable(scale); - GameObject result = __instance.Spawn(position, rotation, scaleNullable, new Il2CppSystem.Nullable(true)); + Poolee poolee = pool.InstantiatePoolee(position, rotation); + poolee.transform.position = position; + poolee.transform.rotation = rotation; + poolee.transform.localScale = scale; + poolee.transform.parent = null; + poolee.gameObject.SetActive(true); allowPatchedMethodCall = false; - return result; + return poolee; } } } diff --git a/BoneSync/Patching/InteractableHostPatches.cs b/BoneSync/Patching/InteractableHostPatches.cs index 02130c8..cde94a7 100644 --- a/BoneSync/Patching/InteractableHostPatches.cs +++ b/BoneSync/Patching/InteractableHostPatches.cs @@ -19,13 +19,8 @@ namespace BoneSync.Patching public static void OnEnablePatch(InteractableHost __instance) { //MelonLoader.MelonLogger.Msg("InteractableHost enabled: " + __instance.name + " Manager: " + __instance?.manager?.name); - ObjectSync.MakeOrGetSyncable(__instance); - } + Syncable syncable = ObjectSync.MakeOrGetSyncable(__instance); - [HarmonyPatch(nameof(InteractableHost.OnDestroy)), HarmonyPostfix] - public static void OnDestroyPatch(InteractableHost __instance) - { - MelonLogger.Msg("InteractableHost destroyed: " + __instance.name); } [HarmonyPatch(nameof(InteractableHost.AttachHand)), HarmonyPostfix] diff --git a/BoneSync/Patching/ObjectHealthPatches.cs b/BoneSync/Patching/ObjectHealthPatches.cs index cc8b490..24f3ec1 100644 --- a/BoneSync/Patching/ObjectHealthPatches.cs +++ b/BoneSync/Patching/ObjectHealthPatches.cs @@ -14,6 +14,7 @@ using UnityEngine; namespace BoneSync.Patching { + [HarmonyPatch(typeof(ObjectDestructable))] public class ObjectDestructablePatches { @@ -23,10 +24,11 @@ namespace BoneSync.Patching { if (CallPatchedMethods.allowPatchedMethodCall) return true; MelonLoader.MelonLogger.Msg("ObjectDestructable.TakeDamage: " + damage); - Syncable syncable = ObjectSync.GetSyncableFromCache(__instance.gameObject); + Syncable syncable = ObjectSync.MakeOrGetSyncable(__instance.gameObject); if (syncable != null) { - if (!syncable.Registered) return true; + if (damage > 0.5f) syncable.RegisterSyncable(); + if (!syncable.isOwner) return true; MelonLoader.MelonLogger.Msg("Patch: ObjectDestructable.TakeDamage: " + damage + " " + syncable.gameObject.name); ObjectHealthInfo objectHealthInfo = new ObjectHealthInfo(__instance._health, __instance._hits, normal, damage, crit, attackType); @@ -47,10 +49,11 @@ namespace BoneSync.Patching { if (CallPatchedMethods.allowPatchedMethodCall) return true; MelonLoader.MelonLogger.Msg("Prop_Health.TAKEDAMAGE: " + damage); - Syncable syncable = ObjectSync.GetSyncableFromCache(__instance.gameObject); + Syncable syncable = ObjectSync.MakeOrGetSyncable(__instance.gameObject); if (syncable != null) { - if (!syncable.Registered) return true; + if (damage > 0.5f) syncable.RegisterSyncable(); + if (!syncable.isOwner) return true; MelonLoader.MelonLogger.Msg("Patch: Prop_Health.TAKEDAMAGE: " + damage + " " + syncable.gameObject.name); ObjectHealthInfo objectHealthInfo = new ObjectHealthInfo(__instance.cur_Health, __instance.hits, Vector3.zero, damage, crit, attackType); diff --git a/BoneSync/Patching/PoolPatches.cs b/BoneSync/Patching/PoolPatches.cs index dd8278d..93c2dc7 100644 --- a/BoneSync/Patching/PoolPatches.cs +++ b/BoneSync/Patching/PoolPatches.cs @@ -1,4 +1,5 @@ using System; +using System.Collections; using System.Collections.Generic; using System.Linq; using System.Runtime.InteropServices; @@ -6,61 +7,151 @@ using System.Text; using System.Threading.Tasks; using BoneSync.Networking.Messages; using BoneSync.Sync; +using BoneSync.Sync.Components; using HarmonyLib; using MelonLoader; using StressLevelZero; using StressLevelZero.Pool; +using StressLevelZero.Props.Weapons; using UnityEngine; namespace BoneSync.Patching { - - [HarmonyPatch(typeof(Pool))] - internal class PoolPatches + public static class PoolBlacklist { + private static Dictionary _blacklistedCache = new Dictionary(); - public readonly static string[] ignoredPools = new string[] { - "RigidbodyProjectile", - "VFX Despawn Mesh", - "AudioPlayer", - "Decal", - "PopupText", - }; - - public static bool IsIgnoredPool(string poolName) + private static bool _isBlacklistedPool(Pool pool) { - string lowercasePoolName = poolName.ToLower(); - foreach (string ignoredPool in ignoredPools) - { - if (lowercasePoolName.Contains(ignoredPool.ToLower())) - { - return true; - } - } + if (pool.name.Contains("RigidbodyProjectile")) return true; + if (pool.name.Contains("VFX Despawn Mesh")) return true; + if (pool.name.Contains("AudioPlayer")) return true; + if (pool.name.Contains("Decal")) return true; + if (pool.name.Contains("PopupText")) return true; + + if (pool.Prefab.GetComponent() != null) return true; + if (pool.Prefab.GetComponent() != null) return true; + if (pool.Prefab.GetComponent() != null) return true; + return false; } - - [HarmonyPatch(nameof(Pool.Spawn))] - [HarmonyPostfix] - private static void SpawnPatchPost(Pool __instance, ref GameObject __result) + public static bool isBlacklistedPool(Pool pool) { - //MelonLogger.Msg("Spawned object: " + __result.name); + if (_blacklistedCache.ContainsKey(pool)) + return _blacklistedCache[pool]; + _blacklistedCache[pool] = _isBlacklistedPool(pool); + return _blacklistedCache[pool]; } - - [HarmonyPatch(nameof(Pool.Spawn))] + } + + [HarmonyPatch(typeof(Pool))] + public static class PoolPatches + { + [HarmonyPatch(nameof(Pool.InstantiatePoolee))] [HarmonyPrefix] - private static bool SpawnPatchPre(Pool __instance, ref Vector3 position, ref Quaternion rotation, ref Il2CppSystem.Nullable scale, ref Il2CppSystem.Nullable autoEnable) + private static bool InstantiatePooleePatchPre(Pool __instance) { - if (CallPatchedMethods.allowPatchedMethodCall) return true; - if (IsIgnoredPool(__instance.name)) return true; - if (BoneSync.lobby.IsConnected()) - { - - MelonLogger.Msg("Patched Spawning object in pool: " + __instance.name); - return BoneSync.lobby.IsHost; // only allow host to spawn objects naturally - } + if (!__instance.Prefab) + return false; return true; } + [HarmonyPatch(nameof(Pool.InstantiatePoolee))] + [HarmonyPostfix] + private static void InstantiatePooleePatchPost(Pool __instance, Poolee __result, Vector3 position, Quaternion rotation) + { + if (__instance == null) return; + if (PoolBlacklist.isBlacklistedPool(__instance)) return; + MelonLogger.Msg("Patched Instantiating object in pool: " + __instance.name); + __result.onSpawnDelegate = Il2CppSystem.Delegate.Combine(__result.onSpawnDelegate, (Il2CppSystem.Action)((g) => { PooleePatches.OnSpawnPatchPost(__result); })).Cast>(); + + } + + + /*[HarmonyPatch(nameof(Pool.Spawn))] + [HarmonyPostfix] + private static void SpawnPatchPost(Pool __instance, ref GameObject __result) + { + if (__instance == null) return; + if (__instance.Prefab == null) return; + if (CallPatchedMethods.allowPatchedMethodCall) return; + if (PoolBlacklist.isBlacklistedPool(__instance)) return; + if (BoneSync.lobby.IsConnected()) + { + MelonLogger.Msg("Patched Spawning object in pool: " + __instance.name); + bool isHost = BoneSync.lobby.IsHost; + if (!isHost) GameObject.DestroyImmediate(__result); + } + }*/ + + /*[HarmonyPatch(nameof(Pool.Spawn))] + [HarmonyPrefix] + private static bool SpawnPatchPre(Pool __instance, ref Vector3 position, ref Quaternion rotation, ref Il2CppSystem.Nullable scale, ref Il2CppSystem.Nullable autoEnable) + { + if (__instance == null) return true; + if (__instance.Prefab == null) return true; + if (CallPatchedMethods.allowPatchedMethodCall) return true; + if (PoolBlacklist.isBlacklistedPool(__instance)) return true; + if (BoneSync.lobby.IsConnected()) + { + MelonLogger.Msg("Patched Spawning object in pool: " + __instance.name); + return BoneSync.lobby.IsHost; // only allow host to spawn objects naturally + } + __instance. + return true; + + } + */ } + [HarmonyPatch(typeof(Poolee))] + public static class PooleePatches + { + + public static void OnSpawnPatchPost(Poolee __instance) + { + if (CallPatchedMethods.allowPatchedMethodCall) return; + if (__instance.pool == null) return; + if (PoolBlacklist.isBlacklistedPool(__instance.pool)) return; + MelonLogger.Msg("Poolee.OnSpawn: " + __instance.gameObject.transform.GetPath()); + if (!BoneSync.lobby.IsConnected()) return; + Syncable syncable = ObjectSync.MakeOrGetSyncable(__instance); + + if (BoneSync.lobby.IsHost) + { + //syncable.RegisterSyncable(); + } else + { + MelonCoroutines.Start(OnSpawnClient(__instance)); + } + } + + public static IEnumerator OnSpawnClient(Poolee poolee) + { + GameObject go = poolee.gameObject; + if (SceneLoader.loading) + { + while (SceneLoader.loading) + { + go.SetActive(false); + yield return null; + } + + + } + + for (int i = 0; i < 2; i++) + { + go.SetActive(false); + yield return null; + } + } + + + public static IEnumerator OnSpawnHost(Poolee poolee) + { + return null; + } + + } + } diff --git a/BoneSync/Sync/Components/SyncableBase.cs b/BoneSync/Sync/Components/SyncableBase.cs index c37b186..f24ee84 100644 --- a/BoneSync/Sync/Components/SyncableBase.cs +++ b/BoneSync/Sync/Components/SyncableBase.cs @@ -31,23 +31,6 @@ namespace BoneSync.Sync.Components return "/" + current.name; return current.parent.GetPath() + "/" + current.name; } - - public static Transform FromPath(string path) - { - Transform current = null; - foreach (string name in path.Split('/')) - { - if (current == null) - { - current = GameObject.Find(name).transform; - } - else - { - current = current.Find(name); - } - } - return current; - } } [RegisterTypeInIl2Cpp] @@ -76,13 +59,26 @@ namespace BoneSync.Sync.Components public bool isStale => Time.time - _lastSyncTime > 5f; public bool isOwner => _ownerId == BoneSync.lobby.GetLocalId(); + public bool IsHolding() + { + if (interactableManager) + { + return interactableManager.grabbedHosts.Count > 0; + } + if (interactableHost) + { + return interactableHost.isAttached; + } + return false; + } + public bool ShouldSendSync() { if (!Registered) return false; if (!isOwner) return false; if (isStale) return true; - - return false; + if (AllRigidbodiesSleeping()) return false; + return true; } public ushort GetSyncId() => _syncId; @@ -111,13 +107,17 @@ namespace BoneSync.Sync.Components private AIBrain aiBrain; private PuppetMaster puppetMaster; + private SpawnFragment spawnFragment; + public void OnEnable() { + syncablesCache[gameObject] = this; + FindComponents(); bool shouldAutoSync = CheckIfShouldAutoSync(); - if (shouldAutoSync) + if (shouldAutoSync && BoneSync.lobby.IsHost) { MelonLogger.Msg("AutoSyncing: " + transform.GetPath()); RegisterSyncable(); @@ -140,7 +140,7 @@ namespace BoneSync.Sync.Components } if (interactableHost || interactableManager) { - return transform.GetPath(); + return transform.GetPath().Replace(" ", "[]"); } return ""; } @@ -157,6 +157,7 @@ namespace BoneSync.Sync.Components gun = GetComponent(); magazine = GetComponent(); plugs = GetComponentsInChildren(); + spawnFragment = GetComponent(); //rigidbodies = GetComponentsInChildren(); UpdateTransformList(); @@ -165,7 +166,8 @@ namespace BoneSync.Sync.Components public bool CanBeSynced() { - FindComponents(); + if (spawnFragment) return false; // if has spawn fragment, don't sync + FindComponents(); if (rigidbodies.Length > 0) return true; return false; @@ -174,7 +176,7 @@ namespace BoneSync.Sync.Components public void OnDestroy() { DiscardSyncable(); - MelonLogger.Msg("Syncable destroyed: " + transform.GetPath()); + //MelonLogger.Msg("Syncable destroyed: " + transform.GetPath()); } public void DiscardSyncable() diff --git a/BoneSync/Sync/Components/SyncableNetworking.cs b/BoneSync/Sync/Components/SyncableNetworking.cs index 76bbfdd..fa15d3a 100644 --- a/BoneSync/Sync/Components/SyncableNetworking.cs +++ b/BoneSync/Sync/Components/SyncableNetworking.cs @@ -1,5 +1,6 @@ using MelonLoader; using System; +using System.Collections; using System.Collections.Generic; using System.Linq; using System.Text; @@ -16,24 +17,24 @@ namespace BoneSync.Sync.Components _lastSyncTime = Time.time; ObjectSync.SendObjectSyncMessage(this); } - public async Task SyncCoroutineAsync() + public IEnumerator SyncCoroutineAsync() { MelonLogger.Msg("Running sync coroutine for: " + transform.GetPath()); - if (_syncCoroutineRunning) return; + if (_syncCoroutineRunning) yield break; _syncCoroutineRunning = true; while (isOwner) { if (ShouldSendSync()) SendObjectSync(); - await Task.Delay(!Registered ? 1000 : 1000 / SYNC_FPS); + yield return new WaitForSeconds(!Registered ? 1 : 1 / SYNC_FPS); } _syncCoroutineRunning = false; - return; + yield break; } public void SetOwner(ulong ownerId) { MelonLogger.Msg("Setting owner for " + _syncId + " to " + ownerId); _ownerId = ownerId; - _ = SyncCoroutineAsync(); + MelonCoroutines.Start(SyncCoroutineAsync()); UpdateKinematic(); } private void _SendRegisterSync() @@ -42,5 +43,15 @@ namespace BoneSync.Sync.Components SetOwner(BoneSync.lobby.GetLocalId()); SetSyncId(ObjectSync.SendRegisterSyncableMessage(this)); } + + public void OnOwnershipTransferRequest(ulong newOwnerId) + { + MelonLogger.Msg("Ownership transfer request for " + _syncId + " to " + newOwnerId); + if (isOwner) + { + MelonLogger.Msg("Sending ownership transfer for " + _syncId + " to " + newOwnerId); + //BoneSync.lobby.SendOwnershipTransferMessage(_syncId, newOwnerId); + } + } } } diff --git a/BoneSync/Sync/Components/SyncablePhysics.cs b/BoneSync/Sync/Components/SyncablePhysics.cs index 967cb25..551aebf 100644 --- a/BoneSync/Sync/Components/SyncablePhysics.cs +++ b/BoneSync/Sync/Components/SyncablePhysics.cs @@ -12,6 +12,15 @@ namespace BoneSync.Sync.Components { public partial class Syncable : MonoBehaviour { + + public bool AllRigidbodiesSleeping() + { + foreach (Rigidbody rb in rigidbodies) + { + if (!rb.IsSleeping()) return false; + } + return true; + } private void SetKinematic(bool kinematic) { foreach (Rigidbody rb in rigidbodies) diff --git a/BoneSync/Sync/ObjectSync.cs b/BoneSync/Sync/ObjectSync.cs index dd9f0b8..6bd9a5e 100644 --- a/BoneSync/Sync/ObjectSync.cs +++ b/BoneSync/Sync/ObjectSync.cs @@ -36,7 +36,7 @@ namespace BoneSync.Sync ownerId = syncable._ownerId, }; } - else if (syncable.poolee && syncable.poolee.pool) + else if (syncable.poolee && syncable.poolee.pool && BoneSync.lobby.IsHost) { info = new RegisterSyncableInfo() { @@ -65,20 +65,14 @@ namespace BoneSync.Sync - RegisterSyncableMessage message = new RegisterSyncableMessage(info); if (BoneSync.lobby.IsHost) { info.id = GetNextId(); - message.Broadcast(); - } - else + new RegisterSyncableMessage(info).Broadcast(); + } else { - if (message.senderId != BoneSync.lobby.GetHostId()) - { - MelonLogger.Warning("Non host tried to send register syncable message"); - } info.id = 0; - message.Send(BoneSync.lobby.GetHostId()); + new RegisterSyncableMessage(info).SendToHost(); } MelonLogger.Msg("Sending register syncable message for: " + syncable.transform.name + " with id: " + info.id + " and type : " + info.type); @@ -139,6 +133,20 @@ namespace BoneSync.Sync return syncable; } + public static Syncable MakeOrGetSyncable(GameObject gameObject) + { + Syncable syncable = GetSyncableFromCache(gameObject); + if (syncable == null) + { + syncable = _MakeOrGetSyncable(gameObject); + } + return syncable; + } + public static Syncable MakeOrGetSyncable(Poolee poolee) + { + return _MakeOrGetSyncable(poolee.gameObject); + } + public static Syncable MakeOrGetSyncable(InteractableHost interactableHost) { if (interactableHost.manager) return MakeOrGetSyncable(interactableHost.manager); @@ -150,19 +158,29 @@ namespace BoneSync.Sync return _MakeOrGetSyncable(interactableHostManager.gameObject); } - public static Syncable SpawnPooleeAndMakeSyncable(string poolName, RegisterSyncableInfo info) + public static Syncable SpawnPooleeAndMakeSyncable(RegisterSyncableInfo info) { - SimpleTransform spawnLocation = info.spawnInfo.Value.spawnLocation; - Pool pool = PoolManager.GetPool(poolName); - if (pool == null) + + SpawnPoolableInfo spawnInfo = info.spawnInfo.Value; + SimpleTransform spawnLocation = spawnInfo.spawnLocation; + + // !! This is a bit of a hack, but it works for now + // if pool starts with "pool - " remove it + if (spawnInfo.poolName.StartsWith("pool - ")) { - MelonLogger.Warning("Pool not found: " + poolName); + spawnInfo.poolName = spawnInfo.poolName.Substring(7); + } + + Pool pool = PoolManager.GetPool(spawnInfo.poolName); + if (!pool) + { + MelonLogger.Warning("[SpawnPooleeAndMakeSyncable] Failed to find pool: " + spawnInfo.poolName); return null; } - GameObject spawned = CallPatchedMethods.PoolSpawn(pool, spawnLocation.position, spawnLocation.rotation, spawnLocation.scale); - MelonLogger.Msg("Spawned object: " + spawned.transform.GetPath() + " in pool: " + poolName); - Poolee poolee = spawned.GetComponent(); - return _MakeOrGetSyncable(poolee.gameObject); + Poolee poolee = CallPatchedMethods.InstantiatePoolee(pool, spawnLocation.position, spawnLocation.rotation, pool.Prefab.transform.localScale); + + Syncable syncable = MakeOrGetSyncable(poolee); + return syncable; } public static void OnRegisterSyncMessage(RegisterSyncableMessage registerSyncableMessage) { @@ -172,6 +190,13 @@ namespace BoneSync.Sync { info.id = GetNextId(); new RegisterSyncableMessage(info).Broadcast(); + } else + { + if (registerSyncableMessage.senderId != BoneSync.lobby.GetHostId()) + { + MelonLogger.Warning("Received register sync message from non-host: " + registerSyncableMessage.senderId); + return; + } } switch (info.type) @@ -182,7 +207,7 @@ namespace BoneSync.Sync break; case RegisterSyncType.RegisterAndSpawn: MelonLogger.Msg("Registering and spawning syncable from pool: " + info.spawnInfo.Value.poolName + " with id: " + info.id); - syncable = SpawnPooleeAndMakeSyncable(info.spawnInfo.Value.poolName, info); + syncable = SpawnPooleeAndMakeSyncable(info); break; } diff --git a/BoneSync/Sync/ObjectSyncCache.cs b/BoneSync/Sync/ObjectSyncCache.cs index 57e88b0..363635a 100644 --- a/BoneSync/Sync/ObjectSyncCache.cs +++ b/BoneSync/Sync/ObjectSyncCache.cs @@ -19,7 +19,7 @@ namespace BoneSync.Sync public static void AddSyncable(Syncable syncable) { - string path = syncable.transform.GetPath(); + string path = syncable.GetSyncableWorldPath(); if (path != null && path != "") { _pathToSyncable[path] = syncable; @@ -44,9 +44,10 @@ namespace BoneSync.Sync public static void RemoveSyncable(Syncable syncable) { - if (syncable.transform) + string path = syncable.GetSyncableWorldPath(); + if (path != null && path != "") { - _pathToSyncable.Remove(syncable.transform.GetPath()); + _pathToSyncable.Remove(path); } if (syncable.GetSyncId() != 0) { @@ -69,13 +70,6 @@ namespace BoneSync.Sync public static void UpdateSyncId(Syncable syncable) { // remove other enties where value is the same - foreach (KeyValuePair entry in _idToSyncable) - { - if (entry.Value == syncable) - { - _idToSyncable.Remove(entry.Key); - } - } ushort id = syncable.GetSyncId(); if (_idToSyncable.ContainsKey(id)) { diff --git a/BoneSync/packages.config b/BoneSync/packages.config deleted file mode 100644 index a5081ad..0000000 --- a/BoneSync/packages.config +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file