more sync stuff
This commit is contained in:
@@ -7,6 +7,7 @@ using UnityEngine;
|
||||
using BoneSync.Player;
|
||||
using BoneSync.Sync;
|
||||
using Facepunch.Steamworks;
|
||||
using System.Reflection.Emit;
|
||||
|
||||
namespace BoneSync
|
||||
{
|
||||
@@ -52,6 +53,7 @@ namespace BoneSync
|
||||
public override void OnSceneWasInitialized(int buildIndex, string sceneName)
|
||||
{
|
||||
//MelonLogger.Msg("OnLevelWasInitialized: " + sceneName);
|
||||
SceneSync.OnSceneInit(buildIndex);
|
||||
}
|
||||
|
||||
public override void OnSceneWasUnloaded(int buildIndex, string sceneName)
|
||||
@@ -76,11 +78,6 @@ namespace BoneSync
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnLevelWasInitialized(int level)
|
||||
{
|
||||
SceneSync.OnSceneInit(level);
|
||||
}
|
||||
|
||||
public override void BONEWORKS_OnLoadingScreen()
|
||||
{
|
||||
base.BONEWORKS_OnLoadingScreen();
|
||||
|
||||
@@ -5,12 +5,14 @@ using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using BoneSync.Sync;
|
||||
using BoneSync.Sync.Components;
|
||||
using MelonLoader;
|
||||
|
||||
namespace BoneSync.Networking.Messages
|
||||
{
|
||||
public struct DiscardSyncableMessageData
|
||||
{
|
||||
public ushort syncId;
|
||||
public bool despawn;
|
||||
}
|
||||
[PacketType(PacketType.DiscardSyncable), PacketReliability(PacketReliability.ReliableFast)]
|
||||
internal class DiscardSyncableMessage : NetworkMessage
|
||||
@@ -21,20 +23,26 @@ namespace BoneSync.Networking.Messages
|
||||
{
|
||||
_data = discardSyncableMessageData;
|
||||
byteEncoder.WriteUShort(_data.syncId);
|
||||
byteEncoder.WriteBool(_data.despawn);
|
||||
}
|
||||
|
||||
public DiscardSyncableMessage(Packet packet)
|
||||
{
|
||||
byteEncoder.WriteBytes(packet.Data);
|
||||
_data.syncId = byteEncoder.ReadUShort();
|
||||
_data.despawn = byteEncoder.ReadBool();
|
||||
}
|
||||
|
||||
public override void Execute()
|
||||
{
|
||||
Syncable syncable = ObjectSyncCache.GetSyncable(_data.syncId);
|
||||
|
||||
if (syncable != null)
|
||||
{
|
||||
syncable.DiscardSyncable(true);
|
||||
syncable.DiscardSyncable(true, _data.despawn);
|
||||
} else
|
||||
{
|
||||
MelonLogger.Warning(senderId + " tried to discard a syncable that doesn't exist (syncId: " + _data.syncId + ")");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -16,6 +16,8 @@ namespace BoneSync.Networking.Messages
|
||||
public bool[] _attributes;
|
||||
public ObjectMagazineData? magazineData;
|
||||
}
|
||||
|
||||
[PacketType(PacketType.ObjectAttribute), PacketReliability(PacketReliability.ReliableFast)]
|
||||
internal class ObjectAttributeMessage : NetworkMessage
|
||||
{
|
||||
private ObjectAttributeMessageData _data;
|
||||
@@ -26,8 +28,8 @@ namespace BoneSync.Networking.Messages
|
||||
_data = objectAttributeMessageData;
|
||||
byteEncoder.WriteUShort(_data.syncId);
|
||||
|
||||
attributes.Add(_data.magazineData != null);
|
||||
if (_data.magazineData != null)
|
||||
attributes.Add(_data.magazineData.HasValue);
|
||||
if (_data.magazineData.HasValue)
|
||||
{
|
||||
byteEncoder.WriteByte(_data.magazineData.Value.ammoCount);
|
||||
}
|
||||
|
||||
@@ -16,5 +16,6 @@ namespace BoneSync.Networking
|
||||
ObjectEvent = 5,
|
||||
ObjectOwnership = 6,
|
||||
DiscardSyncable = 7,
|
||||
ObjectAttribute = 8,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,6 +31,13 @@ namespace BoneSync.Patching
|
||||
allowPatchedMethodCall = false;
|
||||
}
|
||||
|
||||
public static void Despawn(Poolee poolee)
|
||||
{
|
||||
allowPatchedMethodCall = true;
|
||||
poolee.Despawn();
|
||||
allowPatchedMethodCall = false;
|
||||
}
|
||||
|
||||
public static Poolee InstantiatePoolee(Pool pool, Vector3 position, Quaternion rotation, Vector3 scale)
|
||||
{
|
||||
allowPatchedMethodCall = true;
|
||||
|
||||
@@ -4,6 +4,7 @@ using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using BoneSync.Sync;
|
||||
using BoneSync.Sync.Components;
|
||||
using HarmonyLib;
|
||||
using StressLevelZero.Interaction;
|
||||
namespace BoneSync.Patching
|
||||
@@ -15,7 +16,13 @@ namespace BoneSync.Patching
|
||||
public static void OnEnablePatch(ForcePullGrip __instance)
|
||||
{
|
||||
MelonLoader.MelonLogger.Msg("ForcePullGrip.Pull: " + __instance.name);
|
||||
ObjectSync.MakeOrGetSyncable(__instance.gameObject);
|
||||
InteractableHost interactableHost = __instance.GetComponent<InteractableHost>();
|
||||
if (interactableHost == null) return;
|
||||
Syncable syncable = ObjectSync.MakeOrGetSyncable(interactableHost);
|
||||
if (syncable)
|
||||
{
|
||||
syncable.RegisterSyncable();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -79,6 +79,7 @@ namespace BoneSync.Patching
|
||||
if (PoolBlacklist.isBlacklistedPool(__instance)) return;
|
||||
MelonLogger.Msg("Patched Instantiating object in pool: " + __instance.name);
|
||||
__result.onSpawnDelegate = Il2CppSystem.Delegate.Combine(__result.onSpawnDelegate, (Il2CppSystem.Action<GameObject>)((g) => { PooleePatches.OnSpawnPatchPost(__result); })).Cast<Il2CppSystem.Action<GameObject>>();
|
||||
__result.onDespawnDelegate = Il2CppSystem.Delegate.Combine(__result.onDespawnDelegate, (Il2CppSystem.Action<GameObject>)((g) => { PooleePatches.OnDespawnPatchPost(__result); })).Cast<Il2CppSystem.Action<GameObject>>();
|
||||
|
||||
}
|
||||
|
||||
@@ -140,6 +141,22 @@ namespace BoneSync.Patching
|
||||
|
||||
}
|
||||
|
||||
public static void OnDespawnPatchPost(Poolee __instance)
|
||||
{
|
||||
if (CallPatchedMethods.allowPatchedMethodCall) return;
|
||||
if (!BoneSync.lobby.IsConnected()) return;
|
||||
|
||||
MelonLogger.Msg("Poolee.OnDespawn: " + __instance.gameObject.transform.GetPath());
|
||||
|
||||
//Syncable syncable = ObjectSync.MakeOrGetSyncable(__instance);
|
||||
|
||||
//if (syncable == null) return;
|
||||
|
||||
//if (syncable.isOwner) return;
|
||||
|
||||
//syncable.DiscardSyncable(true);
|
||||
}
|
||||
|
||||
public static IEnumerator OnSpawnClient(Poolee poolee)
|
||||
{
|
||||
GameObject go = poolee.gameObject;
|
||||
|
||||
@@ -31,6 +31,28 @@ namespace BoneSync.Sync.Components
|
||||
return "/" + current.name;
|
||||
return current.parent.GetPath() + "/" + current.name;
|
||||
}
|
||||
|
||||
public static Transform TransformFromPath(string path)
|
||||
{
|
||||
if (path.StartsWith("/"))
|
||||
{
|
||||
path = path.Substring(1);
|
||||
}
|
||||
string[] pathParts = path.Split('/');
|
||||
Transform current = null;
|
||||
foreach (string part in pathParts)
|
||||
{
|
||||
if (current == null)
|
||||
{
|
||||
current = GameObject.Find(part).transform;
|
||||
}
|
||||
else
|
||||
{
|
||||
current = current.Find(part);
|
||||
}
|
||||
}
|
||||
return current;
|
||||
}
|
||||
}
|
||||
|
||||
[RegisterTypeInIl2Cpp]
|
||||
@@ -92,15 +114,20 @@ namespace BoneSync.Sync.Components
|
||||
|
||||
private SpawnFragment spawnFragment;
|
||||
|
||||
private IEnumerator _CheckAutoSyncCo()
|
||||
private void CheckAutoSync()
|
||||
{
|
||||
yield return null;
|
||||
bool shouldAutoSync = CheckIfShouldAutoSync();
|
||||
if (shouldAutoSync && (BoneSync.lobby.IsHost || ClientSpawningAllowed()))
|
||||
{
|
||||
MelonLogger.Msg("AutoSyncing: " + transform.GetPath());
|
||||
RegisterSyncable();
|
||||
}
|
||||
}
|
||||
private IEnumerator _OnEnableCo()
|
||||
{
|
||||
yield return null; // wait a frame to make sure all components are initialized, I hate this but it works
|
||||
FindComponents();
|
||||
CheckAutoSync();
|
||||
yield break;
|
||||
}
|
||||
|
||||
@@ -110,11 +137,15 @@ namespace BoneSync.Sync.Components
|
||||
|
||||
FindComponents();
|
||||
|
||||
MelonCoroutines.Start(_CheckAutoSyncCo());
|
||||
MelonCoroutines.Start(_OnEnableCo());
|
||||
}
|
||||
|
||||
public bool CheckIfShouldAutoSync()
|
||||
{
|
||||
if (transform.GetPath().StartsWith("/Pool Manager/"))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (poolee && poolee.pool) {
|
||||
return true;
|
||||
}
|
||||
@@ -129,7 +160,7 @@ namespace BoneSync.Sync.Components
|
||||
}
|
||||
if (interactableHost || interactableManager)
|
||||
{
|
||||
return transform.GetPath().Replace(" ", "[]");
|
||||
return transform.GetPath();
|
||||
}
|
||||
return "";
|
||||
}
|
||||
@@ -153,6 +184,13 @@ namespace BoneSync.Sync.Components
|
||||
ObjectSyncCache.AddSyncable(this);
|
||||
}
|
||||
|
||||
private void ResetSyncStatus()
|
||||
{
|
||||
_ownerId = 0;
|
||||
_syncId = 0;
|
||||
_attemptedRegister = false;
|
||||
SetKinematic(false);
|
||||
}
|
||||
public bool CanBeSynced()
|
||||
{
|
||||
if (spawnFragment) return false; // if has spawn fragment, don't sync
|
||||
@@ -162,24 +200,38 @@ namespace BoneSync.Sync.Components
|
||||
return false;
|
||||
}
|
||||
|
||||
private void _DiscardSyncable(bool force)
|
||||
private void _DiscardSyncable(bool force, bool despawn)
|
||||
{
|
||||
if (Registered)
|
||||
bool isRegistered = Registered;
|
||||
MelonLogger.Msg("Discarding syncable: " + transform.GetPath() + " force: " + force + " isRegistered: " + isRegistered + " despawn: " + despawn);
|
||||
if (isRegistered)
|
||||
{
|
||||
MelonLogger.Warning("Discarding registered syncable: " + transform.GetPath() + " force: " + force);
|
||||
//MelonLogger.Warning("Discarding registered syncable: " + transform.GetPath() + " force: " + force);
|
||||
|
||||
bool isowner = isOwner;
|
||||
|
||||
if (isowner)
|
||||
{
|
||||
_SendDiscard(); // owner sends discard message
|
||||
_SendDiscard(true); // owner sends discard message
|
||||
}
|
||||
|
||||
if (!isowner && !force) return; // only owner can discard
|
||||
}
|
||||
syncablesCache.Remove(gameObject);
|
||||
|
||||
if (gameObject) syncablesCache.Remove(gameObject);
|
||||
|
||||
ObjectSyncCache.RemoveSyncable(this);
|
||||
Destroy(this); // delete the component
|
||||
|
||||
ResetSyncStatus();
|
||||
|
||||
DestroyImmediate(this); // delete the component
|
||||
|
||||
if (despawn)
|
||||
{
|
||||
gameObject?.SetActive(false);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
public void OnDestroy()
|
||||
@@ -188,19 +240,25 @@ namespace BoneSync.Sync.Components
|
||||
{
|
||||
MelonLogger.Warning("Destroying registered syncable: " + transform.GetPath());
|
||||
}
|
||||
_DiscardSyncable(true);
|
||||
DiscardSyncableImmediate(true, Registered);
|
||||
//MelonLogger.Msg("Syncable destroyed: " + transform.GetPath());
|
||||
}
|
||||
|
||||
private IEnumerator _FlagForDiscardCo(bool force)
|
||||
private IEnumerator _FlagForDiscardCo(bool force, bool despawn) { yield return null; _DiscardSyncable(force, despawn); } // delay discard to prevent silly behavior
|
||||
|
||||
public void DiscardSyncable(bool force = false, bool despawn = false)
|
||||
{
|
||||
yield return null;
|
||||
_DiscardSyncable(force);
|
||||
if (Registered && isOwner)
|
||||
{
|
||||
DiscardSyncableImmediate(force, despawn);
|
||||
return;
|
||||
}
|
||||
MelonCoroutines.Start(_FlagForDiscardCo(force, despawn));
|
||||
}
|
||||
|
||||
public void DiscardSyncable(bool force = false)
|
||||
public void DiscardSyncableImmediate(bool force = false, bool despawn = false)
|
||||
{
|
||||
MelonCoroutines.Start(_FlagForDiscardCo(force));
|
||||
_DiscardSyncable(true, despawn);
|
||||
}
|
||||
|
||||
public void OnDisable()
|
||||
@@ -209,10 +267,9 @@ namespace BoneSync.Sync.Components
|
||||
{
|
||||
MelonLogger.Warning("tried to disable non-owner syncable: " + transform.GetPath());
|
||||
gameObject.SetActive(true);
|
||||
} else
|
||||
{
|
||||
DiscardSyncable();
|
||||
return;
|
||||
}
|
||||
DiscardSyncable();
|
||||
}
|
||||
|
||||
public void RegisterSyncable()
|
||||
|
||||
@@ -56,11 +56,13 @@ namespace BoneSync.Sync.Components
|
||||
SetSyncId(ObjectSync.SendRegisterSyncableMessage(this));
|
||||
}
|
||||
|
||||
private void _SendDiscard()
|
||||
private void _SendDiscard(bool despawn = false)
|
||||
{
|
||||
MelonLogger.Msg("Sending discard for " + _syncId + " despawn: " + despawn);
|
||||
DiscardSyncableMessageData discardSyncableMessageData = new DiscardSyncableMessageData()
|
||||
{
|
||||
syncId = _syncId
|
||||
syncId = _syncId,
|
||||
despawn = despawn
|
||||
};
|
||||
DiscardSyncableMessage discardSyncableMessage = new DiscardSyncableMessage(discardSyncableMessageData);
|
||||
discardSyncableMessage.Broadcast();
|
||||
@@ -85,7 +87,7 @@ namespace BoneSync.Sync.Components
|
||||
|
||||
public void TryBecomeOwner()
|
||||
{
|
||||
if (!isOwner)
|
||||
if (Registered && !isOwner)
|
||||
{
|
||||
MelonLogger.Msg("Attempting to become owner of " + _syncId);
|
||||
OwnershipTransferMessageData data = new OwnershipTransferMessageData()
|
||||
|
||||
@@ -105,12 +105,6 @@ namespace BoneSync.Sync
|
||||
//Scene scene = gameObject.scene;
|
||||
//MelonLogger.Msg("Making or getting syncable for: " + gameObject.name + " in scene: " + scene.name);
|
||||
|
||||
Syncable parentSyncable = gameObject.transform.parent.GetComponentInParent<Syncable>();
|
||||
if (parentSyncable != null)
|
||||
{
|
||||
return parentSyncable;
|
||||
}
|
||||
|
||||
Syncable syncable = gameObject.GetComponent<Syncable>();
|
||||
|
||||
// delete all sub syncables
|
||||
@@ -210,6 +204,12 @@ namespace BoneSync.Sync
|
||||
}
|
||||
}
|
||||
|
||||
if (info.id == 0)
|
||||
{
|
||||
MelonLogger.Warning("Received register sync message with id 0");
|
||||
return;
|
||||
}
|
||||
|
||||
bool hasCallback = info.callbackId != 0;
|
||||
if (hasCallback)
|
||||
{
|
||||
@@ -250,6 +250,9 @@ namespace BoneSync.Sync
|
||||
{
|
||||
ObjectSyncMessageData data = objectSyncMessage.objectSyncMessageData;
|
||||
ushort objectId = data.objectId;
|
||||
|
||||
if (objectId == 0) return;
|
||||
|
||||
if (objectId >= _nextSyncableId && !BoneSync.lobby.IsHost)
|
||||
{
|
||||
_nextSyncableId = (ushort)(objectId + 1);
|
||||
@@ -257,7 +260,7 @@ namespace BoneSync.Sync
|
||||
Syncable syncable = ObjectSyncCache.GetSyncable(objectId);
|
||||
if (syncable == null)
|
||||
{
|
||||
MelonLogger.Msg("SyncEvent: Syncable not found for id: " + objectId);
|
||||
//MelonLogger.Msg("SyncEvent: Syncable not found for id: " + objectId);
|
||||
return;
|
||||
}
|
||||
syncable.ApplyObjectSyncTransforms(data.objectSyncTransforms);
|
||||
|
||||
@@ -6,6 +6,7 @@ using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using UnityEngine;
|
||||
|
||||
namespace BoneSync.Sync
|
||||
{
|
||||
@@ -86,6 +87,11 @@ namespace BoneSync.Sync
|
||||
{
|
||||
return _pathToSyncable[path];
|
||||
}
|
||||
Transform transform = TransformExtensions.TransformFromPath(path);
|
||||
if (transform)
|
||||
{
|
||||
return transform.GetComponent<Syncable>();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,9 +1,12 @@
|
||||
using MelonLoader;
|
||||
using BoneSync.Sync.Components;
|
||||
using MelonLoader;
|
||||
using StressLevelZero.Interaction;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using UnityEngine;
|
||||
using UnityEngine.SceneManagement;
|
||||
|
||||
namespace BoneSync.Sync
|
||||
@@ -27,12 +30,45 @@ namespace BoneSync.Sync
|
||||
|
||||
return sceneName;
|
||||
}
|
||||
}
|
||||
|
||||
public static void RenameDuplicateSceneTransforms(Scene scene)
|
||||
{
|
||||
Dictionary<string, ushort> seenTransformNames = new Dictionary<string, ushort>();
|
||||
uint total = 0;
|
||||
foreach (GameObject go in scene.GetRootGameObjects())
|
||||
{
|
||||
foreach (InteractableHost host in go.GetComponentsInChildren<InteractableHost>(true))
|
||||
{
|
||||
Transform t = host.transform;
|
||||
string path = t.GetPath();
|
||||
if (seenTransformNames.ContainsKey(path))
|
||||
{
|
||||
seenTransformNames[path]++;
|
||||
t.name = t.name + " (BoneSync." + seenTransformNames[path] + ")";
|
||||
total++;
|
||||
//MelonLogger.Msg("Renamed duplicate transform: " + path);
|
||||
}
|
||||
else
|
||||
{
|
||||
seenTransformNames[path] = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
MelonLogger.Msg("Renamed " + total + " duplicate transforms in " + scene.name);
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
public static void OnSceneInit(int buildIndex)
|
||||
{
|
||||
string SceneName = SceneManager.GetSceneByBuildIndex(buildIndex).name;
|
||||
Scene scene = SceneManager.GetSceneByBuildIndex(buildIndex);
|
||||
string SceneName = scene.name;
|
||||
_currentSceneName = SceneName;
|
||||
MelonLogger.Msg("Scene initialized: " + SceneName);
|
||||
RenameDuplicateSceneTransforms(scene);
|
||||
}
|
||||
|
||||
public static void Initialize()
|
||||
|
||||
Reference in New Issue
Block a user