mirror of
https://github.com/misternebula/quantum-space-buddies.git
synced 2025-01-27 12:35:28 +00:00
more tabs
This commit is contained in:
parent
c6c76cb395
commit
7925b637a0
@ -8,237 +8,237 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.Animation
|
||||
{
|
||||
public class AnimationSync : PlayerSyncObject
|
||||
{
|
||||
private Animator _anim;
|
||||
private Animator _bodyAnim;
|
||||
private QSBNetworkAnimator _netAnim;
|
||||
public class AnimationSync : PlayerSyncObject
|
||||
{
|
||||
private Animator _anim;
|
||||
private Animator _bodyAnim;
|
||||
private QSBNetworkAnimator _netAnim;
|
||||
|
||||
private RuntimeAnimatorController _suitedAnimController;
|
||||
private AnimatorOverrideController _unsuitedAnimController;
|
||||
private GameObject _suitedGraphics;
|
||||
private GameObject _unsuitedGraphics;
|
||||
private PlayerCharacterController _playerController;
|
||||
private CrouchSync _crouchSync;
|
||||
private RuntimeAnimatorController _suitedAnimController;
|
||||
private AnimatorOverrideController _unsuitedAnimController;
|
||||
private GameObject _suitedGraphics;
|
||||
private GameObject _unsuitedGraphics;
|
||||
private PlayerCharacterController _playerController;
|
||||
private CrouchSync _crouchSync;
|
||||
|
||||
private RuntimeAnimatorController _chertController;
|
||||
private RuntimeAnimatorController _eskerController;
|
||||
private RuntimeAnimatorController _feldsparController;
|
||||
private RuntimeAnimatorController _gabbroController;
|
||||
private RuntimeAnimatorController _riebeckController;
|
||||
private RuntimeAnimatorController _chertController;
|
||||
private RuntimeAnimatorController _eskerController;
|
||||
private RuntimeAnimatorController _feldsparController;
|
||||
private RuntimeAnimatorController _gabbroController;
|
||||
private RuntimeAnimatorController _riebeckController;
|
||||
|
||||
public AnimatorMirror Mirror { get; private set; }
|
||||
public AnimationType CurrentType = AnimationType.PlayerUnsuited;
|
||||
public Animator Animator
|
||||
{
|
||||
get { return _bodyAnim; }
|
||||
}
|
||||
public AnimatorMirror Mirror { get; private set; }
|
||||
public AnimationType CurrentType = AnimationType.PlayerUnsuited;
|
||||
public Animator Animator
|
||||
{
|
||||
get { return _bodyAnim; }
|
||||
}
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
_anim = gameObject.AddComponent<Animator>();
|
||||
_netAnim = gameObject.AddComponent<QSBNetworkAnimator>();
|
||||
_netAnim.enabled = false;
|
||||
_netAnim.animator = _anim;
|
||||
private void Awake()
|
||||
{
|
||||
_anim = gameObject.AddComponent<Animator>();
|
||||
_netAnim = gameObject.AddComponent<QSBNetworkAnimator>();
|
||||
_netAnim.enabled = false;
|
||||
_netAnim.animator = _anim;
|
||||
|
||||
QSBSceneManager.OnUniverseSceneLoaded += (OWScene scene) => LoadControllers();
|
||||
}
|
||||
QSBSceneManager.OnUniverseSceneLoaded += (OWScene scene) => LoadControllers();
|
||||
}
|
||||
|
||||
private void OnDestroy()
|
||||
{
|
||||
_netAnim.enabled = false;
|
||||
if (_playerController == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_playerController.OnJump -= OnJump;
|
||||
_playerController.OnBecomeGrounded -= OnBecomeGrounded;
|
||||
_playerController.OnBecomeUngrounded -= OnBecomeUngrounded;
|
||||
private void OnDestroy()
|
||||
{
|
||||
_netAnim.enabled = false;
|
||||
if (_playerController == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_playerController.OnJump -= OnJump;
|
||||
_playerController.OnBecomeGrounded -= OnBecomeGrounded;
|
||||
_playerController.OnBecomeUngrounded -= OnBecomeUngrounded;
|
||||
|
||||
QSBSceneManager.OnUniverseSceneLoaded -= (OWScene scene) => LoadControllers();
|
||||
}
|
||||
QSBSceneManager.OnUniverseSceneLoaded -= (OWScene scene) => LoadControllers();
|
||||
}
|
||||
|
||||
private void LoadControllers()
|
||||
{
|
||||
var bundle = QSB.InstrumentAssetBundle;
|
||||
_chertController = bundle.LoadAsset("assets/Chert/Traveller_Chert.controller") as RuntimeAnimatorController;
|
||||
_riebeckController = bundle.LoadAsset("assets/Riebeck/Traveller_Riebeck.controller") as RuntimeAnimatorController;
|
||||
}
|
||||
private void LoadControllers()
|
||||
{
|
||||
var bundle = QSB.InstrumentAssetBundle;
|
||||
_chertController = bundle.LoadAsset("assets/Chert/Traveller_Chert.controller") as RuntimeAnimatorController;
|
||||
_riebeckController = bundle.LoadAsset("assets/Riebeck/Traveller_Riebeck.controller") as RuntimeAnimatorController;
|
||||
}
|
||||
|
||||
private void InitCommon(Transform body)
|
||||
{
|
||||
if (QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
LoadControllers();
|
||||
}
|
||||
_netAnim.enabled = true;
|
||||
_bodyAnim = body.GetComponent<Animator>();
|
||||
Mirror = body.gameObject.AddComponent<AnimatorMirror>();
|
||||
if (IsLocalPlayer)
|
||||
{
|
||||
Mirror.Init(_bodyAnim, _anim);
|
||||
}
|
||||
else
|
||||
{
|
||||
Mirror.Init(_anim, _bodyAnim);
|
||||
}
|
||||
private void InitCommon(Transform body)
|
||||
{
|
||||
if (QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
LoadControllers();
|
||||
}
|
||||
_netAnim.enabled = true;
|
||||
_bodyAnim = body.GetComponent<Animator>();
|
||||
Mirror = body.gameObject.AddComponent<AnimatorMirror>();
|
||||
if (IsLocalPlayer)
|
||||
{
|
||||
Mirror.Init(_bodyAnim, _anim);
|
||||
}
|
||||
else
|
||||
{
|
||||
Mirror.Init(_anim, _bodyAnim);
|
||||
}
|
||||
|
||||
QSBPlayerManager.PlayerSyncObjects.Add(this);
|
||||
QSBPlayerManager.PlayerSyncObjects.Add(this);
|
||||
|
||||
for (var i = 0; i < _anim.parameterCount; i++)
|
||||
{
|
||||
_netAnim.SetParameterAutoSend(i, true);
|
||||
}
|
||||
for (var i = 0; i < _anim.parameterCount; i++)
|
||||
{
|
||||
_netAnim.SetParameterAutoSend(i, true);
|
||||
}
|
||||
|
||||
var playerAnimController = body.GetComponent<PlayerAnimController>();
|
||||
_suitedAnimController = AnimControllerPatch.SuitedAnimController;
|
||||
_unsuitedAnimController = playerAnimController.GetValue<AnimatorOverrideController>("_unsuitedAnimOverride");
|
||||
_suitedGraphics = playerAnimController.GetValue<GameObject>("_suitedGroup");
|
||||
_unsuitedGraphics = playerAnimController.GetValue<GameObject>("_unsuitedGroup");
|
||||
}
|
||||
var playerAnimController = body.GetComponent<PlayerAnimController>();
|
||||
_suitedAnimController = AnimControllerPatch.SuitedAnimController;
|
||||
_unsuitedAnimController = playerAnimController.GetValue<AnimatorOverrideController>("_unsuitedAnimOverride");
|
||||
_suitedGraphics = playerAnimController.GetValue<GameObject>("_suitedGroup");
|
||||
_unsuitedGraphics = playerAnimController.GetValue<GameObject>("_unsuitedGroup");
|
||||
}
|
||||
|
||||
public void InitLocal(Transform body)
|
||||
{
|
||||
InitCommon(body);
|
||||
public void InitLocal(Transform body)
|
||||
{
|
||||
InitCommon(body);
|
||||
|
||||
_playerController = body.parent.GetComponent<PlayerCharacterController>();
|
||||
_playerController.OnJump += OnJump;
|
||||
_playerController.OnBecomeGrounded += OnBecomeGrounded;
|
||||
_playerController.OnBecomeUngrounded += OnBecomeUngrounded;
|
||||
_playerController = body.parent.GetComponent<PlayerCharacterController>();
|
||||
_playerController.OnJump += OnJump;
|
||||
_playerController.OnBecomeGrounded += OnBecomeGrounded;
|
||||
_playerController.OnBecomeUngrounded += OnBecomeUngrounded;
|
||||
|
||||
InitCrouchSync();
|
||||
}
|
||||
InitCrouchSync();
|
||||
}
|
||||
|
||||
public void InitRemote(Transform body)
|
||||
{
|
||||
InitCommon(body);
|
||||
public void InitRemote(Transform body)
|
||||
{
|
||||
InitCommon(body);
|
||||
|
||||
var playerAnimController = body.GetComponent<PlayerAnimController>();
|
||||
playerAnimController.enabled = false;
|
||||
var playerAnimController = body.GetComponent<PlayerAnimController>();
|
||||
playerAnimController.enabled = false;
|
||||
|
||||
playerAnimController.SetValue("_suitedGroup", new GameObject());
|
||||
playerAnimController.SetValue("_unsuitedGroup", new GameObject());
|
||||
playerAnimController.SetValue("_baseAnimController", null);
|
||||
playerAnimController.SetValue("_unsuitedAnimOverride", null);
|
||||
playerAnimController.SetValue("_rightArmHidden", false);
|
||||
playerAnimController.SetValue("_suitedGroup", new GameObject());
|
||||
playerAnimController.SetValue("_unsuitedGroup", new GameObject());
|
||||
playerAnimController.SetValue("_baseAnimController", null);
|
||||
playerAnimController.SetValue("_unsuitedAnimOverride", null);
|
||||
playerAnimController.SetValue("_rightArmHidden", false);
|
||||
|
||||
var rightArmObjects = playerAnimController.GetValue<GameObject[]>("_rightArmObjects").ToList();
|
||||
rightArmObjects.ForEach(rightArmObject => rightArmObject.layer = LayerMask.NameToLayer("Default"));
|
||||
var rightArmObjects = playerAnimController.GetValue<GameObject[]>("_rightArmObjects").ToList();
|
||||
rightArmObjects.ForEach(rightArmObject => rightArmObject.layer = LayerMask.NameToLayer("Default"));
|
||||
|
||||
body.Find("player_mesh_noSuit:Traveller_HEA_Player/player_mesh_noSuit:Player_Head").gameObject.layer = 0;
|
||||
body.Find("Traveller_Mesh_v01:Traveller_Geo/Traveller_Mesh_v01:PlayerSuit_Helmet").gameObject.layer = 0;
|
||||
body.Find("player_mesh_noSuit:Traveller_HEA_Player/player_mesh_noSuit:Player_Head").gameObject.layer = 0;
|
||||
body.Find("Traveller_Mesh_v01:Traveller_Geo/Traveller_Mesh_v01:PlayerSuit_Helmet").gameObject.layer = 0;
|
||||
|
||||
InitCrouchSync();
|
||||
InitCrouchSync();
|
||||
|
||||
var ikSync = body.gameObject.AddComponent<PlayerHeadRotationSync>();
|
||||
QSB.Helper.Events.Unity.RunWhen(() => Player.Camera != null, () => ikSync.Init(Player.Camera.transform));
|
||||
}
|
||||
var ikSync = body.gameObject.AddComponent<PlayerHeadRotationSync>();
|
||||
QSB.Helper.Events.Unity.RunWhen(() => Player.Camera != null, () => ikSync.Init(Player.Camera.transform));
|
||||
}
|
||||
|
||||
private void InitCrouchSync()
|
||||
{
|
||||
_crouchSync = gameObject.AddComponent<CrouchSync>();
|
||||
_crouchSync.Init(this, _playerController, _bodyAnim);
|
||||
}
|
||||
private void InitCrouchSync()
|
||||
{
|
||||
_crouchSync = gameObject.AddComponent<CrouchSync>();
|
||||
_crouchSync.Init(this, _playerController, _bodyAnim);
|
||||
}
|
||||
|
||||
private void OnJump() => _netAnim.SetTrigger("Jump");
|
||||
private void OnBecomeGrounded() => _netAnim.SetTrigger("Grounded");
|
||||
private void OnBecomeUngrounded() => _netAnim.SetTrigger("Ungrounded");
|
||||
private void OnJump() => _netAnim.SetTrigger("Jump");
|
||||
private void OnBecomeGrounded() => _netAnim.SetTrigger("Grounded");
|
||||
private void OnBecomeUngrounded() => _netAnim.SetTrigger("Ungrounded");
|
||||
|
||||
public void SendCrouch(float value = 0)
|
||||
{
|
||||
GlobalMessenger<float>.FireEvent(EventNames.QSBCrouch, value);
|
||||
}
|
||||
public void SendCrouch(float value = 0)
|
||||
{
|
||||
GlobalMessenger<float>.FireEvent(EventNames.QSBCrouch, value);
|
||||
}
|
||||
|
||||
public void HandleCrouch(float value)
|
||||
{
|
||||
_crouchSync.CrouchParam.Target = value;
|
||||
}
|
||||
public void HandleCrouch(float value)
|
||||
{
|
||||
_crouchSync.CrouchParam.Target = value;
|
||||
}
|
||||
|
||||
private void SuitUp()
|
||||
{
|
||||
GlobalMessenger<uint, AnimationType>.FireEvent(EventNames.QSBChangeAnimType, PlayerId, AnimationType.PlayerSuited);
|
||||
SetAnimationType(AnimationType.PlayerSuited);
|
||||
}
|
||||
private void SuitUp()
|
||||
{
|
||||
GlobalMessenger<uint, AnimationType>.FireEvent(EventNames.QSBChangeAnimType, PlayerId, AnimationType.PlayerSuited);
|
||||
SetAnimationType(AnimationType.PlayerSuited);
|
||||
}
|
||||
|
||||
private void SuitDown()
|
||||
{
|
||||
GlobalMessenger<uint, AnimationType>.FireEvent(EventNames.QSBChangeAnimType, PlayerId, AnimationType.PlayerUnsuited);
|
||||
SetAnimationType(AnimationType.PlayerUnsuited);
|
||||
}
|
||||
private void SuitDown()
|
||||
{
|
||||
GlobalMessenger<uint, AnimationType>.FireEvent(EventNames.QSBChangeAnimType, PlayerId, AnimationType.PlayerUnsuited);
|
||||
SetAnimationType(AnimationType.PlayerUnsuited);
|
||||
}
|
||||
|
||||
public void SetSuitState(bool state)
|
||||
{
|
||||
if (state)
|
||||
{
|
||||
SuitUp();
|
||||
return;
|
||||
}
|
||||
SuitDown();
|
||||
}
|
||||
public void SetSuitState(bool state)
|
||||
{
|
||||
if (state)
|
||||
{
|
||||
SuitUp();
|
||||
return;
|
||||
}
|
||||
SuitDown();
|
||||
}
|
||||
|
||||
public void SetAnimationType(AnimationType type)
|
||||
{
|
||||
if (CurrentType == type)
|
||||
{
|
||||
return;
|
||||
}
|
||||
CurrentType = type;
|
||||
if (_unsuitedAnimController == null)
|
||||
{
|
||||
DebugLog.DebugWrite($"Error - Unsuited controller is null. ({PlayerId})", MessageType.Error);
|
||||
}
|
||||
if (_suitedAnimController == null)
|
||||
{
|
||||
DebugLog.DebugWrite($"Error - Suited controller is null. ({PlayerId})", MessageType.Error);
|
||||
}
|
||||
RuntimeAnimatorController controller = default;
|
||||
switch (type)
|
||||
{
|
||||
case AnimationType.PlayerSuited:
|
||||
controller = _suitedAnimController;
|
||||
_unsuitedGraphics?.SetActive(false);
|
||||
_suitedGraphics?.SetActive(true);
|
||||
break;
|
||||
case AnimationType.PlayerUnsuited:
|
||||
controller = _unsuitedAnimController;
|
||||
_unsuitedGraphics?.SetActive(true);
|
||||
_suitedGraphics?.SetActive(false);
|
||||
break;
|
||||
case AnimationType.Chert:
|
||||
controller = _chertController;
|
||||
break;
|
||||
case AnimationType.Esker:
|
||||
controller = _eskerController;
|
||||
break;
|
||||
case AnimationType.Feldspar:
|
||||
controller = _feldsparController;
|
||||
break;
|
||||
case AnimationType.Gabbro:
|
||||
controller = _gabbroController;
|
||||
break;
|
||||
case AnimationType.Riebeck:
|
||||
controller = _riebeckController;
|
||||
break;
|
||||
}
|
||||
_anim.runtimeAnimatorController = controller;
|
||||
_bodyAnim.runtimeAnimatorController = controller;
|
||||
if (type != AnimationType.PlayerSuited && type != AnimationType.PlayerUnsuited)
|
||||
{
|
||||
_bodyAnim.SetTrigger("Playing");
|
||||
_anim.SetTrigger("Playing");
|
||||
}
|
||||
else
|
||||
{
|
||||
// Avoids "jumping" when exiting instrument and putting on suit
|
||||
_bodyAnim.SetTrigger("Grounded");
|
||||
_anim.SetTrigger("Grounded");
|
||||
}
|
||||
_netAnim.animator = _anim; // Probably not needed.
|
||||
Mirror.RebuildFloatParams();
|
||||
for (var i = 0; i < _anim.parameterCount; i++)
|
||||
{
|
||||
_netAnim.SetParameterAutoSend(i, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
public void SetAnimationType(AnimationType type)
|
||||
{
|
||||
if (CurrentType == type)
|
||||
{
|
||||
return;
|
||||
}
|
||||
CurrentType = type;
|
||||
if (_unsuitedAnimController == null)
|
||||
{
|
||||
DebugLog.DebugWrite($"Error - Unsuited controller is null. ({PlayerId})", MessageType.Error);
|
||||
}
|
||||
if (_suitedAnimController == null)
|
||||
{
|
||||
DebugLog.DebugWrite($"Error - Suited controller is null. ({PlayerId})", MessageType.Error);
|
||||
}
|
||||
RuntimeAnimatorController controller = default;
|
||||
switch (type)
|
||||
{
|
||||
case AnimationType.PlayerSuited:
|
||||
controller = _suitedAnimController;
|
||||
_unsuitedGraphics?.SetActive(false);
|
||||
_suitedGraphics?.SetActive(true);
|
||||
break;
|
||||
case AnimationType.PlayerUnsuited:
|
||||
controller = _unsuitedAnimController;
|
||||
_unsuitedGraphics?.SetActive(true);
|
||||
_suitedGraphics?.SetActive(false);
|
||||
break;
|
||||
case AnimationType.Chert:
|
||||
controller = _chertController;
|
||||
break;
|
||||
case AnimationType.Esker:
|
||||
controller = _eskerController;
|
||||
break;
|
||||
case AnimationType.Feldspar:
|
||||
controller = _feldsparController;
|
||||
break;
|
||||
case AnimationType.Gabbro:
|
||||
controller = _gabbroController;
|
||||
break;
|
||||
case AnimationType.Riebeck:
|
||||
controller = _riebeckController;
|
||||
break;
|
||||
}
|
||||
_anim.runtimeAnimatorController = controller;
|
||||
_bodyAnim.runtimeAnimatorController = controller;
|
||||
if (type != AnimationType.PlayerSuited && type != AnimationType.PlayerUnsuited)
|
||||
{
|
||||
_bodyAnim.SetTrigger("Playing");
|
||||
_anim.SetTrigger("Playing");
|
||||
}
|
||||
else
|
||||
{
|
||||
// Avoids "jumping" when exiting instrument and putting on suit
|
||||
_bodyAnim.SetTrigger("Grounded");
|
||||
_anim.SetTrigger("Grounded");
|
||||
}
|
||||
_netAnim.animator = _anim; // Probably not needed.
|
||||
Mirror.RebuildFloatParams();
|
||||
for (var i = 0; i < _anim.parameterCount; i++)
|
||||
{
|
||||
_netAnim.SetParameterAutoSend(i, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -4,69 +4,69 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.Animation
|
||||
{
|
||||
public class CrouchSync : QSBNetworkBehaviour
|
||||
{
|
||||
public AnimFloatParam CrouchParam { get; } = new AnimFloatParam();
|
||||
public class CrouchSync : QSBNetworkBehaviour
|
||||
{
|
||||
public AnimFloatParam CrouchParam { get; } = new AnimFloatParam();
|
||||
|
||||
private const float CrouchSendInterval = 0.1f;
|
||||
private const float CrouchChargeThreshold = 0.01f;
|
||||
private const float CrouchSmoothTime = 0.05f;
|
||||
private const int CrouchLayerIndex = 1;
|
||||
private const float CrouchSendInterval = 0.1f;
|
||||
private const float CrouchChargeThreshold = 0.01f;
|
||||
private const float CrouchSmoothTime = 0.05f;
|
||||
private const int CrouchLayerIndex = 1;
|
||||
|
||||
private float _sendTimer;
|
||||
private float _lastSentJumpChargeFraction;
|
||||
private float _sendTimer;
|
||||
private float _lastSentJumpChargeFraction;
|
||||
|
||||
private AnimationSync _animationSync;
|
||||
private PlayerCharacterController _playerController;
|
||||
private Animator _bodyAnim;
|
||||
private AnimationSync _animationSync;
|
||||
private PlayerCharacterController _playerController;
|
||||
private Animator _bodyAnim;
|
||||
|
||||
public void Init(AnimationSync animationSync, PlayerCharacterController playerController, Animator bodyAnim)
|
||||
{
|
||||
_animationSync = animationSync;
|
||||
_playerController = playerController;
|
||||
_bodyAnim = bodyAnim;
|
||||
}
|
||||
public void Init(AnimationSync animationSync, PlayerCharacterController playerController, Animator bodyAnim)
|
||||
{
|
||||
_animationSync = animationSync;
|
||||
_playerController = playerController;
|
||||
_bodyAnim = bodyAnim;
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
if (IsLocalPlayer)
|
||||
{
|
||||
SyncLocalCrouch();
|
||||
return;
|
||||
}
|
||||
SyncRemoteCrouch();
|
||||
}
|
||||
private void Update()
|
||||
{
|
||||
if (IsLocalPlayer)
|
||||
{
|
||||
SyncLocalCrouch();
|
||||
return;
|
||||
}
|
||||
SyncRemoteCrouch();
|
||||
}
|
||||
|
||||
private void SyncLocalCrouch()
|
||||
{
|
||||
if (_playerController == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_sendTimer += Time.unscaledDeltaTime;
|
||||
if (_sendTimer < CrouchSendInterval)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var jumpChargeFraction = _playerController.GetJumpChargeFraction();
|
||||
if (Math.Abs(jumpChargeFraction - _lastSentJumpChargeFraction) < CrouchChargeThreshold)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_animationSync.SendCrouch(jumpChargeFraction);
|
||||
_lastSentJumpChargeFraction = jumpChargeFraction;
|
||||
_sendTimer = 0;
|
||||
}
|
||||
private void SyncLocalCrouch()
|
||||
{
|
||||
if (_playerController == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_sendTimer += Time.unscaledDeltaTime;
|
||||
if (_sendTimer < CrouchSendInterval)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var jumpChargeFraction = _playerController.GetJumpChargeFraction();
|
||||
if (Math.Abs(jumpChargeFraction - _lastSentJumpChargeFraction) < CrouchChargeThreshold)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_animationSync.SendCrouch(jumpChargeFraction);
|
||||
_lastSentJumpChargeFraction = jumpChargeFraction;
|
||||
_sendTimer = 0;
|
||||
}
|
||||
|
||||
private void SyncRemoteCrouch()
|
||||
{
|
||||
if (_bodyAnim == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
CrouchParam.Smooth(CrouchSmoothTime);
|
||||
var jumpChargeFraction = CrouchParam.Current;
|
||||
_bodyAnim.SetLayerWeight(CrouchLayerIndex, jumpChargeFraction);
|
||||
}
|
||||
}
|
||||
private void SyncRemoteCrouch()
|
||||
{
|
||||
if (_bodyAnim == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
CrouchParam.Smooth(CrouchSmoothTime);
|
||||
var jumpChargeFraction = CrouchParam.Current;
|
||||
_bodyAnim.SetLayerWeight(CrouchLayerIndex, jumpChargeFraction);
|
||||
}
|
||||
}
|
||||
}
|
@ -5,370 +5,370 @@ using UnityEngine.Networking;
|
||||
|
||||
namespace QSB.Animation
|
||||
{
|
||||
// Cleaned up unity code. UNET is so broken I gave up and fixed it myself.
|
||||
// Cleaned up unity code. UNET is so broken I gave up and fixed it myself.
|
||||
|
||||
class QSBNetworkAnimator : QSBNetworkBehaviour
|
||||
{
|
||||
private static QSBAnimationMessage AnimationMessage = new QSBAnimationMessage();
|
||||
private static QSBAnimationParametersMessage ParametersMessage = new QSBAnimationParametersMessage();
|
||||
private static QSBAnimationTriggerMessage TriggersMessage = new QSBAnimationTriggerMessage();
|
||||
class QSBNetworkAnimator : QSBNetworkBehaviour
|
||||
{
|
||||
private static QSBAnimationMessage AnimationMessage = new QSBAnimationMessage();
|
||||
private static QSBAnimationParametersMessage ParametersMessage = new QSBAnimationParametersMessage();
|
||||
private static QSBAnimationTriggerMessage TriggersMessage = new QSBAnimationTriggerMessage();
|
||||
|
||||
private Animator m_Animator;
|
||||
private uint m_ParameterSendBits;
|
||||
private int m_AnimationHash;
|
||||
private int m_TransitionHash;
|
||||
private NetworkWriter m_ParameterWriter;
|
||||
private float m_SendTimer;
|
||||
private Animator m_Animator;
|
||||
private uint m_ParameterSendBits;
|
||||
private int m_AnimationHash;
|
||||
private int m_TransitionHash;
|
||||
private NetworkWriter m_ParameterWriter;
|
||||
private float m_SendTimer;
|
||||
|
||||
public Animator animator
|
||||
{
|
||||
get
|
||||
{
|
||||
return m_Animator;
|
||||
}
|
||||
set
|
||||
{
|
||||
m_Animator = value;
|
||||
m_ParameterSendBits = 0U;
|
||||
}
|
||||
}
|
||||
public Animator animator
|
||||
{
|
||||
get
|
||||
{
|
||||
return m_Animator;
|
||||
}
|
||||
set
|
||||
{
|
||||
m_Animator = value;
|
||||
m_ParameterSendBits = 0U;
|
||||
}
|
||||
}
|
||||
|
||||
public void SetParameterAutoSend(int index, bool value)
|
||||
{
|
||||
if (value)
|
||||
m_ParameterSendBits |= (uint)(1 << index);
|
||||
else
|
||||
m_ParameterSendBits &= (uint)~(1 << index);
|
||||
}
|
||||
public void SetParameterAutoSend(int index, bool value)
|
||||
{
|
||||
if (value)
|
||||
m_ParameterSendBits |= (uint)(1 << index);
|
||||
else
|
||||
m_ParameterSendBits &= (uint)~(1 << index);
|
||||
}
|
||||
|
||||
public bool GetParameterAutoSend(int index)
|
||||
{
|
||||
return ((int)m_ParameterSendBits & 1 << index) != 0;
|
||||
}
|
||||
public bool GetParameterAutoSend(int index)
|
||||
{
|
||||
return ((int)m_ParameterSendBits & 1 << index) != 0;
|
||||
}
|
||||
|
||||
public override void OnStartAuthority()
|
||||
{
|
||||
m_ParameterWriter = new NetworkWriter();
|
||||
}
|
||||
public override void OnStartAuthority()
|
||||
{
|
||||
m_ParameterWriter = new NetworkWriter();
|
||||
}
|
||||
|
||||
private void FixedUpdate()
|
||||
{
|
||||
if (m_ParameterWriter == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
CheckSendRate();
|
||||
if (!CheckAnimStateChanged(out var stateHash, out var normalizedTime))
|
||||
{
|
||||
return;
|
||||
}
|
||||
var animationMessage = new QSBAnimationMessage
|
||||
{
|
||||
netId = NetId,
|
||||
stateHash = stateHash,
|
||||
normalizedTime = normalizedTime
|
||||
};
|
||||
private void FixedUpdate()
|
||||
{
|
||||
if (m_ParameterWriter == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
CheckSendRate();
|
||||
if (!CheckAnimStateChanged(out var stateHash, out var normalizedTime))
|
||||
{
|
||||
return;
|
||||
}
|
||||
var animationMessage = new QSBAnimationMessage
|
||||
{
|
||||
netId = NetId,
|
||||
stateHash = stateHash,
|
||||
normalizedTime = normalizedTime
|
||||
};
|
||||
|
||||
m_ParameterWriter.SeekZero();
|
||||
WriteParameters(m_ParameterWriter, false);
|
||||
animationMessage.parameters = m_ParameterWriter.ToArray();
|
||||
m_ParameterWriter.SeekZero();
|
||||
WriteParameters(m_ParameterWriter, false);
|
||||
animationMessage.parameters = m_ParameterWriter.ToArray();
|
||||
|
||||
if (HasAuthority || QSBClientScene.readyConnection != null)
|
||||
{
|
||||
QSBClientScene.readyConnection.Send(40, animationMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!IsServer || LocalPlayerAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkServer.SendToReady(gameObject, 40, animationMessage);
|
||||
}
|
||||
}
|
||||
if (HasAuthority || QSBClientScene.readyConnection != null)
|
||||
{
|
||||
QSBClientScene.readyConnection.Send(40, animationMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!IsServer || LocalPlayerAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkServer.SendToReady(gameObject, 40, animationMessage);
|
||||
}
|
||||
}
|
||||
|
||||
private bool CheckAnimStateChanged(out int stateHash, out float normalizedTime)
|
||||
{
|
||||
stateHash = 0;
|
||||
normalizedTime = 0.0f;
|
||||
if (m_Animator.IsInTransition(0))
|
||||
{
|
||||
var animatorTransitionInfo = m_Animator.GetAnimatorTransitionInfo(0);
|
||||
if (animatorTransitionInfo.fullPathHash == m_TransitionHash)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
m_TransitionHash = animatorTransitionInfo.fullPathHash;
|
||||
m_AnimationHash = 0;
|
||||
return true;
|
||||
}
|
||||
var animatorStateInfo = m_Animator.GetCurrentAnimatorStateInfo(0);
|
||||
if (animatorStateInfo.fullPathHash == m_AnimationHash)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (m_AnimationHash != 0)
|
||||
{
|
||||
stateHash = animatorStateInfo.fullPathHash;
|
||||
normalizedTime = animatorStateInfo.normalizedTime;
|
||||
}
|
||||
m_TransitionHash = 0;
|
||||
m_AnimationHash = animatorStateInfo.fullPathHash;
|
||||
return true;
|
||||
}
|
||||
private bool CheckAnimStateChanged(out int stateHash, out float normalizedTime)
|
||||
{
|
||||
stateHash = 0;
|
||||
normalizedTime = 0.0f;
|
||||
if (m_Animator.IsInTransition(0))
|
||||
{
|
||||
var animatorTransitionInfo = m_Animator.GetAnimatorTransitionInfo(0);
|
||||
if (animatorTransitionInfo.fullPathHash == m_TransitionHash)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
m_TransitionHash = animatorTransitionInfo.fullPathHash;
|
||||
m_AnimationHash = 0;
|
||||
return true;
|
||||
}
|
||||
var animatorStateInfo = m_Animator.GetCurrentAnimatorStateInfo(0);
|
||||
if (animatorStateInfo.fullPathHash == m_AnimationHash)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (m_AnimationHash != 0)
|
||||
{
|
||||
stateHash = animatorStateInfo.fullPathHash;
|
||||
normalizedTime = animatorStateInfo.normalizedTime;
|
||||
}
|
||||
m_TransitionHash = 0;
|
||||
m_AnimationHash = animatorStateInfo.fullPathHash;
|
||||
return true;
|
||||
}
|
||||
|
||||
private void CheckSendRate()
|
||||
{
|
||||
if (GetNetworkSendInterval() == 0.0 || m_SendTimer >= Time.time)
|
||||
{
|
||||
return;
|
||||
}
|
||||
m_SendTimer = Time.time + GetNetworkSendInterval();
|
||||
var parametersMessage = new QSBAnimationParametersMessage
|
||||
{
|
||||
netId = NetId
|
||||
};
|
||||
m_ParameterWriter.SeekZero();
|
||||
WriteParameters(m_ParameterWriter, true);
|
||||
parametersMessage.parameters = m_ParameterWriter.ToArray();
|
||||
if (HasAuthority && QSBClientScene.readyConnection != null)
|
||||
{
|
||||
QSBClientScene.readyConnection.Send(41, parametersMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!IsServer || LocalPlayerAuthority)
|
||||
return;
|
||||
QSBNetworkServer.SendToReady(gameObject, 41, parametersMessage);
|
||||
}
|
||||
}
|
||||
private void CheckSendRate()
|
||||
{
|
||||
if (GetNetworkSendInterval() == 0.0 || m_SendTimer >= Time.time)
|
||||
{
|
||||
return;
|
||||
}
|
||||
m_SendTimer = Time.time + GetNetworkSendInterval();
|
||||
var parametersMessage = new QSBAnimationParametersMessage
|
||||
{
|
||||
netId = NetId
|
||||
};
|
||||
m_ParameterWriter.SeekZero();
|
||||
WriteParameters(m_ParameterWriter, true);
|
||||
parametersMessage.parameters = m_ParameterWriter.ToArray();
|
||||
if (HasAuthority && QSBClientScene.readyConnection != null)
|
||||
{
|
||||
QSBClientScene.readyConnection.Send(41, parametersMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!IsServer || LocalPlayerAuthority)
|
||||
return;
|
||||
QSBNetworkServer.SendToReady(gameObject, 41, parametersMessage);
|
||||
}
|
||||
}
|
||||
|
||||
internal void HandleAnimMsg(QSBAnimationMessage msg, NetworkReader reader)
|
||||
{
|
||||
if (HasAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (msg.stateHash != 0)
|
||||
{
|
||||
m_Animator.Play(msg.stateHash, 0, msg.normalizedTime);
|
||||
}
|
||||
ReadParameters(reader, false);
|
||||
}
|
||||
internal void HandleAnimMsg(QSBAnimationMessage msg, NetworkReader reader)
|
||||
{
|
||||
if (HasAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (msg.stateHash != 0)
|
||||
{
|
||||
m_Animator.Play(msg.stateHash, 0, msg.normalizedTime);
|
||||
}
|
||||
ReadParameters(reader, false);
|
||||
}
|
||||
|
||||
internal void HandleAnimParamsMsg(QSBAnimationParametersMessage msg, NetworkReader reader)
|
||||
{
|
||||
if (HasAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
ReadParameters(reader, true);
|
||||
}
|
||||
internal void HandleAnimParamsMsg(QSBAnimationParametersMessage msg, NetworkReader reader)
|
||||
{
|
||||
if (HasAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
ReadParameters(reader, true);
|
||||
}
|
||||
|
||||
internal void HandleAnimTriggerMsg(int hash)
|
||||
{
|
||||
m_Animator.SetTrigger(hash);
|
||||
}
|
||||
internal void HandleAnimTriggerMsg(int hash)
|
||||
{
|
||||
m_Animator.SetTrigger(hash);
|
||||
}
|
||||
|
||||
private void WriteParameters(NetworkWriter writer, bool autoSend)
|
||||
{
|
||||
for (int index = 0; index < m_Animator.parameters.Length; ++index)
|
||||
{
|
||||
if (!autoSend || GetParameterAutoSend(index))
|
||||
{
|
||||
var parameter = m_Animator.parameters[index];
|
||||
switch (parameter.type)
|
||||
{
|
||||
case AnimatorControllerParameterType.Int:
|
||||
writer.WritePackedUInt32((uint)m_Animator.GetInteger(parameter.nameHash));
|
||||
break;
|
||||
case AnimatorControllerParameterType.Float:
|
||||
writer.Write(m_Animator.GetFloat(parameter.nameHash));
|
||||
break;
|
||||
case AnimatorControllerParameterType.Bool:
|
||||
writer.Write(m_Animator.GetBool(parameter.nameHash));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
private void WriteParameters(NetworkWriter writer, bool autoSend)
|
||||
{
|
||||
for (int index = 0; index < m_Animator.parameters.Length; ++index)
|
||||
{
|
||||
if (!autoSend || GetParameterAutoSend(index))
|
||||
{
|
||||
var parameter = m_Animator.parameters[index];
|
||||
switch (parameter.type)
|
||||
{
|
||||
case AnimatorControllerParameterType.Int:
|
||||
writer.WritePackedUInt32((uint)m_Animator.GetInteger(parameter.nameHash));
|
||||
break;
|
||||
case AnimatorControllerParameterType.Float:
|
||||
writer.Write(m_Animator.GetFloat(parameter.nameHash));
|
||||
break;
|
||||
case AnimatorControllerParameterType.Bool:
|
||||
writer.Write(m_Animator.GetBool(parameter.nameHash));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void ReadParameters(NetworkReader reader, bool autoSend)
|
||||
{
|
||||
for (int index = 0; index < m_Animator.parameters.Length; ++index)
|
||||
{
|
||||
if (!autoSend || GetParameterAutoSend(index))
|
||||
{
|
||||
var parameter = m_Animator.parameters[index];
|
||||
if (reader.Length == reader.Position)
|
||||
{
|
||||
return;
|
||||
}
|
||||
switch (parameter.type)
|
||||
{
|
||||
case AnimatorControllerParameterType.Int:
|
||||
var num = (int)reader.ReadPackedUInt32();
|
||||
m_Animator.SetInteger(parameter.nameHash, num);
|
||||
break;
|
||||
case AnimatorControllerParameterType.Float:
|
||||
var single = reader.ReadSingle();
|
||||
m_Animator.SetFloat(parameter.nameHash, single);
|
||||
break;
|
||||
case AnimatorControllerParameterType.Bool:
|
||||
var flag = reader.ReadBoolean();
|
||||
m_Animator.SetBool(parameter.nameHash, flag);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
private void ReadParameters(NetworkReader reader, bool autoSend)
|
||||
{
|
||||
for (int index = 0; index < m_Animator.parameters.Length; ++index)
|
||||
{
|
||||
if (!autoSend || GetParameterAutoSend(index))
|
||||
{
|
||||
var parameter = m_Animator.parameters[index];
|
||||
if (reader.Length == reader.Position)
|
||||
{
|
||||
return;
|
||||
}
|
||||
switch (parameter.type)
|
||||
{
|
||||
case AnimatorControllerParameterType.Int:
|
||||
var num = (int)reader.ReadPackedUInt32();
|
||||
m_Animator.SetInteger(parameter.nameHash, num);
|
||||
break;
|
||||
case AnimatorControllerParameterType.Float:
|
||||
var single = reader.ReadSingle();
|
||||
m_Animator.SetFloat(parameter.nameHash, single);
|
||||
break;
|
||||
case AnimatorControllerParameterType.Bool:
|
||||
var flag = reader.ReadBoolean();
|
||||
m_Animator.SetBool(parameter.nameHash, flag);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override bool OnSerialize(NetworkWriter writer, bool forceAll)
|
||||
{
|
||||
if (!forceAll)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (m_Animator.IsInTransition(0))
|
||||
{
|
||||
var animatorStateInfo = m_Animator.GetNextAnimatorStateInfo(0);
|
||||
writer.Write(animatorStateInfo.fullPathHash);
|
||||
writer.Write(animatorStateInfo.normalizedTime);
|
||||
}
|
||||
else
|
||||
{
|
||||
var animatorStateInfo = m_Animator.GetCurrentAnimatorStateInfo(0);
|
||||
writer.Write(animatorStateInfo.fullPathHash);
|
||||
writer.Write(animatorStateInfo.normalizedTime);
|
||||
}
|
||||
WriteParameters(writer, false);
|
||||
return true;
|
||||
}
|
||||
public override bool OnSerialize(NetworkWriter writer, bool forceAll)
|
||||
{
|
||||
if (!forceAll)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (m_Animator.IsInTransition(0))
|
||||
{
|
||||
var animatorStateInfo = m_Animator.GetNextAnimatorStateInfo(0);
|
||||
writer.Write(animatorStateInfo.fullPathHash);
|
||||
writer.Write(animatorStateInfo.normalizedTime);
|
||||
}
|
||||
else
|
||||
{
|
||||
var animatorStateInfo = m_Animator.GetCurrentAnimatorStateInfo(0);
|
||||
writer.Write(animatorStateInfo.fullPathHash);
|
||||
writer.Write(animatorStateInfo.normalizedTime);
|
||||
}
|
||||
WriteParameters(writer, false);
|
||||
return true;
|
||||
}
|
||||
|
||||
public override void OnDeserialize(NetworkReader reader, bool initialState)
|
||||
{
|
||||
if (!initialState)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var stateNameHash = reader.ReadInt32();
|
||||
var normalizedTime = reader.ReadSingle();
|
||||
ReadParameters(reader, false);
|
||||
m_Animator.Play(stateNameHash, 0, normalizedTime);
|
||||
}
|
||||
public override void OnDeserialize(NetworkReader reader, bool initialState)
|
||||
{
|
||||
if (!initialState)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var stateNameHash = reader.ReadInt32();
|
||||
var normalizedTime = reader.ReadSingle();
|
||||
ReadParameters(reader, false);
|
||||
m_Animator.Play(stateNameHash, 0, normalizedTime);
|
||||
}
|
||||
|
||||
public void SetTrigger(string triggerName)
|
||||
{
|
||||
SetTrigger(Animator.StringToHash(triggerName));
|
||||
}
|
||||
public void SetTrigger(string triggerName)
|
||||
{
|
||||
SetTrigger(Animator.StringToHash(triggerName));
|
||||
}
|
||||
|
||||
public void SetTrigger(int hash)
|
||||
{
|
||||
var animationTriggerMessage = new QSBAnimationTriggerMessage
|
||||
{
|
||||
netId = NetId,
|
||||
hash = hash
|
||||
};
|
||||
if (HasAuthority && LocalPlayerAuthority)
|
||||
{
|
||||
if (QSBNetworkClient.allClients.Count <= 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var readyConnection = QSBClientScene.readyConnection;
|
||||
if (readyConnection == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
readyConnection.Send(42, animationTriggerMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!IsServer || LocalPlayerAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkServer.SendToReady(gameObject, 42, animationTriggerMessage);
|
||||
}
|
||||
}
|
||||
public void SetTrigger(int hash)
|
||||
{
|
||||
var animationTriggerMessage = new QSBAnimationTriggerMessage
|
||||
{
|
||||
netId = NetId,
|
||||
hash = hash
|
||||
};
|
||||
if (HasAuthority && LocalPlayerAuthority)
|
||||
{
|
||||
if (QSBNetworkClient.allClients.Count <= 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var readyConnection = QSBClientScene.readyConnection;
|
||||
if (readyConnection == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
readyConnection.Send(42, animationTriggerMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!IsServer || LocalPlayerAuthority)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkServer.SendToReady(gameObject, 42, animationTriggerMessage);
|
||||
}
|
||||
}
|
||||
|
||||
internal static void OnAnimationServerMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(AnimationMessage);
|
||||
var localObject = QSBNetworkServer.FindLocalObject(AnimationMessage.netId);
|
||||
if (localObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
var reader = new NetworkReader(AnimationMessage.parameters);
|
||||
component?.HandleAnimMsg(AnimationMessage, reader);
|
||||
QSBNetworkServer.SendToReady(localObject, 40, AnimationMessage);
|
||||
}
|
||||
internal static void OnAnimationServerMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(AnimationMessage);
|
||||
var localObject = QSBNetworkServer.FindLocalObject(AnimationMessage.netId);
|
||||
if (localObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
var reader = new NetworkReader(AnimationMessage.parameters);
|
||||
component?.HandleAnimMsg(AnimationMessage, reader);
|
||||
QSBNetworkServer.SendToReady(localObject, 40, AnimationMessage);
|
||||
}
|
||||
|
||||
internal static void OnAnimationParametersServerMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(ParametersMessage);
|
||||
var localObject = QSBNetworkServer.FindLocalObject(ParametersMessage.netId);
|
||||
if (localObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
var reader = new NetworkReader(ParametersMessage.parameters);
|
||||
component?.HandleAnimParamsMsg(ParametersMessage, reader);
|
||||
QSBNetworkServer.SendToReady(localObject, 41, ParametersMessage);
|
||||
}
|
||||
internal static void OnAnimationParametersServerMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(ParametersMessage);
|
||||
var localObject = QSBNetworkServer.FindLocalObject(ParametersMessage.netId);
|
||||
if (localObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
var reader = new NetworkReader(ParametersMessage.parameters);
|
||||
component?.HandleAnimParamsMsg(ParametersMessage, reader);
|
||||
QSBNetworkServer.SendToReady(localObject, 41, ParametersMessage);
|
||||
}
|
||||
|
||||
internal static void OnAnimationTriggerServerMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(TriggersMessage);
|
||||
var localObject = QSBNetworkServer.FindLocalObject(TriggersMessage.netId);
|
||||
if (localObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
component?.HandleAnimTriggerMsg(TriggersMessage.hash);
|
||||
QSBNetworkServer.SendToReady(localObject, 42, TriggersMessage);
|
||||
}
|
||||
internal static void OnAnimationTriggerServerMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(TriggersMessage);
|
||||
var localObject = QSBNetworkServer.FindLocalObject(TriggersMessage.netId);
|
||||
if (localObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
component?.HandleAnimTriggerMsg(TriggersMessage.hash);
|
||||
QSBNetworkServer.SendToReady(localObject, 42, TriggersMessage);
|
||||
}
|
||||
|
||||
internal static void OnAnimationClientMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(AnimationMessage);
|
||||
var localObject = QSBClientScene.FindLocalObject(AnimationMessage.netId);
|
||||
if (localObject == null)
|
||||
return;
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
if (component == null)
|
||||
return;
|
||||
var reader = new NetworkReader(AnimationMessage.parameters);
|
||||
component.HandleAnimMsg(AnimationMessage, reader);
|
||||
}
|
||||
internal static void OnAnimationClientMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(AnimationMessage);
|
||||
var localObject = QSBClientScene.FindLocalObject(AnimationMessage.netId);
|
||||
if (localObject == null)
|
||||
return;
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
if (component == null)
|
||||
return;
|
||||
var reader = new NetworkReader(AnimationMessage.parameters);
|
||||
component.HandleAnimMsg(AnimationMessage, reader);
|
||||
}
|
||||
|
||||
internal static void OnAnimationParametersClientMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(ParametersMessage);
|
||||
var localObject = QSBClientScene.FindLocalObject(ParametersMessage.netId);
|
||||
if (localObject == null)
|
||||
return;
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
if (component == null)
|
||||
return;
|
||||
var reader = new NetworkReader(ParametersMessage.parameters);
|
||||
component.HandleAnimParamsMsg(ParametersMessage, reader);
|
||||
}
|
||||
internal static void OnAnimationParametersClientMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(ParametersMessage);
|
||||
var localObject = QSBClientScene.FindLocalObject(ParametersMessage.netId);
|
||||
if (localObject == null)
|
||||
return;
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
if (component == null)
|
||||
return;
|
||||
var reader = new NetworkReader(ParametersMessage.parameters);
|
||||
component.HandleAnimParamsMsg(ParametersMessage, reader);
|
||||
}
|
||||
|
||||
internal static void OnAnimationTriggerClientMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(TriggersMessage);
|
||||
var localObject = QSBClientScene.FindLocalObject(TriggersMessage.netId);
|
||||
if (localObject == null)
|
||||
return;
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
if (component == null)
|
||||
return;
|
||||
component.HandleAnimTriggerMsg(TriggersMessage.hash);
|
||||
}
|
||||
}
|
||||
internal static void OnAnimationTriggerClientMessage(QSBNetworkMessage netMsg)
|
||||
{
|
||||
netMsg.ReadMessage(TriggersMessage);
|
||||
var localObject = QSBClientScene.FindLocalObject(TriggersMessage.netId);
|
||||
if (localObject == null)
|
||||
return;
|
||||
var component = localObject.GetComponent<QSBNetworkAnimator>();
|
||||
if (component == null)
|
||||
return;
|
||||
component.HandleAnimTriggerMsg(TriggersMessage.hash);
|
||||
}
|
||||
}
|
||||
}
|
@ -5,64 +5,64 @@ using QSB.TransformSync;
|
||||
|
||||
namespace QSB.EventsCore
|
||||
{
|
||||
public abstract class QSBEvent<T> : IQSBEvent where T : PlayerMessage, new()
|
||||
{
|
||||
public abstract EventType Type { get; }
|
||||
public uint LocalPlayerId => QSBPlayerManager.LocalPlayerId;
|
||||
private readonly MessageHandler<T> _eventHandler;
|
||||
public abstract class QSBEvent<T> : IQSBEvent where T : PlayerMessage, new()
|
||||
{
|
||||
public abstract EventType Type { get; }
|
||||
public uint LocalPlayerId => QSBPlayerManager.LocalPlayerId;
|
||||
private readonly MessageHandler<T> _eventHandler;
|
||||
|
||||
protected QSBEvent()
|
||||
{
|
||||
_eventHandler = new MessageHandler<T>(Type);
|
||||
_eventHandler.OnClientReceiveMessage += OnClientReceive;
|
||||
_eventHandler.OnServerReceiveMessage += OnServerReceive;
|
||||
}
|
||||
protected QSBEvent()
|
||||
{
|
||||
_eventHandler = new MessageHandler<T>(Type);
|
||||
_eventHandler.OnClientReceiveMessage += OnClientReceive;
|
||||
_eventHandler.OnServerReceiveMessage += OnServerReceive;
|
||||
}
|
||||
|
||||
public abstract void SetupListener();
|
||||
public abstract void SetupListener();
|
||||
|
||||
public abstract void CloseListener();
|
||||
public abstract void CloseListener();
|
||||
|
||||
public virtual void OnReceiveRemote(T message)
|
||||
{
|
||||
}
|
||||
public virtual void OnReceiveRemote(T message)
|
||||
{
|
||||
}
|
||||
|
||||
public virtual void OnReceiveLocal(T message)
|
||||
{
|
||||
}
|
||||
public virtual void OnReceiveLocal(T message)
|
||||
{
|
||||
}
|
||||
|
||||
public virtual void OnServerReceive(T message)
|
||||
{
|
||||
_eventHandler.SendToAll(message);
|
||||
}
|
||||
public virtual void OnServerReceive(T message)
|
||||
{
|
||||
_eventHandler.SendToAll(message);
|
||||
}
|
||||
|
||||
public void SendEvent(T message)
|
||||
{
|
||||
message.FromId = QSBPlayerManager.LocalPlayerId;
|
||||
QSB.Helper.Events.Unity.RunWhen(() => PlayerTransformSync.LocalInstance != null, () => Send(message));
|
||||
}
|
||||
public void SendEvent(T message)
|
||||
{
|
||||
message.FromId = QSBPlayerManager.LocalPlayerId;
|
||||
QSB.Helper.Events.Unity.RunWhen(() => PlayerTransformSync.LocalInstance != null, () => Send(message));
|
||||
}
|
||||
|
||||
private void Send(T message)
|
||||
{
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
_eventHandler.SendToAll(message);
|
||||
}
|
||||
else
|
||||
{
|
||||
_eventHandler.SendToServer(message);
|
||||
}
|
||||
}
|
||||
private void Send(T message)
|
||||
{
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
_eventHandler.SendToAll(message);
|
||||
}
|
||||
else
|
||||
{
|
||||
_eventHandler.SendToServer(message);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnClientReceive(T message)
|
||||
{
|
||||
if (message.FromId == QSBPlayerManager.LocalPlayerId ||
|
||||
QSBPlayerManager.IsBelongingToLocalPlayer(message.AboutId))
|
||||
{
|
||||
OnReceiveLocal(message);
|
||||
return;
|
||||
}
|
||||
private void OnClientReceive(T message)
|
||||
{
|
||||
if (message.FromId == QSBPlayerManager.LocalPlayerId ||
|
||||
QSBPlayerManager.IsBelongingToLocalPlayer(message.AboutId))
|
||||
{
|
||||
OnReceiveLocal(message);
|
||||
return;
|
||||
}
|
||||
|
||||
OnReceiveRemote(message);
|
||||
}
|
||||
}
|
||||
OnReceiveRemote(message);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -4,37 +4,37 @@ using QSB.WorldSync;
|
||||
|
||||
namespace QSB.GeyserSync
|
||||
{
|
||||
public class QSBGeyser : WorldObject
|
||||
{
|
||||
private GeyserController _geyserController;
|
||||
public class QSBGeyser : WorldObject
|
||||
{
|
||||
private GeyserController _geyserController;
|
||||
|
||||
public void Init(GeyserController geyserController, int id)
|
||||
{
|
||||
ObjectId = id;
|
||||
_geyserController = geyserController;
|
||||
public void Init(GeyserController geyserController, int id)
|
||||
{
|
||||
ObjectId = id;
|
||||
_geyserController = geyserController;
|
||||
|
||||
geyserController.OnGeyserActivateEvent += () => HandleEvent(true);
|
||||
geyserController.OnGeyserDeactivateEvent += () => HandleEvent(false);
|
||||
}
|
||||
geyserController.OnGeyserActivateEvent += () => HandleEvent(true);
|
||||
geyserController.OnGeyserDeactivateEvent += () => HandleEvent(false);
|
||||
}
|
||||
|
||||
private void HandleEvent(bool state)
|
||||
{
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
GlobalMessenger<int, bool>.FireEvent(EventNames.QSBGeyserState, ObjectId, state);
|
||||
}
|
||||
}
|
||||
private void HandleEvent(bool state)
|
||||
{
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
GlobalMessenger<int, bool>.FireEvent(EventNames.QSBGeyserState, ObjectId, state);
|
||||
}
|
||||
}
|
||||
|
||||
public void SetState(bool state)
|
||||
{
|
||||
if (state)
|
||||
{
|
||||
_geyserController?.ActivateGeyser();
|
||||
}
|
||||
else
|
||||
{
|
||||
_geyserController?.DeactivateGeyser();
|
||||
}
|
||||
}
|
||||
}
|
||||
public void SetState(bool state)
|
||||
{
|
||||
if (state)
|
||||
{
|
||||
_geyserController?.ActivateGeyser();
|
||||
}
|
||||
else
|
||||
{
|
||||
_geyserController?.DeactivateGeyser();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -8,68 +8,68 @@ using UnityEngine.Networking;
|
||||
|
||||
namespace QSB.Messaging
|
||||
{
|
||||
// Extend this to create new message handlers.
|
||||
public class MessageHandler<T> where T : MessageBase, new()
|
||||
{
|
||||
public event Action<T> OnClientReceiveMessage;
|
||||
public event Action<T> OnServerReceiveMessage;
|
||||
// Extend this to create new message handlers.
|
||||
public class MessageHandler<T> where T : MessageBase, new()
|
||||
{
|
||||
public event Action<T> OnClientReceiveMessage;
|
||||
public event Action<T> OnServerReceiveMessage;
|
||||
|
||||
private readonly EventType _eventType;
|
||||
private readonly EventType _eventType;
|
||||
|
||||
public MessageHandler(EventType eventType)
|
||||
{
|
||||
_eventType = eventType + MsgType.Highest + 1;
|
||||
if (QSBNetworkManager.Instance.IsReady)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else
|
||||
{
|
||||
QSBNetworkManager.Instance.OnNetworkManagerReady += Init;
|
||||
}
|
||||
}
|
||||
public MessageHandler(EventType eventType)
|
||||
{
|
||||
_eventType = eventType + MsgType.Highest + 1;
|
||||
if (QSBNetworkManager.Instance.IsReady)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else
|
||||
{
|
||||
QSBNetworkManager.Instance.OnNetworkManagerReady += Init;
|
||||
}
|
||||
}
|
||||
|
||||
private void Init()
|
||||
{
|
||||
var eventName = Enum.GetName(typeof(EventType), _eventType - 1 - MsgType.Highest).ToUpper();
|
||||
if (QSBNetworkServer.handlers.Keys.Contains((short)_eventType))
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - NetworkServer already contains a handler for EventType {_eventType}", MessageType.Warning);
|
||||
QSBNetworkServer.handlers.Remove((short)_eventType);
|
||||
}
|
||||
QSBNetworkServer.RegisterHandler((short)_eventType, OnServerReceiveMessageHandler);
|
||||
QSBNetworkManager.singleton.client.RegisterHandler((short)_eventType, OnClientReceiveMessageHandler);
|
||||
}
|
||||
private void Init()
|
||||
{
|
||||
var eventName = Enum.GetName(typeof(EventType), _eventType - 1 - MsgType.Highest).ToUpper();
|
||||
if (QSBNetworkServer.handlers.Keys.Contains((short)_eventType))
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - NetworkServer already contains a handler for EventType {_eventType}", MessageType.Warning);
|
||||
QSBNetworkServer.handlers.Remove((short)_eventType);
|
||||
}
|
||||
QSBNetworkServer.RegisterHandler((short)_eventType, OnServerReceiveMessageHandler);
|
||||
QSBNetworkManager.singleton.client.RegisterHandler((short)_eventType, OnClientReceiveMessageHandler);
|
||||
}
|
||||
|
||||
public void SendToAll(T message)
|
||||
{
|
||||
if (!QSBNetworkManager.Instance.IsReady)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkServer.SendToAll((short)_eventType, message);
|
||||
}
|
||||
public void SendToAll(T message)
|
||||
{
|
||||
if (!QSBNetworkManager.Instance.IsReady)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkServer.SendToAll((short)_eventType, message);
|
||||
}
|
||||
|
||||
public void SendToServer(T message)
|
||||
{
|
||||
if (!QSBNetworkManager.Instance.IsReady)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkManager.singleton.client.Send((short)_eventType, message);
|
||||
}
|
||||
public void SendToServer(T message)
|
||||
{
|
||||
if (!QSBNetworkManager.Instance.IsReady)
|
||||
{
|
||||
return;
|
||||
}
|
||||
QSBNetworkManager.singleton.client.Send((short)_eventType, message);
|
||||
}
|
||||
|
||||
private void OnClientReceiveMessageHandler(QSBNetworkMessage netMsg)
|
||||
{
|
||||
var message = netMsg.ReadMessage<T>();
|
||||
OnClientReceiveMessage?.Invoke(message);
|
||||
}
|
||||
private void OnClientReceiveMessageHandler(QSBNetworkMessage netMsg)
|
||||
{
|
||||
var message = netMsg.ReadMessage<T>();
|
||||
OnClientReceiveMessage?.Invoke(message);
|
||||
}
|
||||
|
||||
private void OnServerReceiveMessageHandler(QSBNetworkMessage netMsg)
|
||||
{
|
||||
var message = netMsg.ReadMessage<T>();
|
||||
OnServerReceiveMessage?.Invoke(message);
|
||||
}
|
||||
private void OnServerReceiveMessageHandler(QSBNetworkMessage netMsg)
|
||||
{
|
||||
var message = netMsg.ReadMessage<T>();
|
||||
OnServerReceiveMessage?.Invoke(message);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -5,28 +5,28 @@ using QSB.WorldSync.Events;
|
||||
|
||||
namespace QSB.OrbSync.Events
|
||||
{
|
||||
public class OrbSlotEvent : QSBEvent<BoolWorldObjectMessage>
|
||||
{
|
||||
public override EventType Type => EventType.OrbSlot;
|
||||
public class OrbSlotEvent : QSBEvent<BoolWorldObjectMessage>
|
||||
{
|
||||
public override EventType Type => EventType.OrbSlot;
|
||||
|
||||
public override void SetupListener() => GlobalMessenger<int, bool>.AddListener(EventNames.QSBOrbSlot, Handler);
|
||||
public override void SetupListener() => GlobalMessenger<int, bool>.AddListener(EventNames.QSBOrbSlot, Handler);
|
||||
|
||||
public override void CloseListener() => GlobalMessenger<int, bool>.RemoveListener(EventNames.QSBOrbSlot, Handler);
|
||||
public override void CloseListener() => GlobalMessenger<int, bool>.RemoveListener(EventNames.QSBOrbSlot, Handler);
|
||||
|
||||
private void Handler(int id, bool state) => SendEvent(CreateMessage(id, state));
|
||||
private void Handler(int id, bool state) => SendEvent(CreateMessage(id, state));
|
||||
|
||||
private BoolWorldObjectMessage CreateMessage(int id, bool state) => new BoolWorldObjectMessage
|
||||
{
|
||||
AboutId = LocalPlayerId,
|
||||
ObjectId = id,
|
||||
State = state
|
||||
};
|
||||
private BoolWorldObjectMessage CreateMessage(int id, bool state) => new BoolWorldObjectMessage
|
||||
{
|
||||
AboutId = LocalPlayerId,
|
||||
ObjectId = id,
|
||||
State = state
|
||||
};
|
||||
|
||||
public override void OnReceiveRemote(BoolWorldObjectMessage message)
|
||||
{
|
||||
DebugLog.DebugWrite($"receive slot {message.ObjectId} to {message.State}");
|
||||
var orbSlot = WorldRegistry.GetObject<QSBOrbSlot>(message.ObjectId);
|
||||
orbSlot?.SetState(message.State);
|
||||
}
|
||||
}
|
||||
public override void OnReceiveRemote(BoolWorldObjectMessage message)
|
||||
{
|
||||
DebugLog.DebugWrite($"receive slot {message.ObjectId} to {message.State}");
|
||||
var orbSlot = WorldRegistry.GetObject<QSBOrbSlot>(message.ObjectId);
|
||||
orbSlot?.SetState(message.State);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -8,79 +8,79 @@ using System.Linq;
|
||||
|
||||
namespace QSB.OrbSync.Events
|
||||
{
|
||||
public class OrbUserEvent : QSBEvent<WorldObjectMessage>
|
||||
{
|
||||
public override EventType Type => EventType.OrbUser;
|
||||
public class OrbUserEvent : QSBEvent<WorldObjectMessage>
|
||||
{
|
||||
public override EventType Type => EventType.OrbUser;
|
||||
|
||||
public override void SetupListener() => GlobalMessenger<int>.AddListener(EventNames.QSBOrbUser, Handler);
|
||||
public override void SetupListener() => GlobalMessenger<int>.AddListener(EventNames.QSBOrbUser, Handler);
|
||||
|
||||
public override void CloseListener() => GlobalMessenger<int>.RemoveListener(EventNames.QSBOrbUser, Handler);
|
||||
public override void CloseListener() => GlobalMessenger<int>.RemoveListener(EventNames.QSBOrbUser, Handler);
|
||||
|
||||
private void Handler(int id) => SendEvent(CreateMessage(id));
|
||||
private void Handler(int id) => SendEvent(CreateMessage(id));
|
||||
|
||||
private WorldObjectMessage CreateMessage(int id) => new WorldObjectMessage
|
||||
{
|
||||
AboutId = LocalPlayerId,
|
||||
ObjectId = id
|
||||
};
|
||||
private WorldObjectMessage CreateMessage(int id) => new WorldObjectMessage
|
||||
{
|
||||
AboutId = LocalPlayerId,
|
||||
ObjectId = id
|
||||
};
|
||||
|
||||
public override void OnServerReceive(WorldObjectMessage message)
|
||||
{
|
||||
var fromPlayer = QSBNetworkServer.connections.First(x => x.GetPlayer().PlayerId == message.FromId);
|
||||
foreach (var item in QSBNetworkServer.connections)
|
||||
{
|
||||
DebugLog.DebugWrite(item.GetPlayer().PlayerId.ToString());
|
||||
}
|
||||
if (WorldRegistry.OrbSyncList.Count == 0)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - OrbSyncList is empty. (ID {message.ObjectId})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (fromPlayer == null)
|
||||
{
|
||||
DebugLog.DebugWrite("Error - FromPlayer is null!", MessageType.Error);
|
||||
}
|
||||
var orb = WorldRegistry.OrbSyncList
|
||||
.First(x => x.AttachedOrb == WorldRegistry.OldOrbList[message.ObjectId]);
|
||||
if (orb == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - No orb found for user event. (ID {message.ObjectId})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
var orbIdentity = orb.GetComponent<QSBNetworkIdentity>();
|
||||
if (orbIdentity == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - Orb identity is null. (ID {message.ObjectId})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (orbIdentity.ClientAuthorityOwner != null && orbIdentity.ClientAuthorityOwner != fromPlayer)
|
||||
{
|
||||
DebugLog.DebugWrite($"Removed authority of orb {message.ObjectId} from {orbIdentity.ClientAuthorityOwner.GetPlayer().PlayerId}");
|
||||
orbIdentity.RemoveClientAuthority(orbIdentity.ClientAuthorityOwner);
|
||||
}
|
||||
DebugLog.DebugWrite($"Assigned authority of orb {message.ObjectId} to player {message.FromId}.");
|
||||
orbIdentity.AssignClientAuthority(fromPlayer);
|
||||
orb.enabled = true;
|
||||
}
|
||||
public override void OnServerReceive(WorldObjectMessage message)
|
||||
{
|
||||
var fromPlayer = QSBNetworkServer.connections.First(x => x.GetPlayer().PlayerId == message.FromId);
|
||||
foreach (var item in QSBNetworkServer.connections)
|
||||
{
|
||||
DebugLog.DebugWrite(item.GetPlayer().PlayerId.ToString());
|
||||
}
|
||||
if (WorldRegistry.OrbSyncList.Count == 0)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - OrbSyncList is empty. (ID {message.ObjectId})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (fromPlayer == null)
|
||||
{
|
||||
DebugLog.DebugWrite("Error - FromPlayer is null!", MessageType.Error);
|
||||
}
|
||||
var orb = WorldRegistry.OrbSyncList
|
||||
.First(x => x.AttachedOrb == WorldRegistry.OldOrbList[message.ObjectId]);
|
||||
if (orb == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - No orb found for user event. (ID {message.ObjectId})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
var orbIdentity = orb.GetComponent<QSBNetworkIdentity>();
|
||||
if (orbIdentity == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - Orb identity is null. (ID {message.ObjectId})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (orbIdentity.ClientAuthorityOwner != null && orbIdentity.ClientAuthorityOwner != fromPlayer)
|
||||
{
|
||||
DebugLog.DebugWrite($"Removed authority of orb {message.ObjectId} from {orbIdentity.ClientAuthorityOwner.GetPlayer().PlayerId}");
|
||||
orbIdentity.RemoveClientAuthority(orbIdentity.ClientAuthorityOwner);
|
||||
}
|
||||
DebugLog.DebugWrite($"Assigned authority of orb {message.ObjectId} to player {message.FromId}.");
|
||||
orbIdentity.AssignClientAuthority(fromPlayer);
|
||||
orb.enabled = true;
|
||||
}
|
||||
|
||||
public override void OnReceiveRemote(WorldObjectMessage message)
|
||||
{
|
||||
if (WorldRegistry.OrbSyncList.Count < message.ObjectId)
|
||||
{
|
||||
DebugLog.DebugWrite($"Error - Orb id {message.ObjectId} out of range of orb sync list {WorldRegistry.OrbSyncList.Count}.", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
var orb = WorldRegistry.OrbSyncList
|
||||
.First(x => x.AttachedOrb == WorldRegistry.OldOrbList[message.ObjectId]);
|
||||
orb.enabled = true;
|
||||
}
|
||||
public override void OnReceiveRemote(WorldObjectMessage message)
|
||||
{
|
||||
if (WorldRegistry.OrbSyncList.Count < message.ObjectId)
|
||||
{
|
||||
DebugLog.DebugWrite($"Error - Orb id {message.ObjectId} out of range of orb sync list {WorldRegistry.OrbSyncList.Count}.", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
var orb = WorldRegistry.OrbSyncList
|
||||
.First(x => x.AttachedOrb == WorldRegistry.OldOrbList[message.ObjectId]);
|
||||
orb.enabled = true;
|
||||
}
|
||||
|
||||
public override void OnReceiveLocal(WorldObjectMessage message)
|
||||
{
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
OnServerReceive(message);
|
||||
}
|
||||
}
|
||||
}
|
||||
public override void OnReceiveLocal(WorldObjectMessage message)
|
||||
{
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
OnServerReceive(message);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -7,54 +7,54 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.OrbSync
|
||||
{
|
||||
public class OrbManager : MonoBehaviour
|
||||
{
|
||||
public static OrbManager Instance { get; private set; }
|
||||
public class OrbManager : MonoBehaviour
|
||||
{
|
||||
public static OrbManager Instance { get; private set; }
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
Instance = this;
|
||||
}
|
||||
private void Awake()
|
||||
{
|
||||
Instance = this;
|
||||
}
|
||||
|
||||
private void BuildOrbSlots()
|
||||
{
|
||||
DebugLog.DebugWrite("Building QSBOrbSlots...", MessageType.Info);
|
||||
WorldRegistry.RemoveObjects<QSBOrbSlot>();
|
||||
var orbSlots = Resources.FindObjectsOfTypeAll<NomaiInterfaceSlot>();
|
||||
for (var id = 0; id < orbSlots.Length; id++)
|
||||
{
|
||||
var qsbOrbSlot = WorldRegistry.GetObject<QSBOrbSlot>(id) ?? new QSBOrbSlot();
|
||||
qsbOrbSlot.Init(orbSlots[id], id);
|
||||
}
|
||||
private void BuildOrbSlots()
|
||||
{
|
||||
DebugLog.DebugWrite("Building QSBOrbSlots...", MessageType.Info);
|
||||
WorldRegistry.RemoveObjects<QSBOrbSlot>();
|
||||
var orbSlots = Resources.FindObjectsOfTypeAll<NomaiInterfaceSlot>();
|
||||
for (var id = 0; id < orbSlots.Length; id++)
|
||||
{
|
||||
var qsbOrbSlot = WorldRegistry.GetObject<QSBOrbSlot>(id) ?? new QSBOrbSlot();
|
||||
qsbOrbSlot.Init(orbSlots[id], id);
|
||||
}
|
||||
|
||||
DebugLog.DebugWrite($"Finished orb slot build with {orbSlots.Length} slots.", MessageType.Success);
|
||||
}
|
||||
DebugLog.DebugWrite($"Finished orb slot build with {orbSlots.Length} slots.", MessageType.Success);
|
||||
}
|
||||
|
||||
public void BuildOrbs()
|
||||
{
|
||||
DebugLog.DebugWrite("Building orb syncs...", MessageType.Info);
|
||||
WorldRegistry.OldOrbList.Clear();
|
||||
WorldRegistry.OldOrbList = Resources.FindObjectsOfTypeAll<NomaiInterfaceOrb>().ToList();
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
DebugLog.DebugWrite("- Is server, instantiating orb prefabs.");
|
||||
WorldRegistry.OrbSyncList.ForEach(x => QSBNetworkServer.Destroy(x.gameObject));
|
||||
WorldRegistry.OrbSyncList.Clear();
|
||||
WorldRegistry.OldOrbList.ForEach(x => QSBNetworkServer.Spawn(Instantiate(QSBNetworkManager.Instance.OrbPrefab)));
|
||||
}
|
||||
DebugLog.DebugWrite($"Finished orb build with {WorldRegistry.OldOrbList.Count} orbs.", MessageType.Success);
|
||||
}
|
||||
public void BuildOrbs()
|
||||
{
|
||||
DebugLog.DebugWrite("Building orb syncs...", MessageType.Info);
|
||||
WorldRegistry.OldOrbList.Clear();
|
||||
WorldRegistry.OldOrbList = Resources.FindObjectsOfTypeAll<NomaiInterfaceOrb>().ToList();
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
DebugLog.DebugWrite("- Is server, instantiating orb prefabs.");
|
||||
WorldRegistry.OrbSyncList.ForEach(x => QSBNetworkServer.Destroy(x.gameObject));
|
||||
WorldRegistry.OrbSyncList.Clear();
|
||||
WorldRegistry.OldOrbList.ForEach(x => QSBNetworkServer.Spawn(Instantiate(QSBNetworkManager.Instance.OrbPrefab)));
|
||||
}
|
||||
DebugLog.DebugWrite($"Finished orb build with {WorldRegistry.OldOrbList.Count} orbs.", MessageType.Success);
|
||||
}
|
||||
|
||||
public void QueueBuildSlots()
|
||||
{
|
||||
DebugLog.DebugWrite("Queueing build of QSBOrbSlots...", MessageType.Info);
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSB.HasWokenUp, BuildOrbSlots);
|
||||
}
|
||||
public void QueueBuildSlots()
|
||||
{
|
||||
DebugLog.DebugWrite("Queueing build of QSBOrbSlots...", MessageType.Info);
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSB.HasWokenUp, BuildOrbSlots);
|
||||
}
|
||||
|
||||
public void QueueBuildOrbs()
|
||||
{
|
||||
DebugLog.DebugWrite("Queueing build of NetworkOrbs...", MessageType.Info);
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSBNetworkServer.active, BuildOrbs);
|
||||
}
|
||||
}
|
||||
public void QueueBuildOrbs()
|
||||
{
|
||||
DebugLog.DebugWrite("Queueing build of NetworkOrbs...", MessageType.Info);
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSBNetworkServer.active, BuildOrbs);
|
||||
}
|
||||
}
|
||||
}
|
@ -4,60 +4,60 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.OrbSync
|
||||
{
|
||||
public class OrbPatches : QSBPatch
|
||||
{
|
||||
public override QSBPatchTypes Type => QSBPatchTypes.OnClientConnect;
|
||||
public class OrbPatches : QSBPatch
|
||||
{
|
||||
public override QSBPatchTypes Type => QSBPatchTypes.OnClientConnect;
|
||||
|
||||
public static void StartDragCallEvent(bool __result, NomaiInterfaceOrb __instance)
|
||||
{
|
||||
if (__result)
|
||||
{
|
||||
GlobalMessenger<int>.FireEvent(EventNames.QSBOrbUser, WorldRegistry.OldOrbList.FindIndex(x => x == __instance));
|
||||
}
|
||||
}
|
||||
public static void StartDragCallEvent(bool __result, NomaiInterfaceOrb __instance)
|
||||
{
|
||||
if (__result)
|
||||
{
|
||||
GlobalMessenger<int>.FireEvent(EventNames.QSBOrbUser, WorldRegistry.OldOrbList.FindIndex(x => x == __instance));
|
||||
}
|
||||
}
|
||||
|
||||
public static bool CheckOrbCollision(ref bool __result, NomaiInterfaceSlot __instance, NomaiInterfaceOrb orb,
|
||||
bool ____ignoreDraggedOrbs, float ____radius, float ____exitRadius, ref NomaiInterfaceOrb ____occupyingOrb)
|
||||
{
|
||||
if (____ignoreDraggedOrbs && orb.IsBeingDragged())
|
||||
{
|
||||
__result = false;
|
||||
return false;
|
||||
}
|
||||
var orbDistance = Vector3.Distance(orb.transform.position, __instance.transform.position);
|
||||
var triggerRadius = orb.IsBeingDragged() ? ____exitRadius : ____radius;
|
||||
if (____occupyingOrb == null && orbDistance < ____radius)
|
||||
{
|
||||
____occupyingOrb = orb;
|
||||
if (Time.timeSinceLevelLoad > 1f)
|
||||
{
|
||||
WorldRegistry.HandleSlotStateChange(__instance, orb, true);
|
||||
WorldRegistry.RaiseEvent(__instance, "OnSlotActivated");
|
||||
}
|
||||
__result = true;
|
||||
return false;
|
||||
}
|
||||
if (____occupyingOrb == null || ____occupyingOrb != orb)
|
||||
{
|
||||
__result = false;
|
||||
return false;
|
||||
}
|
||||
if (orbDistance > triggerRadius)
|
||||
{
|
||||
WorldRegistry.HandleSlotStateChange(__instance, orb, false);
|
||||
____occupyingOrb = null;
|
||||
WorldRegistry.RaiseEvent(__instance, "OnSlotDeactivated");
|
||||
__result = false;
|
||||
return false;
|
||||
}
|
||||
__result = true;
|
||||
return false;
|
||||
}
|
||||
public static bool CheckOrbCollision(ref bool __result, NomaiInterfaceSlot __instance, NomaiInterfaceOrb orb,
|
||||
bool ____ignoreDraggedOrbs, float ____radius, float ____exitRadius, ref NomaiInterfaceOrb ____occupyingOrb)
|
||||
{
|
||||
if (____ignoreDraggedOrbs && orb.IsBeingDragged())
|
||||
{
|
||||
__result = false;
|
||||
return false;
|
||||
}
|
||||
var orbDistance = Vector3.Distance(orb.transform.position, __instance.transform.position);
|
||||
var triggerRadius = orb.IsBeingDragged() ? ____exitRadius : ____radius;
|
||||
if (____occupyingOrb == null && orbDistance < ____radius)
|
||||
{
|
||||
____occupyingOrb = orb;
|
||||
if (Time.timeSinceLevelLoad > 1f)
|
||||
{
|
||||
WorldRegistry.HandleSlotStateChange(__instance, orb, true);
|
||||
WorldRegistry.RaiseEvent(__instance, "OnSlotActivated");
|
||||
}
|
||||
__result = true;
|
||||
return false;
|
||||
}
|
||||
if (____occupyingOrb == null || ____occupyingOrb != orb)
|
||||
{
|
||||
__result = false;
|
||||
return false;
|
||||
}
|
||||
if (orbDistance > triggerRadius)
|
||||
{
|
||||
WorldRegistry.HandleSlotStateChange(__instance, orb, false);
|
||||
____occupyingOrb = null;
|
||||
WorldRegistry.RaiseEvent(__instance, "OnSlotDeactivated");
|
||||
__result = false;
|
||||
return false;
|
||||
}
|
||||
__result = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
public override void DoPatches()
|
||||
{
|
||||
QSB.Helper.HarmonyHelper.AddPostfix<NomaiInterfaceOrb>("StartDragFromPosition", typeof(OrbPatches), nameof(StartDragCallEvent));
|
||||
QSB.Helper.HarmonyHelper.AddPrefix<NomaiInterfaceSlot>("CheckOrbCollision", typeof(OrbPatches), nameof(CheckOrbCollision));
|
||||
}
|
||||
}
|
||||
public override void DoPatches()
|
||||
{
|
||||
QSB.Helper.HarmonyHelper.AddPostfix<NomaiInterfaceOrb>("StartDragFromPosition", typeof(OrbPatches), nameof(StartDragCallEvent));
|
||||
QSB.Helper.HarmonyHelper.AddPrefix<NomaiInterfaceSlot>("CheckOrbCollision", typeof(OrbPatches), nameof(CheckOrbCollision));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -12,38 +12,38 @@ using System.Linq;
|
||||
|
||||
namespace QSB.Patches
|
||||
{
|
||||
public delegate void PatchEvent(QSBPatchTypes type);
|
||||
public delegate void PatchEvent(QSBPatchTypes type);
|
||||
|
||||
public static class QSBPatchManager
|
||||
{
|
||||
public static List<QSBPatch> _patchList = new List<QSBPatch>();
|
||||
public static class QSBPatchManager
|
||||
{
|
||||
public static List<QSBPatch> _patchList = new List<QSBPatch>();
|
||||
|
||||
public static event PatchEvent OnPatchType;
|
||||
public static event PatchEvent OnPatchType;
|
||||
|
||||
public static void Init()
|
||||
{
|
||||
_patchList = new List<QSBPatch>
|
||||
{
|
||||
new ConversationPatches(),
|
||||
new DeathPatches(),
|
||||
new ElevatorPatches(),
|
||||
new OrbPatches(),
|
||||
new WakeUpPatches(),
|
||||
new ProbePatches()
|
||||
};
|
||||
public static void Init()
|
||||
{
|
||||
_patchList = new List<QSBPatch>
|
||||
{
|
||||
new ConversationPatches(),
|
||||
new DeathPatches(),
|
||||
new ElevatorPatches(),
|
||||
new OrbPatches(),
|
||||
new WakeUpPatches(),
|
||||
new ProbePatches()
|
||||
};
|
||||
|
||||
DebugLog.DebugWrite("Patch Manager ready.", MessageType.Success);
|
||||
}
|
||||
DebugLog.DebugWrite("Patch Manager ready.", MessageType.Success);
|
||||
}
|
||||
|
||||
public static void DoPatchType(QSBPatchTypes type)
|
||||
{
|
||||
OnPatchType?.Invoke(type);
|
||||
DebugLog.DebugWrite($"Patch block {Enum.GetName(typeof(QSBPatchTypes), type)}", MessageType.Info);
|
||||
foreach (var patch in _patchList.Where(x => x.Type == type))
|
||||
{
|
||||
DebugLog.DebugWrite($" - Patching in {patch.GetType().Name}", MessageType.Info);
|
||||
patch.DoPatches();
|
||||
}
|
||||
}
|
||||
}
|
||||
public static void DoPatchType(QSBPatchTypes type)
|
||||
{
|
||||
OnPatchType?.Invoke(type);
|
||||
DebugLog.DebugWrite($"Patch block {Enum.GetName(typeof(QSBPatchTypes), type)}", MessageType.Info);
|
||||
foreach (var patch in _patchList.Where(x => x.Type == type))
|
||||
{
|
||||
DebugLog.DebugWrite($" - Patching in {patch.GetType().Name}", MessageType.Info);
|
||||
patch.DoPatches();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2,11 +2,11 @@
|
||||
|
||||
namespace QSB.Player
|
||||
{
|
||||
public abstract class PlayerSyncObject : QSBNetworkBehaviour
|
||||
{
|
||||
public uint AttachedNetId => GetComponent<QSBNetworkIdentity>()?.NetId.Value ?? uint.MaxValue;
|
||||
public uint PlayerId => this.GetPlayerOfObject();
|
||||
public uint PreviousPlayerId { get; set; }
|
||||
public PlayerInfo Player => QSBPlayerManager.GetPlayer(PlayerId);
|
||||
}
|
||||
public abstract class PlayerSyncObject : QSBNetworkBehaviour
|
||||
{
|
||||
public uint AttachedNetId => GetComponent<QSBNetworkIdentity>()?.NetId.Value ?? uint.MaxValue;
|
||||
public uint PlayerId => this.GetPlayerOfObject();
|
||||
public uint PreviousPlayerId { get; set; }
|
||||
public PlayerInfo Player => QSBPlayerManager.GetPlayer(PlayerId);
|
||||
}
|
||||
}
|
||||
|
@ -8,142 +8,142 @@ using System.Linq;
|
||||
|
||||
namespace QSB.Player
|
||||
{
|
||||
public static class QSBPlayerManager
|
||||
{
|
||||
public static uint LocalPlayerId => PlayerTransformSync.LocalInstance.GetComponent<QSBNetworkIdentity>()?.NetId.Value ?? uint.MaxValue;
|
||||
public static PlayerInfo LocalPlayer => GetPlayer(LocalPlayerId);
|
||||
public static List<PlayerInfo> PlayerList { get; } = new List<PlayerInfo>();
|
||||
public static class QSBPlayerManager
|
||||
{
|
||||
public static uint LocalPlayerId => PlayerTransformSync.LocalInstance.GetComponent<QSBNetworkIdentity>()?.NetId.Value ?? uint.MaxValue;
|
||||
public static PlayerInfo LocalPlayer => GetPlayer(LocalPlayerId);
|
||||
public static List<PlayerInfo> PlayerList { get; } = new List<PlayerInfo>();
|
||||
|
||||
public static List<PlayerSyncObject> PlayerSyncObjects { get; } = new List<PlayerSyncObject>();
|
||||
public static List<PlayerSyncObject> PlayerSyncObjects { get; } = new List<PlayerSyncObject>();
|
||||
|
||||
public static PlayerInfo GetPlayer(uint id)
|
||||
{
|
||||
if (id == uint.MaxValue || id == 0U)
|
||||
{
|
||||
return default;
|
||||
}
|
||||
var player = PlayerList.FirstOrDefault(x => x.PlayerId == id);
|
||||
if (player != null)
|
||||
{
|
||||
return player;
|
||||
}
|
||||
DebugLog.DebugWrite($"Creating player id {id}", MessageType.Info);
|
||||
player = new PlayerInfo(id);
|
||||
PlayerList.Add(player);
|
||||
return player;
|
||||
}
|
||||
public static PlayerInfo GetPlayer(uint id)
|
||||
{
|
||||
if (id == uint.MaxValue || id == 0U)
|
||||
{
|
||||
return default;
|
||||
}
|
||||
var player = PlayerList.FirstOrDefault(x => x.PlayerId == id);
|
||||
if (player != null)
|
||||
{
|
||||
return player;
|
||||
}
|
||||
DebugLog.DebugWrite($"Creating player id {id}", MessageType.Info);
|
||||
player = new PlayerInfo(id);
|
||||
PlayerList.Add(player);
|
||||
return player;
|
||||
}
|
||||
|
||||
public static void RemovePlayer(uint id)
|
||||
{
|
||||
DebugLog.DebugWrite($"Removing player {GetPlayer(id).Name} id {id}", MessageType.Info);
|
||||
PlayerList.Remove(GetPlayer(id));
|
||||
}
|
||||
public static void RemovePlayer(uint id)
|
||||
{
|
||||
DebugLog.DebugWrite($"Removing player {GetPlayer(id).Name} id {id}", MessageType.Info);
|
||||
PlayerList.Remove(GetPlayer(id));
|
||||
}
|
||||
|
||||
public static void RemoveAllPlayers()
|
||||
{
|
||||
DebugLog.DebugWrite($"Removing all players.", MessageType.Info);
|
||||
PlayerList.Clear();
|
||||
}
|
||||
public static void RemoveAllPlayers()
|
||||
{
|
||||
DebugLog.DebugWrite($"Removing all players.", MessageType.Info);
|
||||
PlayerList.Clear();
|
||||
}
|
||||
|
||||
public static bool PlayerExists(uint id)
|
||||
{
|
||||
return id != uint.MaxValue && PlayerList.Any(x => x.PlayerId == id);
|
||||
}
|
||||
public static bool PlayerExists(uint id)
|
||||
{
|
||||
return id != uint.MaxValue && PlayerList.Any(x => x.PlayerId == id);
|
||||
}
|
||||
|
||||
public static void HandleFullStateMessage(PlayerStateMessage message)
|
||||
{
|
||||
var player = GetPlayer(message.AboutId);
|
||||
player.Name = message.PlayerName;
|
||||
player.IsReady = message.PlayerReady;
|
||||
player.State = message.PlayerState;
|
||||
if (LocalPlayer.IsReady)
|
||||
{
|
||||
player.UpdateStateObjects();
|
||||
}
|
||||
}
|
||||
public static void HandleFullStateMessage(PlayerStateMessage message)
|
||||
{
|
||||
var player = GetPlayer(message.AboutId);
|
||||
player.Name = message.PlayerName;
|
||||
player.IsReady = message.PlayerReady;
|
||||
player.State = message.PlayerState;
|
||||
if (LocalPlayer.IsReady)
|
||||
{
|
||||
player.UpdateStateObjects();
|
||||
}
|
||||
}
|
||||
|
||||
public static IEnumerable<T> GetSyncObjects<T>() where T : PlayerSyncObject
|
||||
{
|
||||
return PlayerSyncObjects.OfType<T>().Where(x => x != null);
|
||||
}
|
||||
public static IEnumerable<T> GetSyncObjects<T>() where T : PlayerSyncObject
|
||||
{
|
||||
return PlayerSyncObjects.OfType<T>().Where(x => x != null);
|
||||
}
|
||||
|
||||
public static T GetSyncObject<T>(uint id) where T : PlayerSyncObject
|
||||
{
|
||||
return GetSyncObjects<T>().FirstOrDefault(x => x != null && x.AttachedNetId == id);
|
||||
}
|
||||
public static T GetSyncObject<T>(uint id) where T : PlayerSyncObject
|
||||
{
|
||||
return GetSyncObjects<T>().FirstOrDefault(x => x != null && x.AttachedNetId == id);
|
||||
}
|
||||
|
||||
public static bool IsBelongingToLocalPlayer(uint id)
|
||||
{
|
||||
return id == LocalPlayerId ||
|
||||
PlayerSyncObjects.Any(x => x != null && x.AttachedNetId == id && x.IsLocalPlayer);
|
||||
}
|
||||
public static bool IsBelongingToLocalPlayer(uint id)
|
||||
{
|
||||
return id == LocalPlayerId ||
|
||||
PlayerSyncObjects.Any(x => x != null && x.AttachedNetId == id && x.IsLocalPlayer);
|
||||
}
|
||||
|
||||
public static uint GetPlayerOfObject(this PlayerSyncObject syncObject)
|
||||
{
|
||||
if (PlayerList.Count == 0)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - No players exist to find owner of object. (Attached NetID : {syncObject.AttachedNetId})", MessageType.Error);
|
||||
syncObject.PreviousPlayerId = uint.MaxValue;
|
||||
return uint.MaxValue;
|
||||
}
|
||||
// Get all Player IDs
|
||||
var playerIds = PlayerList.Select(x => x.PlayerId).ToList();
|
||||
// Get highest ID below the given syncobject's netid. A netid cannot belong to a playerid above it, only below or equal to it.
|
||||
var lowerBound = playerIds.Where(x => x <= syncObject.AttachedNetId).ToList().Max();
|
||||
if (playerIds.Min() > syncObject.AttachedNetId)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - Minimum playerid is greater than syncobject's netid. (Attached NetID : {syncObject.AttachedNetId})", MessageType.Warning);
|
||||
syncObject.PreviousPlayerId = uint.MaxValue;
|
||||
return uint.MaxValue;
|
||||
}
|
||||
// If the player list count is not the same as the count of the same type syncobject (eg. 3 players and 4 PlayerTransformSyncs)
|
||||
// and the highest ID below the syncobject's id is the same as the highest player id.
|
||||
if (PlayerList.Count != PlayerSyncObjects.Count(x => x.GetType() == syncObject.GetType()) && lowerBound == playerIds.Max())
|
||||
{
|
||||
// If the previous player id was not the error value, return it. To smooth over discrepancies between player list and object list.
|
||||
if (syncObject.PreviousPlayerId != uint.MaxValue)
|
||||
{
|
||||
return syncObject.PreviousPlayerId;
|
||||
}
|
||||
// If the syncobject is a PlayerTransformSync, make a player.
|
||||
if (syncObject.GetType() == typeof(PlayerTransformSync) && syncObject.AttachedNetId != 0U)
|
||||
{
|
||||
return GetPlayer(syncObject.AttachedNetId).PlayerId;
|
||||
}
|
||||
DebugLog.ToConsole($"Warning - Unequal player:syncobject count. ({PlayerList.Count}:{PlayerSyncObjects.Count(x => x.GetType() == syncObject.GetType())}) (Attached NetID : {syncObject.AttachedNetId})", MessageType.Warning);
|
||||
syncObject.PreviousPlayerId = uint.MaxValue;
|
||||
return uint.MaxValue;
|
||||
}
|
||||
if (syncObject.PreviousPlayerId == uint.MaxValue)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - Syncobject previously had uint.MaxValue as it's playerid. (Attached NetID : {syncObject.AttachedNetId})", MessageType.Warning);
|
||||
}
|
||||
syncObject.PreviousPlayerId = lowerBound;
|
||||
return lowerBound;
|
||||
}
|
||||
public static uint GetPlayerOfObject(this PlayerSyncObject syncObject)
|
||||
{
|
||||
if (PlayerList.Count == 0)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - No players exist to find owner of object. (Attached NetID : {syncObject.AttachedNetId})", MessageType.Error);
|
||||
syncObject.PreviousPlayerId = uint.MaxValue;
|
||||
return uint.MaxValue;
|
||||
}
|
||||
// Get all Player IDs
|
||||
var playerIds = PlayerList.Select(x => x.PlayerId).ToList();
|
||||
// Get highest ID below the given syncobject's netid. A netid cannot belong to a playerid above it, only below or equal to it.
|
||||
var lowerBound = playerIds.Where(x => x <= syncObject.AttachedNetId).ToList().Max();
|
||||
if (playerIds.Min() > syncObject.AttachedNetId)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - Minimum playerid is greater than syncobject's netid. (Attached NetID : {syncObject.AttachedNetId})", MessageType.Warning);
|
||||
syncObject.PreviousPlayerId = uint.MaxValue;
|
||||
return uint.MaxValue;
|
||||
}
|
||||
// If the player list count is not the same as the count of the same type syncobject (eg. 3 players and 4 PlayerTransformSyncs)
|
||||
// and the highest ID below the syncobject's id is the same as the highest player id.
|
||||
if (PlayerList.Count != PlayerSyncObjects.Count(x => x.GetType() == syncObject.GetType()) && lowerBound == playerIds.Max())
|
||||
{
|
||||
// If the previous player id was not the error value, return it. To smooth over discrepancies between player list and object list.
|
||||
if (syncObject.PreviousPlayerId != uint.MaxValue)
|
||||
{
|
||||
return syncObject.PreviousPlayerId;
|
||||
}
|
||||
// If the syncobject is a PlayerTransformSync, make a player.
|
||||
if (syncObject.GetType() == typeof(PlayerTransformSync) && syncObject.AttachedNetId != 0U)
|
||||
{
|
||||
return GetPlayer(syncObject.AttachedNetId).PlayerId;
|
||||
}
|
||||
DebugLog.ToConsole($"Warning - Unequal player:syncobject count. ({PlayerList.Count}:{PlayerSyncObjects.Count(x => x.GetType() == syncObject.GetType())}) (Attached NetID : {syncObject.AttachedNetId})", MessageType.Warning);
|
||||
syncObject.PreviousPlayerId = uint.MaxValue;
|
||||
return uint.MaxValue;
|
||||
}
|
||||
if (syncObject.PreviousPlayerId == uint.MaxValue)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - Syncobject previously had uint.MaxValue as it's playerid. (Attached NetID : {syncObject.AttachedNetId})", MessageType.Warning);
|
||||
}
|
||||
syncObject.PreviousPlayerId = lowerBound;
|
||||
return lowerBound;
|
||||
}
|
||||
|
||||
public static List<uint> GetPlayerNetIds(PlayerInfo player)
|
||||
{
|
||||
if (PlayerSyncObjects.Count == 0)
|
||||
{
|
||||
return default;
|
||||
}
|
||||
int count = 0;
|
||||
int totalCount = PlayerSyncObjects.Count;
|
||||
PlayerSyncObjects.RemoveAll(x => x == null);
|
||||
PlayerSyncObjects.RemoveAll(x => x.GetComponent<QSBNetworkIdentity>() == null);
|
||||
if (PlayerSyncObjects.Count != totalCount)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - Removed {totalCount - PlayerSyncObjects.Count} items from PlayerSyncObjects.", MessageType.Warning);
|
||||
}
|
||||
foreach (var item in PlayerSyncObjects.DistinctBy(x => x.AttachedNetId))
|
||||
{
|
||||
if (item.PlayerId == player.PlayerId)
|
||||
{
|
||||
count++;
|
||||
}
|
||||
}
|
||||
return Enumerable.Range((int)player.PlayerId, count).Select(x => (uint)x).ToList();
|
||||
}
|
||||
}
|
||||
public static List<uint> GetPlayerNetIds(PlayerInfo player)
|
||||
{
|
||||
if (PlayerSyncObjects.Count == 0)
|
||||
{
|
||||
return default;
|
||||
}
|
||||
int count = 0;
|
||||
int totalCount = PlayerSyncObjects.Count;
|
||||
PlayerSyncObjects.RemoveAll(x => x == null);
|
||||
PlayerSyncObjects.RemoveAll(x => x.GetComponent<QSBNetworkIdentity>() == null);
|
||||
if (PlayerSyncObjects.Count != totalCount)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - Removed {totalCount - PlayerSyncObjects.Count} items from PlayerSyncObjects.", MessageType.Warning);
|
||||
}
|
||||
foreach (var item in PlayerSyncObjects.DistinctBy(x => x.AttachedNetId))
|
||||
{
|
||||
if (item.PlayerId == player.PlayerId)
|
||||
{
|
||||
count++;
|
||||
}
|
||||
}
|
||||
return Enumerable.Range((int)player.PlayerId, count).Select(x => (uint)x).ToList();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
148
QSB/QSB.cs
148
QSB/QSB.cs
@ -15,92 +15,92 @@ using UnityEngine.Networking;
|
||||
|
||||
namespace QSB
|
||||
{
|
||||
public class QSB : ModBehaviour
|
||||
{
|
||||
public static IModBehaviour ModBehaviour { get; private set; }
|
||||
public static IModHelper Helper { get; private set; }
|
||||
public static string DefaultServerIP { get; private set; }
|
||||
public static int Port { get; private set; }
|
||||
public static bool DebugMode { get; private set; }
|
||||
public static AssetBundle NetworkAssetBundle { get; private set; }
|
||||
public static AssetBundle InstrumentAssetBundle { get; private set; }
|
||||
public static bool HasWokenUp { get; set; }
|
||||
public class QSB : ModBehaviour
|
||||
{
|
||||
public static IModBehaviour ModBehaviour { get; private set; }
|
||||
public static IModHelper Helper { get; private set; }
|
||||
public static string DefaultServerIP { get; private set; }
|
||||
public static int Port { get; private set; }
|
||||
public static bool DebugMode { get; private set; }
|
||||
public static AssetBundle NetworkAssetBundle { get; private set; }
|
||||
public static AssetBundle InstrumentAssetBundle { get; private set; }
|
||||
public static bool HasWokenUp { get; set; }
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
Application.runInBackground = true;
|
||||
private void Awake()
|
||||
{
|
||||
Application.runInBackground = true;
|
||||
|
||||
var instance = TextTranslation.Get().GetValue<TextTranslation.TranslationTable>("m_table");
|
||||
instance.theUITable[(int)UITextType.PleaseUseController] =
|
||||
"<color=orange>Quantum Space Buddies</color> is best experienced with friends...";
|
||||
var instance = TextTranslation.Get().GetValue<TextTranslation.TranslationTable>("m_table");
|
||||
instance.theUITable[(int)UITextType.PleaseUseController] =
|
||||
"<color=orange>Quantum Space Buddies</color> is best experienced with friends...";
|
||||
|
||||
ModBehaviour = this;
|
||||
ModBehaviour = this;
|
||||
|
||||
LogFilter.currentLogLevel = LogFilter.Debug;
|
||||
LogFilter.currentLogLevel = LogFilter.Debug;
|
||||
|
||||
// Application.logMessageReceived += Application_logMessageReceived;
|
||||
}
|
||||
// Application.logMessageReceived += Application_logMessageReceived;
|
||||
}
|
||||
|
||||
private void Application_logMessageReceived(string condition, string stackTrace, LogType type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case LogType.Assert:
|
||||
DebugLog.DebugWrite($"Assert - {condition}", MessageType.Message);
|
||||
break;
|
||||
case LogType.Log:
|
||||
DebugLog.DebugWrite($"Log - {condition}", MessageType.Message);
|
||||
break;
|
||||
case LogType.Warning:
|
||||
DebugLog.DebugWrite($"Warning - {condition}", MessageType.Warning);
|
||||
break;
|
||||
}
|
||||
}
|
||||
private void Application_logMessageReceived(string condition, string stackTrace, LogType type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case LogType.Assert:
|
||||
DebugLog.DebugWrite($"Assert - {condition}", MessageType.Message);
|
||||
break;
|
||||
case LogType.Log:
|
||||
DebugLog.DebugWrite($"Log - {condition}", MessageType.Message);
|
||||
break;
|
||||
case LogType.Warning:
|
||||
DebugLog.DebugWrite($"Warning - {condition}", MessageType.Warning);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private void Start()
|
||||
{
|
||||
Helper = ModHelper;
|
||||
DebugLog.ToConsole($"* Start of QSB version {Helper.Manifest.Version} - authored by {Helper.Manifest.Author}", MessageType.Info);
|
||||
private void Start()
|
||||
{
|
||||
Helper = ModHelper;
|
||||
DebugLog.ToConsole($"* Start of QSB version {Helper.Manifest.Version} - authored by {Helper.Manifest.Author}", MessageType.Info);
|
||||
|
||||
NetworkAssetBundle = Helper.Assets.LoadBundle("assets/network");
|
||||
InstrumentAssetBundle = Helper.Assets.LoadBundle("assets/instruments");
|
||||
NetworkAssetBundle = Helper.Assets.LoadBundle("assets/network");
|
||||
InstrumentAssetBundle = Helper.Assets.LoadBundle("assets/instruments");
|
||||
|
||||
QSBPatchManager.Init();
|
||||
QSBPatchManager.Init();
|
||||
|
||||
QSBPatchManager.DoPatchType(QSBPatchTypes.OnModStart);
|
||||
QSBPatchManager.DoPatchType(QSBPatchTypes.OnModStart);
|
||||
|
||||
// Turns out these are very finicky about what order they go. QSBNetworkManager seems to
|
||||
// want to go first-ish, otherwise the NetworkManager complains about the PlayerPrefab being
|
||||
// null (even though it isn't...)
|
||||
gameObject.AddComponent<QSBNetworkManager>();
|
||||
gameObject.AddComponent<QSBNetworkManagerHUD>();
|
||||
gameObject.AddComponent<DebugActions>();
|
||||
gameObject.AddComponent<ElevatorManager>();
|
||||
gameObject.AddComponent<GeyserManager>();
|
||||
gameObject.AddComponent<OrbManager>();
|
||||
gameObject.AddComponent<QSBSectorManager>();
|
||||
gameObject.AddComponent<ConversationManager>();
|
||||
gameObject.AddComponent<QSBInputManager>();
|
||||
gameObject.AddComponent<TimeSyncUI>();
|
||||
// Turns out these are very finicky about what order they go. QSBNetworkManager seems to
|
||||
// want to go first-ish, otherwise the NetworkManager complains about the PlayerPrefab being
|
||||
// null (even though it isn't...)
|
||||
gameObject.AddComponent<QSBNetworkManager>();
|
||||
gameObject.AddComponent<QSBNetworkManagerHUD>();
|
||||
gameObject.AddComponent<DebugActions>();
|
||||
gameObject.AddComponent<ElevatorManager>();
|
||||
gameObject.AddComponent<GeyserManager>();
|
||||
gameObject.AddComponent<OrbManager>();
|
||||
gameObject.AddComponent<QSBSectorManager>();
|
||||
gameObject.AddComponent<ConversationManager>();
|
||||
gameObject.AddComponent<QSBInputManager>();
|
||||
gameObject.AddComponent<TimeSyncUI>();
|
||||
|
||||
// Stop players being able to pause
|
||||
Helper.HarmonyHelper.EmptyMethod(typeof(OWTime).GetMethod("Pause"));
|
||||
}
|
||||
// Stop players being able to pause
|
||||
Helper.HarmonyHelper.EmptyMethod(typeof(OWTime).GetMethod("Pause"));
|
||||
}
|
||||
|
||||
void Update()
|
||||
{
|
||||
QSBNetworkIdentity.UNetStaticUpdate();
|
||||
}
|
||||
void Update()
|
||||
{
|
||||
QSBNetworkIdentity.UNetStaticUpdate();
|
||||
}
|
||||
|
||||
public override void Configure(IModConfig config)
|
||||
{
|
||||
DefaultServerIP = config.GetSettingsValue<string>("defaultServerIP");
|
||||
Port = config.GetSettingsValue<int>("port");
|
||||
if (QSBNetworkManager.Instance != null)
|
||||
{
|
||||
QSBNetworkManager.Instance.networkPort = Port;
|
||||
}
|
||||
DebugMode = config.GetSettingsValue<bool>("debugMode");
|
||||
}
|
||||
}
|
||||
public override void Configure(IModConfig config)
|
||||
{
|
||||
DefaultServerIP = config.GetSettingsValue<string>("defaultServerIP");
|
||||
Port = config.GetSettingsValue<int>("port");
|
||||
if (QSBNetworkManager.Instance != null)
|
||||
{
|
||||
QSBNetworkManager.Instance.networkPort = Port;
|
||||
}
|
||||
DebugMode = config.GetSettingsValue<bool>("debugMode");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2,53 +2,53 @@
|
||||
|
||||
namespace QSB
|
||||
{
|
||||
public delegate void InputEvent();
|
||||
public delegate void InputEvent();
|
||||
|
||||
public class QSBInputManager : MonoBehaviour
|
||||
{
|
||||
public static QSBInputManager Instance;
|
||||
public class QSBInputManager : MonoBehaviour
|
||||
{
|
||||
public static QSBInputManager Instance;
|
||||
|
||||
public static event InputEvent ChertTaunt;
|
||||
public static event InputEvent EskerTaunt;
|
||||
public static event InputEvent RiebeckTaunt;
|
||||
public static event InputEvent GabbroTaunt;
|
||||
public static event InputEvent FeldsparTaunt;
|
||||
public static event InputEvent ExitTaunt;
|
||||
public static event InputEvent ChertTaunt;
|
||||
public static event InputEvent EskerTaunt;
|
||||
public static event InputEvent RiebeckTaunt;
|
||||
public static event InputEvent GabbroTaunt;
|
||||
public static event InputEvent FeldsparTaunt;
|
||||
public static event InputEvent ExitTaunt;
|
||||
|
||||
public void Awake() => Instance = this;
|
||||
public void Awake() => Instance = this;
|
||||
|
||||
public void Update()
|
||||
{
|
||||
if (Input.GetKey(KeyCode.T))
|
||||
{
|
||||
// Listed order is from sun to dark bramble
|
||||
if (Input.GetKeyDown(KeyCode.Alpha1))
|
||||
{
|
||||
ChertTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha2))
|
||||
{
|
||||
EskerTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha5))
|
||||
{
|
||||
RiebeckTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha4))
|
||||
{
|
||||
GabbroTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha3))
|
||||
{
|
||||
FeldsparTaunt?.Invoke();
|
||||
}
|
||||
}
|
||||
public void Update()
|
||||
{
|
||||
if (Input.GetKey(KeyCode.T))
|
||||
{
|
||||
// Listed order is from sun to dark bramble
|
||||
if (Input.GetKeyDown(KeyCode.Alpha1))
|
||||
{
|
||||
ChertTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha2))
|
||||
{
|
||||
EskerTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha5))
|
||||
{
|
||||
RiebeckTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha4))
|
||||
{
|
||||
GabbroTaunt?.Invoke();
|
||||
}
|
||||
else if (Input.GetKeyDown(KeyCode.Alpha3))
|
||||
{
|
||||
FeldsparTaunt?.Invoke();
|
||||
}
|
||||
}
|
||||
|
||||
if (OWInput.GetValue(InputLibrary.moveXZ, InputMode.None) != Vector2.zero
|
||||
|| OWInput.GetValue(InputLibrary.jump, InputMode.None) != 0f)
|
||||
{
|
||||
ExitTaunt?.Invoke();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (OWInput.GetValue(InputLibrary.moveXZ, InputMode.None) != Vector2.zero
|
||||
|| OWInput.GetValue(InputLibrary.jump, InputMode.None) != 0f)
|
||||
{
|
||||
ExitTaunt?.Invoke();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -6,65 +6,65 @@ using UnityEngine.Networking;
|
||||
|
||||
namespace QSB
|
||||
{
|
||||
public class QSBNetworkLobby : NetworkBehaviour
|
||||
{
|
||||
public bool CanEditName { get; set; }
|
||||
public string PlayerName { get; private set; }
|
||||
public class QSBNetworkLobby : NetworkBehaviour
|
||||
{
|
||||
public bool CanEditName { get; set; }
|
||||
public string PlayerName { get; private set; }
|
||||
|
||||
private readonly string[] _defaultNames = {
|
||||
"Arkose",
|
||||
"Chert",
|
||||
"Esker",
|
||||
"Hal",
|
||||
"Hornfels",
|
||||
"Feldspar",
|
||||
"Gabbro",
|
||||
"Galena",
|
||||
"Gneiss",
|
||||
"Gossan",
|
||||
"Marl",
|
||||
"Mica",
|
||||
"Moraine",
|
||||
"Porphy",
|
||||
"Riebeck",
|
||||
"Rutile",
|
||||
"Slate",
|
||||
"Spinel",
|
||||
"Tektite",
|
||||
"Tephra",
|
||||
"Tuff",
|
||||
"Jinha"
|
||||
};
|
||||
private readonly string[] _defaultNames = {
|
||||
"Arkose",
|
||||
"Chert",
|
||||
"Esker",
|
||||
"Hal",
|
||||
"Hornfels",
|
||||
"Feldspar",
|
||||
"Gabbro",
|
||||
"Galena",
|
||||
"Gneiss",
|
||||
"Gossan",
|
||||
"Marl",
|
||||
"Mica",
|
||||
"Moraine",
|
||||
"Porphy",
|
||||
"Riebeck",
|
||||
"Rutile",
|
||||
"Slate",
|
||||
"Spinel",
|
||||
"Tektite",
|
||||
"Tephra",
|
||||
"Tuff",
|
||||
"Jinha"
|
||||
};
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
PlayerName = GetPlayerName();
|
||||
CanEditName = true;
|
||||
QSB.Helper.HarmonyHelper.EmptyMethod<NetworkManagerHUD>("Update");
|
||||
}
|
||||
private void Awake()
|
||||
{
|
||||
PlayerName = GetPlayerName();
|
||||
CanEditName = true;
|
||||
QSB.Helper.HarmonyHelper.EmptyMethod<NetworkManagerHUD>("Update");
|
||||
}
|
||||
|
||||
private string GetPlayerName()
|
||||
{
|
||||
var profileManager = StandaloneProfileManager.SharedInstance;
|
||||
profileManager.Initialize();
|
||||
var profile = profileManager.GetValue<StandaloneProfileManager.ProfileData>("_currentProfile");
|
||||
var profileName = profile?.profileName;
|
||||
return !string.IsNullOrEmpty(profileName)
|
||||
? profileName
|
||||
: _defaultNames.OrderBy(x => Guid.NewGuid()).First();
|
||||
}
|
||||
private string GetPlayerName()
|
||||
{
|
||||
var profileManager = StandaloneProfileManager.SharedInstance;
|
||||
profileManager.Initialize();
|
||||
var profile = profileManager.GetValue<StandaloneProfileManager.ProfileData>("_currentProfile");
|
||||
var profileName = profile?.profileName;
|
||||
return !string.IsNullOrEmpty(profileName)
|
||||
? profileName
|
||||
: _defaultNames.OrderBy(x => Guid.NewGuid()).First();
|
||||
}
|
||||
|
||||
private void OnGUI()
|
||||
{
|
||||
GUI.Label(new Rect(10, 10, 200f, 20f), "Name:");
|
||||
if (CanEditName)
|
||||
{
|
||||
PlayerName = GUI.TextField(new Rect(60, 10, 145, 20f), PlayerName);
|
||||
}
|
||||
else
|
||||
{
|
||||
GUI.Label(new Rect(60, 10, 145, 20f), PlayerName);
|
||||
}
|
||||
}
|
||||
}
|
||||
private void OnGUI()
|
||||
{
|
||||
GUI.Label(new Rect(10, 10, 200f, 20f), "Name:");
|
||||
if (CanEditName)
|
||||
{
|
||||
PlayerName = GUI.TextField(new Rect(60, 10, 145, 20f), PlayerName);
|
||||
}
|
||||
else
|
||||
{
|
||||
GUI.Label(new Rect(60, 10, 145, 20f), PlayerName);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -22,291 +22,291 @@ using UnityEngine.Networking;
|
||||
|
||||
namespace QSB
|
||||
{
|
||||
public class QSBNetworkManager : QSBNetworkManagerUNET
|
||||
{
|
||||
private const int MaxConnections = 128;
|
||||
private const int MaxBufferedPackets = 64;
|
||||
public class QSBNetworkManager : QSBNetworkManagerUNET
|
||||
{
|
||||
private const int MaxConnections = 128;
|
||||
private const int MaxBufferedPackets = 64;
|
||||
|
||||
public static QSBNetworkManager Instance { get; private set; }
|
||||
public static QSBNetworkManager Instance { get; private set; }
|
||||
|
||||
public event Action OnNetworkManagerReady;
|
||||
public bool IsReady { get; private set; }
|
||||
public event Action OnNetworkManagerReady;
|
||||
public bool IsReady { get; private set; }
|
||||
|
||||
private QSBNetworkLobby _lobby;
|
||||
private AssetBundle _assetBundle;
|
||||
private GameObject _shipPrefab;
|
||||
private GameObject _cameraPrefab;
|
||||
private GameObject _probePrefab;
|
||||
public GameObject OrbPrefab;
|
||||
private QSBNetworkLobby _lobby;
|
||||
private AssetBundle _assetBundle;
|
||||
private GameObject _shipPrefab;
|
||||
private GameObject _cameraPrefab;
|
||||
private GameObject _probePrefab;
|
||||
public GameObject OrbPrefab;
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
DebugLog.DebugWrite("AWAKE");
|
||||
Instance = this;
|
||||
private void Awake()
|
||||
{
|
||||
DebugLog.DebugWrite("AWAKE");
|
||||
Instance = this;
|
||||
|
||||
_lobby = gameObject.AddComponent<QSBNetworkLobby>();
|
||||
_assetBundle = QSB.NetworkAssetBundle;
|
||||
_lobby = gameObject.AddComponent<QSBNetworkLobby>();
|
||||
_assetBundle = QSB.NetworkAssetBundle;
|
||||
|
||||
DebugLog.DebugWrite("player");
|
||||
playerPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkplayer.prefab");
|
||||
var ident = playerPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", playerPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", playerPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
playerPrefab.AddComponent<PlayerTransformSync>();
|
||||
playerPrefab.AddComponent<AnimationSync>();
|
||||
playerPrefab.AddComponent<WakeUpSync>();
|
||||
playerPrefab.AddComponent<InstrumentsManager>();
|
||||
DebugLog.DebugWrite("player");
|
||||
playerPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkplayer.prefab");
|
||||
var ident = playerPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", playerPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", playerPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
playerPrefab.AddComponent<PlayerTransformSync>();
|
||||
playerPrefab.AddComponent<AnimationSync>();
|
||||
playerPrefab.AddComponent<WakeUpSync>();
|
||||
playerPrefab.AddComponent<InstrumentsManager>();
|
||||
|
||||
DebugLog.DebugWrite("ship");
|
||||
_shipPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkship.prefab");
|
||||
ident = _shipPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", _shipPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", _shipPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
_shipPrefab.AddComponent<ShipTransformSync>();
|
||||
spawnPrefabs.Add(_shipPrefab);
|
||||
DebugLog.DebugWrite("ship");
|
||||
_shipPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkship.prefab");
|
||||
ident = _shipPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", _shipPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", _shipPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
_shipPrefab.AddComponent<ShipTransformSync>();
|
||||
spawnPrefabs.Add(_shipPrefab);
|
||||
|
||||
DebugLog.DebugWrite("camera");
|
||||
_cameraPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkcameraroot.prefab");
|
||||
ident = _cameraPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", _cameraPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", _cameraPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
_cameraPrefab.AddComponent<PlayerCameraSync>();
|
||||
spawnPrefabs.Add(_cameraPrefab);
|
||||
DebugLog.DebugWrite("camera");
|
||||
_cameraPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkcameraroot.prefab");
|
||||
ident = _cameraPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", _cameraPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", _cameraPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
_cameraPrefab.AddComponent<PlayerCameraSync>();
|
||||
spawnPrefabs.Add(_cameraPrefab);
|
||||
|
||||
DebugLog.DebugWrite("probe");
|
||||
_probePrefab = _assetBundle.LoadAsset<GameObject>("assets/networkprobe.prefab");
|
||||
ident = _probePrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", _probePrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", _probePrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
_probePrefab.AddComponent<PlayerProbeSync>();
|
||||
spawnPrefabs.Add(_probePrefab);
|
||||
DebugLog.DebugWrite("probe");
|
||||
_probePrefab = _assetBundle.LoadAsset<GameObject>("assets/networkprobe.prefab");
|
||||
ident = _probePrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", _probePrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", _probePrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
_probePrefab.AddComponent<PlayerProbeSync>();
|
||||
spawnPrefabs.Add(_probePrefab);
|
||||
|
||||
DebugLog.DebugWrite("orb");
|
||||
OrbPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkorb.prefab");
|
||||
ident = OrbPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", OrbPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", OrbPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
OrbPrefab.AddComponent<NomaiOrbTransformSync>();
|
||||
spawnPrefabs.Add(OrbPrefab);
|
||||
DebugLog.DebugWrite("orb");
|
||||
OrbPrefab = _assetBundle.LoadAsset<GameObject>("assets/networkorb.prefab");
|
||||
ident = OrbPrefab.AddComponent<QSBNetworkIdentity>();
|
||||
ident.LocalPlayerAuthority = true;
|
||||
ident.SetValue("m_AssetId", OrbPrefab.GetComponent<NetworkIdentity>().assetId);
|
||||
ident.SetValue("m_SceneId", OrbPrefab.GetComponent<NetworkIdentity>().sceneId);
|
||||
OrbPrefab.AddComponent<NomaiOrbTransformSync>();
|
||||
spawnPrefabs.Add(OrbPrefab);
|
||||
|
||||
ConfigureNetworkManager();
|
||||
QSBSceneManager.OnUniverseSceneLoaded += OnSceneLoaded;
|
||||
}
|
||||
ConfigureNetworkManager();
|
||||
QSBSceneManager.OnUniverseSceneLoaded += OnSceneLoaded;
|
||||
}
|
||||
|
||||
private void OnDestroy()
|
||||
=> QSBSceneManager.OnUniverseSceneLoaded -= OnSceneLoaded;
|
||||
private void OnDestroy()
|
||||
=> QSBSceneManager.OnUniverseSceneLoaded -= OnSceneLoaded;
|
||||
|
||||
private void OnSceneLoaded(OWScene scene)
|
||||
{
|
||||
DebugLog.DebugWrite("scene loaded");
|
||||
OrbManager.Instance.BuildOrbs();
|
||||
OrbManager.Instance.QueueBuildSlots();
|
||||
WorldRegistry.OldDialogueTrees.Clear();
|
||||
WorldRegistry.OldDialogueTrees = Resources.FindObjectsOfTypeAll<CharacterDialogueTree>().ToList();
|
||||
}
|
||||
private void OnSceneLoaded(OWScene scene)
|
||||
{
|
||||
DebugLog.DebugWrite("scene loaded");
|
||||
OrbManager.Instance.BuildOrbs();
|
||||
OrbManager.Instance.QueueBuildSlots();
|
||||
WorldRegistry.OldDialogueTrees.Clear();
|
||||
WorldRegistry.OldDialogueTrees = Resources.FindObjectsOfTypeAll<CharacterDialogueTree>().ToList();
|
||||
}
|
||||
|
||||
private void ConfigureNetworkManager()
|
||||
{
|
||||
networkAddress = QSB.DefaultServerIP;
|
||||
networkPort = QSB.Port;
|
||||
maxConnections = MaxConnections;
|
||||
customConfig = true;
|
||||
connectionConfig.AddChannel(QosType.Reliable);
|
||||
connectionConfig.AddChannel(QosType.Unreliable);
|
||||
this.SetValue("m_MaxBufferedPackets", MaxBufferedPackets);
|
||||
channels.Add(QosType.Reliable);
|
||||
channels.Add(QosType.Unreliable);
|
||||
private void ConfigureNetworkManager()
|
||||
{
|
||||
networkAddress = QSB.DefaultServerIP;
|
||||
networkPort = QSB.Port;
|
||||
maxConnections = MaxConnections;
|
||||
customConfig = true;
|
||||
connectionConfig.AddChannel(QosType.Reliable);
|
||||
connectionConfig.AddChannel(QosType.Unreliable);
|
||||
this.SetValue("m_MaxBufferedPackets", MaxBufferedPackets);
|
||||
channels.Add(QosType.Reliable);
|
||||
channels.Add(QosType.Unreliable);
|
||||
|
||||
DebugLog.DebugWrite("Network Manager ready.", MessageType.Success);
|
||||
}
|
||||
DebugLog.DebugWrite("Network Manager ready.", MessageType.Success);
|
||||
}
|
||||
|
||||
public override void OnStartServer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartServer", MessageType.Info);
|
||||
if (WorldRegistry.OrbSyncList.Count == 0 && QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
OrbManager.Instance.QueueBuildOrbs();
|
||||
}
|
||||
if (WorldRegistry.OldDialogueTrees.Count == 0 && QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
WorldRegistry.OldDialogueTrees = Resources.FindObjectsOfTypeAll<CharacterDialogueTree>().ToList();
|
||||
}
|
||||
public override void OnStartServer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartServer", MessageType.Info);
|
||||
if (WorldRegistry.OrbSyncList.Count == 0 && QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
OrbManager.Instance.QueueBuildOrbs();
|
||||
}
|
||||
if (WorldRegistry.OldDialogueTrees.Count == 0 && QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
WorldRegistry.OldDialogueTrees = Resources.FindObjectsOfTypeAll<CharacterDialogueTree>().ToList();
|
||||
}
|
||||
|
||||
QSBNetworkServer.UnregisterHandler(40);
|
||||
QSBNetworkServer.UnregisterHandler(41);
|
||||
QSBNetworkServer.UnregisterHandler(42);
|
||||
QSBNetworkServer.RegisterHandler(40, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationServerMessage));
|
||||
QSBNetworkServer.RegisterHandler(41, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationParametersServerMessage));
|
||||
QSBNetworkServer.RegisterHandler(42, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationTriggerServerMessage));
|
||||
}
|
||||
QSBNetworkServer.UnregisterHandler(40);
|
||||
QSBNetworkServer.UnregisterHandler(41);
|
||||
QSBNetworkServer.UnregisterHandler(42);
|
||||
QSBNetworkServer.RegisterHandler(40, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationServerMessage));
|
||||
QSBNetworkServer.RegisterHandler(41, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationParametersServerMessage));
|
||||
QSBNetworkServer.RegisterHandler(42, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationTriggerServerMessage));
|
||||
}
|
||||
|
||||
public override void OnServerAddPlayer(QSBNetworkConnection connection, short playerControllerId) // Called on the server when a client joins
|
||||
{
|
||||
DebugLog.DebugWrite("OnServerAddPlayer", MessageType.Info);
|
||||
base.OnServerAddPlayer(connection, playerControllerId);
|
||||
public override void OnServerAddPlayer(QSBNetworkConnection connection, short playerControllerId) // Called on the server when a client joins
|
||||
{
|
||||
DebugLog.DebugWrite("OnServerAddPlayer", MessageType.Info);
|
||||
base.OnServerAddPlayer(connection, playerControllerId);
|
||||
|
||||
QSBNetworkServer.SpawnWithClientAuthority(Instantiate(_shipPrefab), connection);
|
||||
QSBNetworkServer.SpawnWithClientAuthority(Instantiate(_cameraPrefab), connection);
|
||||
QSBNetworkServer.SpawnWithClientAuthority(Instantiate(_probePrefab), connection);
|
||||
}
|
||||
QSBNetworkServer.SpawnWithClientAuthority(Instantiate(_shipPrefab), connection);
|
||||
QSBNetworkServer.SpawnWithClientAuthority(Instantiate(_cameraPrefab), connection);
|
||||
QSBNetworkServer.SpawnWithClientAuthority(Instantiate(_probePrefab), connection);
|
||||
}
|
||||
|
||||
public override void OnClientConnect(QSBNetworkConnection connection) // Called on the client when connecting to a server
|
||||
{
|
||||
DebugLog.DebugWrite("OnClientConnect", MessageType.Info);
|
||||
base.OnClientConnect(connection);
|
||||
public override void OnClientConnect(QSBNetworkConnection connection) // Called on the client when connecting to a server
|
||||
{
|
||||
DebugLog.DebugWrite("OnClientConnect", MessageType.Info);
|
||||
base.OnClientConnect(connection);
|
||||
|
||||
gameObject.AddComponent<SectorSync.SectorSync>();
|
||||
gameObject.AddComponent<RespawnOnDeath>();
|
||||
gameObject.AddComponent<PreventShipDestruction>();
|
||||
gameObject.AddComponent<SectorSync.SectorSync>();
|
||||
gameObject.AddComponent<RespawnOnDeath>();
|
||||
gameObject.AddComponent<PreventShipDestruction>();
|
||||
|
||||
if (QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
QSBSectorManager.Instance.RebuildSectors();
|
||||
OrbManager.Instance.QueueBuildSlots();
|
||||
}
|
||||
if (QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
QSBSectorManager.Instance.RebuildSectors();
|
||||
OrbManager.Instance.QueueBuildSlots();
|
||||
}
|
||||
|
||||
if (!QSBNetworkServer.localClientActive)
|
||||
{
|
||||
QSBPatchManager.DoPatchType(QSBPatchTypes.OnNonServerClientConnect);
|
||||
singleton.client.UnregisterHandler(40);
|
||||
singleton.client.UnregisterHandler(41);
|
||||
singleton.client.RegisterHandlerSafe(40, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationClientMessage));
|
||||
singleton.client.RegisterHandlerSafe(41, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationParametersClientMessage));
|
||||
}
|
||||
singleton.client.UnregisterHandler(42);
|
||||
singleton.client.RegisterHandlerSafe(42, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationTriggerClientMessage));
|
||||
if (!QSBNetworkServer.localClientActive)
|
||||
{
|
||||
QSBPatchManager.DoPatchType(QSBPatchTypes.OnNonServerClientConnect);
|
||||
singleton.client.UnregisterHandler(40);
|
||||
singleton.client.UnregisterHandler(41);
|
||||
singleton.client.RegisterHandlerSafe(40, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationClientMessage));
|
||||
singleton.client.RegisterHandlerSafe(41, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationParametersClientMessage));
|
||||
}
|
||||
singleton.client.UnregisterHandler(42);
|
||||
singleton.client.RegisterHandlerSafe(42, new QSBNetworkMessageDelegate(QSBNetworkAnimator.OnAnimationTriggerClientMessage));
|
||||
|
||||
QSBPatchManager.DoPatchType(QSBPatchTypes.OnClientConnect);
|
||||
QSBPatchManager.DoPatchType(QSBPatchTypes.OnClientConnect);
|
||||
|
||||
_lobby.CanEditName = false;
|
||||
_lobby.CanEditName = false;
|
||||
|
||||
OnNetworkManagerReady?.Invoke();
|
||||
IsReady = true;
|
||||
OnNetworkManagerReady?.Invoke();
|
||||
IsReady = true;
|
||||
|
||||
QSB.Helper.Events.Unity.RunWhen(() => PlayerTransformSync.LocalInstance != null, QSBEventManager.Init);
|
||||
QSB.Helper.Events.Unity.RunWhen(() => PlayerTransformSync.LocalInstance != null, QSBEventManager.Init);
|
||||
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSBEventManager.Ready,
|
||||
() => GlobalMessenger<string>.FireEvent(EventNames.QSBPlayerJoin, _lobby.PlayerName));
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSBEventManager.Ready,
|
||||
() => GlobalMessenger<string>.FireEvent(EventNames.QSBPlayerJoin, _lobby.PlayerName));
|
||||
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSBEventManager.Ready,
|
||||
() => GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest));
|
||||
}
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSBEventManager.Ready,
|
||||
() => GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest));
|
||||
}
|
||||
|
||||
public override void OnStopClient() // Called on the client when closing connection
|
||||
{
|
||||
DebugLog.DebugWrite("OnStopClient", MessageType.Info);
|
||||
DebugLog.ToConsole("Disconnecting from server...", MessageType.Info);
|
||||
Destroy(GetComponent<SectorSync.SectorSync>());
|
||||
Destroy(GetComponent<RespawnOnDeath>());
|
||||
Destroy(GetComponent<PreventShipDestruction>());
|
||||
QSBEventManager.Reset();
|
||||
QSBPlayerManager.PlayerList.ForEach(player => player.HudMarker?.Remove());
|
||||
public override void OnStopClient() // Called on the client when closing connection
|
||||
{
|
||||
DebugLog.DebugWrite("OnStopClient", MessageType.Info);
|
||||
DebugLog.ToConsole("Disconnecting from server...", MessageType.Info);
|
||||
Destroy(GetComponent<SectorSync.SectorSync>());
|
||||
Destroy(GetComponent<RespawnOnDeath>());
|
||||
Destroy(GetComponent<PreventShipDestruction>());
|
||||
QSBEventManager.Reset();
|
||||
QSBPlayerManager.PlayerList.ForEach(player => player.HudMarker?.Remove());
|
||||
|
||||
foreach (var player in QSBPlayerManager.PlayerList)
|
||||
{
|
||||
QSBPlayerManager.GetPlayerNetIds(player).ForEach(CleanupNetworkBehaviour);
|
||||
}
|
||||
QSBPlayerManager.RemoveAllPlayers();
|
||||
foreach (var player in QSBPlayerManager.PlayerList)
|
||||
{
|
||||
QSBPlayerManager.GetPlayerNetIds(player).ForEach(CleanupNetworkBehaviour);
|
||||
}
|
||||
QSBPlayerManager.RemoveAllPlayers();
|
||||
|
||||
WorldRegistry.RemoveObjects<QSBOrbSlot>();
|
||||
WorldRegistry.RemoveObjects<QSBElevator>();
|
||||
WorldRegistry.RemoveObjects<QSBGeyser>();
|
||||
WorldRegistry.RemoveObjects<QSBSector>();
|
||||
WorldRegistry.OrbSyncList.Clear();
|
||||
WorldRegistry.OldDialogueTrees.Clear();
|
||||
WorldRegistry.RemoveObjects<QSBOrbSlot>();
|
||||
WorldRegistry.RemoveObjects<QSBElevator>();
|
||||
WorldRegistry.RemoveObjects<QSBGeyser>();
|
||||
WorldRegistry.RemoveObjects<QSBSector>();
|
||||
WorldRegistry.OrbSyncList.Clear();
|
||||
WorldRegistry.OldDialogueTrees.Clear();
|
||||
|
||||
_lobby.CanEditName = true;
|
||||
}
|
||||
_lobby.CanEditName = true;
|
||||
}
|
||||
|
||||
public override void OnServerDisconnect(QSBNetworkConnection connection) // Called on the server when any client disconnects
|
||||
{
|
||||
DebugLog.DebugWrite("OnServerDisconnect", MessageType.Info);
|
||||
var player = connection.GetPlayer();
|
||||
var netIds = connection.ClientOwnedObjects.Select(x => x.Value).ToArray();
|
||||
GlobalMessenger<uint, uint[]>.FireEvent(EventNames.QSBPlayerLeave, player.PlayerId, netIds);
|
||||
public override void OnServerDisconnect(QSBNetworkConnection connection) // Called on the server when any client disconnects
|
||||
{
|
||||
DebugLog.DebugWrite("OnServerDisconnect", MessageType.Info);
|
||||
var player = connection.GetPlayer();
|
||||
var netIds = connection.ClientOwnedObjects.Select(x => x.Value).ToArray();
|
||||
GlobalMessenger<uint, uint[]>.FireEvent(EventNames.QSBPlayerLeave, player.PlayerId, netIds);
|
||||
|
||||
foreach (var item in WorldRegistry.OrbSyncList)
|
||||
{
|
||||
var identity = item.GetComponent<QSBNetworkIdentity>();
|
||||
if (identity.ClientAuthorityOwner == connection)
|
||||
{
|
||||
identity.RemoveClientAuthority(connection);
|
||||
}
|
||||
}
|
||||
foreach (var item in WorldRegistry.OrbSyncList)
|
||||
{
|
||||
var identity = item.GetComponent<QSBNetworkIdentity>();
|
||||
if (identity.ClientAuthorityOwner == connection)
|
||||
{
|
||||
identity.RemoveClientAuthority(connection);
|
||||
}
|
||||
}
|
||||
|
||||
player.HudMarker?.Remove();
|
||||
CleanupConnection(connection);
|
||||
}
|
||||
player.HudMarker?.Remove();
|
||||
CleanupConnection(connection);
|
||||
}
|
||||
|
||||
public override void OnStopServer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStopServer", MessageType.Info);
|
||||
Destroy(GetComponent<SectorSync.SectorSync>());
|
||||
Destroy(GetComponent<RespawnOnDeath>());
|
||||
Destroy(GetComponent<PreventShipDestruction>());
|
||||
QSBEventManager.Reset();
|
||||
DebugLog.ToConsole("[S] Server stopped!", MessageType.Info);
|
||||
QSBPlayerManager.PlayerList.ForEach(player => player.HudMarker?.Remove());
|
||||
QSBNetworkServer.connections.ToList().ForEach(CleanupConnection);
|
||||
public override void OnStopServer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStopServer", MessageType.Info);
|
||||
Destroy(GetComponent<SectorSync.SectorSync>());
|
||||
Destroy(GetComponent<RespawnOnDeath>());
|
||||
Destroy(GetComponent<PreventShipDestruction>());
|
||||
QSBEventManager.Reset();
|
||||
DebugLog.ToConsole("[S] Server stopped!", MessageType.Info);
|
||||
QSBPlayerManager.PlayerList.ForEach(player => player.HudMarker?.Remove());
|
||||
QSBNetworkServer.connections.ToList().ForEach(CleanupConnection);
|
||||
|
||||
WorldRegistry.RemoveObjects<QSBOrbSlot>();
|
||||
WorldRegistry.RemoveObjects<QSBElevator>();
|
||||
WorldRegistry.RemoveObjects<QSBGeyser>();
|
||||
WorldRegistry.RemoveObjects<QSBSector>();
|
||||
WorldRegistry.RemoveObjects<QSBOrbSlot>();
|
||||
WorldRegistry.RemoveObjects<QSBElevator>();
|
||||
WorldRegistry.RemoveObjects<QSBGeyser>();
|
||||
WorldRegistry.RemoveObjects<QSBSector>();
|
||||
|
||||
base.OnStopServer();
|
||||
}
|
||||
base.OnStopServer();
|
||||
}
|
||||
|
||||
private void CleanupConnection(QSBNetworkConnection connection)
|
||||
{
|
||||
var player = connection.GetPlayer();
|
||||
DebugLog.ToConsole($"{player.Name} disconnected.", MessageType.Info);
|
||||
QSBPlayerManager.RemovePlayer(player.PlayerId);
|
||||
private void CleanupConnection(QSBNetworkConnection connection)
|
||||
{
|
||||
var player = connection.GetPlayer();
|
||||
DebugLog.ToConsole($"{player.Name} disconnected.", MessageType.Info);
|
||||
QSBPlayerManager.RemovePlayer(player.PlayerId);
|
||||
|
||||
var netIds = connection.ClientOwnedObjects?.Select(x => x.Value).ToList();
|
||||
netIds.ForEach(CleanupNetworkBehaviour);
|
||||
}
|
||||
var netIds = connection.ClientOwnedObjects?.Select(x => x.Value).ToList();
|
||||
netIds.ForEach(CleanupNetworkBehaviour);
|
||||
}
|
||||
|
||||
public void CleanupNetworkBehaviour(uint netId)
|
||||
{
|
||||
DebugLog.DebugWrite($"Cleaning up netId {netId}");
|
||||
// Multiple networkbehaviours can use the same networkidentity (same netId), so get all of them
|
||||
var networkBehaviours = FindObjectsOfType<QSBNetworkBehaviour>()
|
||||
.Where(x => x != null && x.NetId.Value == netId);
|
||||
foreach (var networkBehaviour in networkBehaviours)
|
||||
{
|
||||
var transformSync = networkBehaviour.GetComponent<TransformSync.TransformSync>();
|
||||
public void CleanupNetworkBehaviour(uint netId)
|
||||
{
|
||||
DebugLog.DebugWrite($"Cleaning up netId {netId}");
|
||||
// Multiple networkbehaviours can use the same networkidentity (same netId), so get all of them
|
||||
var networkBehaviours = FindObjectsOfType<QSBNetworkBehaviour>()
|
||||
.Where(x => x != null && x.NetId.Value == netId);
|
||||
foreach (var networkBehaviour in networkBehaviours)
|
||||
{
|
||||
var transformSync = networkBehaviour.GetComponent<TransformSync.TransformSync>();
|
||||
|
||||
if (transformSync != null)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Removing TransformSync from syncobjects");
|
||||
QSBPlayerManager.PlayerSyncObjects.Remove(transformSync);
|
||||
if (transformSync.SyncedTransform != null && netId != QSBPlayerManager.LocalPlayerId && !networkBehaviour.HasAuthority)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Destroying {transformSync.SyncedTransform.gameObject.name}");
|
||||
Destroy(transformSync.SyncedTransform.gameObject);
|
||||
}
|
||||
}
|
||||
if (transformSync != null)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Removing TransformSync from syncobjects");
|
||||
QSBPlayerManager.PlayerSyncObjects.Remove(transformSync);
|
||||
if (transformSync.SyncedTransform != null && netId != QSBPlayerManager.LocalPlayerId && !networkBehaviour.HasAuthority)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Destroying {transformSync.SyncedTransform.gameObject.name}");
|
||||
Destroy(transformSync.SyncedTransform.gameObject);
|
||||
}
|
||||
}
|
||||
|
||||
var animationSync = networkBehaviour.GetComponent<AnimationSync>();
|
||||
var animationSync = networkBehaviour.GetComponent<AnimationSync>();
|
||||
|
||||
if (animationSync != null)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Removing AnimationSync from syncobjects");
|
||||
QSBPlayerManager.PlayerSyncObjects.Remove(animationSync);
|
||||
}
|
||||
if (animationSync != null)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Removing AnimationSync from syncobjects");
|
||||
QSBPlayerManager.PlayerSyncObjects.Remove(animationSync);
|
||||
}
|
||||
|
||||
if (!networkBehaviour.HasAuthority)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Destroying {networkBehaviour.gameObject.name}");
|
||||
Destroy(networkBehaviour.gameObject);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!networkBehaviour.HasAuthority)
|
||||
{
|
||||
DebugLog.DebugWrite($" * Destroying {networkBehaviour.gameObject.name}");
|
||||
Destroy(networkBehaviour.gameObject);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -4,33 +4,33 @@ using System;
|
||||
|
||||
namespace QSB
|
||||
{
|
||||
public static class QSBSceneManager
|
||||
{
|
||||
public static OWScene CurrentScene => LoadManager.GetCurrentScene();
|
||||
public static class QSBSceneManager
|
||||
{
|
||||
public static OWScene CurrentScene => LoadManager.GetCurrentScene();
|
||||
|
||||
public static bool IsInUniverse => InUniverse(CurrentScene);
|
||||
public static bool IsInUniverse => InUniverse(CurrentScene);
|
||||
|
||||
public static event Action<OWScene, bool> OnSceneLoaded;
|
||||
public static event Action<OWScene> OnUniverseSceneLoaded;
|
||||
public static event Action<OWScene, bool> OnSceneLoaded;
|
||||
public static event Action<OWScene> OnUniverseSceneLoaded;
|
||||
|
||||
static QSBSceneManager()
|
||||
{
|
||||
LoadManager.OnCompleteSceneLoad += OnCompleteSceneLoad;
|
||||
DebugLog.DebugWrite("Scene Manager ready.", MessageType.Success);
|
||||
}
|
||||
static QSBSceneManager()
|
||||
{
|
||||
LoadManager.OnCompleteSceneLoad += OnCompleteSceneLoad;
|
||||
DebugLog.DebugWrite("Scene Manager ready.", MessageType.Success);
|
||||
}
|
||||
|
||||
private static void OnCompleteSceneLoad(OWScene oldScene, OWScene newScene)
|
||||
{
|
||||
DebugLog.DebugWrite($"COMPLETE SCENE LOAD ({oldScene} -> {newScene})", MessageType.Info);
|
||||
var universe = InUniverse(newScene);
|
||||
OnSceneLoaded?.Invoke(newScene, universe);
|
||||
if (universe)
|
||||
{
|
||||
OnUniverseSceneLoaded?.Invoke(newScene);
|
||||
}
|
||||
}
|
||||
private static void OnCompleteSceneLoad(OWScene oldScene, OWScene newScene)
|
||||
{
|
||||
DebugLog.DebugWrite($"COMPLETE SCENE LOAD ({oldScene} -> {newScene})", MessageType.Info);
|
||||
var universe = InUniverse(newScene);
|
||||
OnSceneLoaded?.Invoke(newScene, universe);
|
||||
if (universe)
|
||||
{
|
||||
OnUniverseSceneLoaded?.Invoke(newScene);
|
||||
}
|
||||
}
|
||||
|
||||
private static bool InUniverse(OWScene scene)
|
||||
=> scene == OWScene.SolarSystem || scene == OWScene.EyeOfTheUniverse;
|
||||
}
|
||||
private static bool InUniverse(OWScene scene)
|
||||
=> scene == OWScene.SolarSystem || scene == OWScene.EyeOfTheUniverse;
|
||||
}
|
||||
}
|
||||
|
@ -3,23 +3,23 @@ using QSB.QuantumUNET;
|
||||
|
||||
namespace QSB.TimeSync
|
||||
{
|
||||
public class PreserveTimeScale : QSBNetworkBehaviour
|
||||
{
|
||||
private void Start()
|
||||
{
|
||||
QSB.Helper.Menus.PauseMenu.GetTitleButton("Button-EndCurrentLoop").Hide(); // Remove the meditation button
|
||||
public class PreserveTimeScale : QSBNetworkBehaviour
|
||||
{
|
||||
private void Start()
|
||||
{
|
||||
QSB.Helper.Menus.PauseMenu.GetTitleButton("Button-EndCurrentLoop").Hide(); // Remove the meditation button
|
||||
|
||||
// Allow server to sleep at campfires
|
||||
if (IsServer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
// Allow server to sleep at campfires
|
||||
if (IsServer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var campfires = FindObjectsOfType<Campfire>();
|
||||
foreach (var campfire in campfires)
|
||||
{
|
||||
campfire.SetValue("_canSleepHere", false); // Stop players from sleeping at campfires
|
||||
}
|
||||
}
|
||||
}
|
||||
var campfires = FindObjectsOfType<Campfire>();
|
||||
foreach (var campfire in campfires)
|
||||
{
|
||||
campfire.SetValue("_canSleepHere", false); // Stop players from sleeping at campfires
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -7,250 +7,250 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TimeSync
|
||||
{
|
||||
public class WakeUpSync : QSBNetworkBehaviour
|
||||
{
|
||||
public static WakeUpSync LocalInstance { get; private set; }
|
||||
public class WakeUpSync : QSBNetworkBehaviour
|
||||
{
|
||||
public static WakeUpSync LocalInstance { get; private set; }
|
||||
|
||||
private const float TimeThreshold = 0.5f;
|
||||
private const float MaxFastForwardSpeed = 60f;
|
||||
private const float MaxFastForwardDiff = 20f;
|
||||
private const float MinFastForwardSpeed = 2f;
|
||||
private const float TimeThreshold = 0.5f;
|
||||
private const float MaxFastForwardSpeed = 60f;
|
||||
private const float MaxFastForwardDiff = 20f;
|
||||
private const float MinFastForwardSpeed = 2f;
|
||||
|
||||
private enum State { NotLoaded, Loaded, FastForwarding, Pausing }
|
||||
private State _state = State.NotLoaded;
|
||||
private enum State { NotLoaded, Loaded, FastForwarding, Pausing }
|
||||
private State _state = State.NotLoaded;
|
||||
|
||||
private float _sendTimer;
|
||||
private float _serverTime;
|
||||
private float _timeScale;
|
||||
private bool _isInputEnabled = true;
|
||||
private bool _isFirstFastForward = true;
|
||||
private int _localLoopCount;
|
||||
private int _serverLoopCount;
|
||||
private float _sendTimer;
|
||||
private float _serverTime;
|
||||
private float _timeScale;
|
||||
private bool _isInputEnabled = true;
|
||||
private bool _isFirstFastForward = true;
|
||||
private int _localLoopCount;
|
||||
private int _serverLoopCount;
|
||||
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
LocalInstance = this;
|
||||
}
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
LocalInstance = this;
|
||||
}
|
||||
|
||||
private void Start()
|
||||
{
|
||||
if (!IsLocalPlayer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
private void Start()
|
||||
{
|
||||
if (!IsLocalPlayer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
QSBSceneManager.OnSceneLoaded += OnSceneLoaded;
|
||||
if (QSBSceneManager.IsInUniverse)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
QSBSceneManager.OnSceneLoaded += OnSceneLoaded;
|
||||
|
||||
GlobalMessenger.AddListener(EventNames.RestartTimeLoop, OnLoopStart);
|
||||
GlobalMessenger.AddListener(EventNames.WakeUp, OnWakeUp);
|
||||
}
|
||||
GlobalMessenger.AddListener(EventNames.RestartTimeLoop, OnLoopStart);
|
||||
GlobalMessenger.AddListener(EventNames.WakeUp, OnWakeUp);
|
||||
}
|
||||
|
||||
private void OnWakeUp()
|
||||
{
|
||||
DebugLog.DebugWrite("ON WAKE UP!");
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
QSB.HasWokenUp = true;
|
||||
}
|
||||
}
|
||||
private void OnWakeUp()
|
||||
{
|
||||
DebugLog.DebugWrite("ON WAKE UP!");
|
||||
if (QSBNetworkServer.active)
|
||||
{
|
||||
QSB.HasWokenUp = true;
|
||||
}
|
||||
}
|
||||
|
||||
private void OnDestroy()
|
||||
{
|
||||
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
|
||||
GlobalMessenger.RemoveListener(EventNames.RestartTimeLoop, OnLoopStart);
|
||||
GlobalMessenger.RemoveListener(EventNames.WakeUp, OnWakeUp);
|
||||
}
|
||||
private void OnDestroy()
|
||||
{
|
||||
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
|
||||
GlobalMessenger.RemoveListener(EventNames.RestartTimeLoop, OnLoopStart);
|
||||
GlobalMessenger.RemoveListener(EventNames.WakeUp, OnWakeUp);
|
||||
}
|
||||
|
||||
private void OnSceneLoaded(OWScene scene, bool isInUniverse)
|
||||
{
|
||||
QSB.HasWokenUp = (scene == OWScene.EyeOfTheUniverse);
|
||||
if (isInUniverse)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else
|
||||
{
|
||||
_state = State.NotLoaded;
|
||||
}
|
||||
}
|
||||
private void OnSceneLoaded(OWScene scene, bool isInUniverse)
|
||||
{
|
||||
QSB.HasWokenUp = (scene == OWScene.EyeOfTheUniverse);
|
||||
if (isInUniverse)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else
|
||||
{
|
||||
_state = State.NotLoaded;
|
||||
}
|
||||
}
|
||||
|
||||
private void OnLoopStart()
|
||||
{
|
||||
_localLoopCount++;
|
||||
}
|
||||
private void OnLoopStart()
|
||||
{
|
||||
_localLoopCount++;
|
||||
}
|
||||
|
||||
private void Init()
|
||||
{
|
||||
GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest);
|
||||
_state = State.Loaded;
|
||||
gameObject.AddComponent<PreserveTimeScale>();
|
||||
if (IsServer)
|
||||
{
|
||||
SendServerTime();
|
||||
}
|
||||
else
|
||||
{
|
||||
WakeUpOrSleep();
|
||||
}
|
||||
}
|
||||
private void Init()
|
||||
{
|
||||
GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest);
|
||||
_state = State.Loaded;
|
||||
gameObject.AddComponent<PreserveTimeScale>();
|
||||
if (IsServer)
|
||||
{
|
||||
SendServerTime();
|
||||
}
|
||||
else
|
||||
{
|
||||
WakeUpOrSleep();
|
||||
}
|
||||
}
|
||||
|
||||
private void SendServerTime()
|
||||
{
|
||||
GlobalMessenger<float, int>.FireEvent(EventNames.QSBServerTime, Time.timeSinceLevelLoad, _localLoopCount);
|
||||
}
|
||||
private void SendServerTime()
|
||||
{
|
||||
GlobalMessenger<float, int>.FireEvent(EventNames.QSBServerTime, Time.timeSinceLevelLoad, _localLoopCount);
|
||||
}
|
||||
|
||||
public void OnClientReceiveMessage(ServerTimeMessage message)
|
||||
{
|
||||
_serverTime = message.ServerTime;
|
||||
_serverLoopCount = message.LoopCount;
|
||||
WakeUpOrSleep();
|
||||
}
|
||||
public void OnClientReceiveMessage(ServerTimeMessage message)
|
||||
{
|
||||
_serverTime = message.ServerTime;
|
||||
_serverLoopCount = message.LoopCount;
|
||||
WakeUpOrSleep();
|
||||
}
|
||||
|
||||
private void WakeUpOrSleep()
|
||||
{
|
||||
if (_state == State.NotLoaded || _localLoopCount != _serverLoopCount)
|
||||
{
|
||||
return;
|
||||
}
|
||||
private void WakeUpOrSleep()
|
||||
{
|
||||
if (_state == State.NotLoaded || _localLoopCount != _serverLoopCount)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var myTime = Time.timeSinceLevelLoad;
|
||||
var diff = myTime - _serverTime;
|
||||
var myTime = Time.timeSinceLevelLoad;
|
||||
var diff = myTime - _serverTime;
|
||||
|
||||
if (diff > TimeThreshold)
|
||||
{
|
||||
StartPausing();
|
||||
return;
|
||||
}
|
||||
if (diff > TimeThreshold)
|
||||
{
|
||||
StartPausing();
|
||||
return;
|
||||
}
|
||||
|
||||
if (diff < -TimeThreshold)
|
||||
{
|
||||
StartFastForwarding();
|
||||
}
|
||||
}
|
||||
if (diff < -TimeThreshold)
|
||||
{
|
||||
StartFastForwarding();
|
||||
}
|
||||
}
|
||||
|
||||
private void StartFastForwarding()
|
||||
{
|
||||
if (_state == State.FastForwarding)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_timeScale = MaxFastForwardSpeed;
|
||||
_state = State.FastForwarding;
|
||||
TimeSyncUI.Start(TimeSyncType.Fastforwarding);
|
||||
}
|
||||
private void StartFastForwarding()
|
||||
{
|
||||
if (_state == State.FastForwarding)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_timeScale = MaxFastForwardSpeed;
|
||||
_state = State.FastForwarding;
|
||||
TimeSyncUI.Start(TimeSyncType.Fastforwarding);
|
||||
}
|
||||
|
||||
private void StartPausing()
|
||||
{
|
||||
if (_state == State.Pausing)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_timeScale = 0f;
|
||||
_state = State.Pausing;
|
||||
SpinnerUI.Show();
|
||||
TimeSyncUI.Start(TimeSyncType.Pausing);
|
||||
}
|
||||
private void StartPausing()
|
||||
{
|
||||
if (_state == State.Pausing)
|
||||
{
|
||||
return;
|
||||
}
|
||||
_timeScale = 0f;
|
||||
_state = State.Pausing;
|
||||
SpinnerUI.Show();
|
||||
TimeSyncUI.Start(TimeSyncType.Pausing);
|
||||
}
|
||||
|
||||
private void ResetTimeScale()
|
||||
{
|
||||
_timeScale = 1f;
|
||||
_state = State.Loaded;
|
||||
private void ResetTimeScale()
|
||||
{
|
||||
_timeScale = 1f;
|
||||
_state = State.Loaded;
|
||||
|
||||
if (!_isInputEnabled)
|
||||
{
|
||||
EnableInput();
|
||||
}
|
||||
_isFirstFastForward = false;
|
||||
QSB.HasWokenUp = true;
|
||||
Physics.SyncTransforms();
|
||||
SpinnerUI.Hide();
|
||||
TimeSyncUI.Stop();
|
||||
GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest);
|
||||
RespawnOnDeath.Instance.Init();
|
||||
}
|
||||
if (!_isInputEnabled)
|
||||
{
|
||||
EnableInput();
|
||||
}
|
||||
_isFirstFastForward = false;
|
||||
QSB.HasWokenUp = true;
|
||||
Physics.SyncTransforms();
|
||||
SpinnerUI.Hide();
|
||||
TimeSyncUI.Stop();
|
||||
GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest);
|
||||
RespawnOnDeath.Instance.Init();
|
||||
}
|
||||
|
||||
private void DisableInput()
|
||||
{
|
||||
_isInputEnabled = false;
|
||||
OWInput.ChangeInputMode(InputMode.None);
|
||||
}
|
||||
private void DisableInput()
|
||||
{
|
||||
_isInputEnabled = false;
|
||||
OWInput.ChangeInputMode(InputMode.None);
|
||||
}
|
||||
|
||||
private void EnableInput()
|
||||
{
|
||||
_isInputEnabled = true;
|
||||
OWInput.ChangeInputMode(InputMode.Character);
|
||||
}
|
||||
private void EnableInput()
|
||||
{
|
||||
_isInputEnabled = true;
|
||||
OWInput.ChangeInputMode(InputMode.Character);
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
if (IsServer)
|
||||
{
|
||||
UpdateServer();
|
||||
}
|
||||
else if (IsLocalPlayer)
|
||||
{
|
||||
UpdateLocal();
|
||||
}
|
||||
}
|
||||
private void Update()
|
||||
{
|
||||
if (IsServer)
|
||||
{
|
||||
UpdateServer();
|
||||
}
|
||||
else if (IsLocalPlayer)
|
||||
{
|
||||
UpdateLocal();
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateServer()
|
||||
{
|
||||
if (_state != State.Loaded)
|
||||
{
|
||||
return;
|
||||
}
|
||||
private void UpdateServer()
|
||||
{
|
||||
if (_state != State.Loaded)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
_sendTimer += Time.unscaledDeltaTime;
|
||||
if (_sendTimer > 1)
|
||||
{
|
||||
SendServerTime();
|
||||
_sendTimer = 0;
|
||||
}
|
||||
}
|
||||
_sendTimer += Time.unscaledDeltaTime;
|
||||
if (_sendTimer > 1)
|
||||
{
|
||||
SendServerTime();
|
||||
_sendTimer = 0;
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateLocal()
|
||||
{
|
||||
_serverTime += Time.unscaledDeltaTime;
|
||||
private void UpdateLocal()
|
||||
{
|
||||
_serverTime += Time.unscaledDeltaTime;
|
||||
|
||||
if (_state == State.NotLoaded)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (_state == State.NotLoaded)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (_state == State.FastForwarding)
|
||||
{
|
||||
var diff = _serverTime - Time.timeSinceLevelLoad;
|
||||
Time.timeScale = Mathf.Lerp(MinFastForwardSpeed, MaxFastForwardSpeed, Mathf.Abs(diff) / MaxFastForwardDiff);
|
||||
if (_state == State.FastForwarding)
|
||||
{
|
||||
var diff = _serverTime - Time.timeSinceLevelLoad;
|
||||
Time.timeScale = Mathf.Lerp(MinFastForwardSpeed, MaxFastForwardSpeed, Mathf.Abs(diff) / MaxFastForwardDiff);
|
||||
|
||||
if (QSBSceneManager.CurrentScene == OWScene.SolarSystem && _isFirstFastForward)
|
||||
{
|
||||
var spawnPoint = Locator.GetPlayerBody().GetComponent<PlayerSpawner>().GetInitialSpawnPoint().transform;
|
||||
Locator.GetPlayerTransform().position = spawnPoint.position;
|
||||
Locator.GetPlayerTransform().rotation = spawnPoint.rotation;
|
||||
Physics.SyncTransforms();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Time.timeScale = _timeScale;
|
||||
}
|
||||
if (QSBSceneManager.CurrentScene == OWScene.SolarSystem && _isFirstFastForward)
|
||||
{
|
||||
var spawnPoint = Locator.GetPlayerBody().GetComponent<PlayerSpawner>().GetInitialSpawnPoint().transform;
|
||||
Locator.GetPlayerTransform().position = spawnPoint.position;
|
||||
Locator.GetPlayerTransform().rotation = spawnPoint.rotation;
|
||||
Physics.SyncTransforms();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Time.timeScale = _timeScale;
|
||||
}
|
||||
|
||||
var isDoneFastForwarding = _state == State.FastForwarding && Time.timeSinceLevelLoad >= _serverTime;
|
||||
var isDonePausing = _state == State.Pausing && Time.timeSinceLevelLoad < _serverTime;
|
||||
var isDoneFastForwarding = _state == State.FastForwarding && Time.timeSinceLevelLoad >= _serverTime;
|
||||
var isDonePausing = _state == State.Pausing && Time.timeSinceLevelLoad < _serverTime;
|
||||
|
||||
if (isDoneFastForwarding || isDonePausing)
|
||||
{
|
||||
ResetTimeScale();
|
||||
}
|
||||
if (isDoneFastForwarding || isDonePausing)
|
||||
{
|
||||
ResetTimeScale();
|
||||
}
|
||||
|
||||
if (!_isInputEnabled && OWInput.GetInputMode() != InputMode.None)
|
||||
{
|
||||
DisableInput();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!_isInputEnabled && OWInput.GetInputMode() != InputMode.None)
|
||||
{
|
||||
DisableInput();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -5,95 +5,95 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TransformSync
|
||||
{
|
||||
public class NomaiOrbTransformSync : QSBNetworkBehaviour
|
||||
{
|
||||
public NomaiInterfaceOrb AttachedOrb { get; private set; }
|
||||
public Transform OrbTransform { get; private set; }
|
||||
public class NomaiOrbTransformSync : QSBNetworkBehaviour
|
||||
{
|
||||
public NomaiInterfaceOrb AttachedOrb { get; private set; }
|
||||
public Transform OrbTransform { get; private set; }
|
||||
|
||||
private int Index => WorldRegistry.OrbSyncList.IndexOf(this);
|
||||
private int Index => WorldRegistry.OrbSyncList.IndexOf(this);
|
||||
|
||||
private const int MaxUpdatesBeforeDisable = 5;
|
||||
private const int MaxUpdatesBeforeDisable = 5;
|
||||
|
||||
private bool _isInitialized;
|
||||
private bool _isReady;
|
||||
private Transform _orbParent;
|
||||
private int _updateCount;
|
||||
private bool _isInitialized;
|
||||
private bool _isReady;
|
||||
private Transform _orbParent;
|
||||
private int _updateCount;
|
||||
|
||||
public override void OnStartClient()
|
||||
{
|
||||
DontDestroyOnLoad(this);
|
||||
WorldRegistry.OrbSyncList.Add(this);
|
||||
public override void OnStartClient()
|
||||
{
|
||||
DontDestroyOnLoad(this);
|
||||
WorldRegistry.OrbSyncList.Add(this);
|
||||
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSB.HasWokenUp, () => QSB.Helper.Events.Unity.FireOnNextUpdate(OnReady));
|
||||
}
|
||||
QSB.Helper.Events.Unity.RunWhen(() => QSB.HasWokenUp, () => QSB.Helper.Events.Unity.FireOnNextUpdate(OnReady));
|
||||
}
|
||||
|
||||
public override void OnStartAuthority()
|
||||
{
|
||||
DebugLog.DebugWrite("START AUTHORITY - has auth? : " + HasAuthority);
|
||||
}
|
||||
public override void OnStartAuthority()
|
||||
{
|
||||
DebugLog.DebugWrite("START AUTHORITY - has auth? : " + HasAuthority);
|
||||
}
|
||||
|
||||
public override void OnStopAuthority()
|
||||
{
|
||||
DebugLog.DebugWrite("END AUTHORITY - has auth? : " + HasAuthority);
|
||||
}
|
||||
public override void OnStopAuthority()
|
||||
{
|
||||
DebugLog.DebugWrite("END AUTHORITY - has auth? : " + HasAuthority);
|
||||
}
|
||||
|
||||
private void OnReady()
|
||||
{
|
||||
AttachedOrb = WorldRegistry.OldOrbList[Index];
|
||||
_isReady = true;
|
||||
}
|
||||
private void OnReady()
|
||||
{
|
||||
AttachedOrb = WorldRegistry.OldOrbList[Index];
|
||||
_isReady = true;
|
||||
}
|
||||
|
||||
private void OnDestroy()
|
||||
{
|
||||
WorldRegistry.OrbSyncList.Remove(this);
|
||||
}
|
||||
private void OnDestroy()
|
||||
{
|
||||
WorldRegistry.OrbSyncList.Remove(this);
|
||||
}
|
||||
|
||||
protected void Init()
|
||||
{
|
||||
OrbTransform = AttachedOrb.transform;
|
||||
_orbParent = AttachedOrb.GetAttachedOWRigidbody().GetOrigParent();
|
||||
_isInitialized = true;
|
||||
}
|
||||
protected void Init()
|
||||
{
|
||||
OrbTransform = AttachedOrb.transform;
|
||||
_orbParent = AttachedOrb.GetAttachedOWRigidbody().GetOrigParent();
|
||||
_isInitialized = true;
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
if (!_isInitialized && _isReady)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else if (_isInitialized && !_isReady)
|
||||
{
|
||||
_isInitialized = false;
|
||||
}
|
||||
private void Update()
|
||||
{
|
||||
if (!_isInitialized && _isReady)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else if (_isInitialized && !_isReady)
|
||||
{
|
||||
_isInitialized = false;
|
||||
}
|
||||
|
||||
if (OrbTransform == null || !_isInitialized)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (OrbTransform == null || !_isInitialized)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
UpdateTransform();
|
||||
}
|
||||
UpdateTransform();
|
||||
}
|
||||
|
||||
protected virtual void UpdateTransform()
|
||||
{
|
||||
if (HasAuthority)
|
||||
{
|
||||
transform.position = _orbParent.InverseTransformPoint(OrbTransform.position);
|
||||
transform.rotation = _orbParent.InverseTransformRotation(OrbTransform.rotation);
|
||||
return;
|
||||
}
|
||||
OrbTransform.position = _orbParent.TransformPoint(transform.position);
|
||||
OrbTransform.rotation = _orbParent.InverseTransformRotation(OrbTransform.rotation);
|
||||
protected virtual void UpdateTransform()
|
||||
{
|
||||
if (HasAuthority)
|
||||
{
|
||||
transform.position = _orbParent.InverseTransformPoint(OrbTransform.position);
|
||||
transform.rotation = _orbParent.InverseTransformRotation(OrbTransform.rotation);
|
||||
return;
|
||||
}
|
||||
OrbTransform.position = _orbParent.TransformPoint(transform.position);
|
||||
OrbTransform.rotation = _orbParent.InverseTransformRotation(OrbTransform.rotation);
|
||||
|
||||
if (transform.localPosition == Vector3.zero)
|
||||
{
|
||||
_updateCount++;
|
||||
}
|
||||
if (_updateCount >= MaxUpdatesBeforeDisable)
|
||||
{
|
||||
enabled = false;
|
||||
_updateCount = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (transform.localPosition == Vector3.zero)
|
||||
{
|
||||
_updateCount++;
|
||||
}
|
||||
if (_updateCount >= MaxUpdatesBeforeDisable)
|
||||
{
|
||||
enabled = false;
|
||||
_updateCount = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -7,45 +7,45 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TransformSync
|
||||
{
|
||||
public class PlayerCameraSync : TransformSync
|
||||
{
|
||||
public static PlayerCameraSync LocalInstance { get; private set; }
|
||||
public class PlayerCameraSync : TransformSync
|
||||
{
|
||||
public static PlayerCameraSync LocalInstance { get; private set; }
|
||||
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
var body = Locator.GetPlayerCamera().gameObject.transform;
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
var body = Locator.GetPlayerCamera().gameObject.transform;
|
||||
|
||||
Player.Camera = body.gameObject;
|
||||
Player.Camera = body.gameObject;
|
||||
|
||||
Player.IsReady = true;
|
||||
GlobalMessenger<bool>.FireEvent(EventNames.QSBPlayerReady, true);
|
||||
DebugLog.DebugWrite("PlayerCameraSync init done - Request state!");
|
||||
GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest);
|
||||
Player.IsReady = true;
|
||||
GlobalMessenger<bool>.FireEvent(EventNames.QSBPlayerReady, true);
|
||||
DebugLog.DebugWrite("PlayerCameraSync init done - Request state!");
|
||||
GlobalMessenger.FireEvent(EventNames.QSBPlayerStatesRequest);
|
||||
|
||||
return body;
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var body = new GameObject("RemotePlayerCamera");
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var body = new GameObject("RemotePlayerCamera");
|
||||
|
||||
PlayerToolsManager.Init(body.transform);
|
||||
PlayerToolsManager.Init(body.transform);
|
||||
|
||||
Player.Camera = body;
|
||||
Player.Camera = body;
|
||||
|
||||
return body.transform;
|
||||
}
|
||||
return body.transform;
|
||||
}
|
||||
|
||||
public override bool IsReady => Locator.GetPlayerTransform() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
public override bool IsReady => Locator.GetPlayerTransform() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
}
|
||||
|
@ -6,96 +6,96 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TransformSync
|
||||
{
|
||||
public class PlayerProbeSync : TransformSync
|
||||
{
|
||||
public static PlayerProbeSync LocalInstance { get; private set; }
|
||||
public class PlayerProbeSync : TransformSync
|
||||
{
|
||||
public static PlayerProbeSync LocalInstance { get; private set; }
|
||||
|
||||
private Transform _disabledSocket;
|
||||
private Transform _disabledSocket;
|
||||
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
|
||||
private Transform GetProbe()
|
||||
{
|
||||
return Locator.GetProbe().transform.Find("CameraPivot").Find("Geometry");
|
||||
}
|
||||
private Transform GetProbe()
|
||||
{
|
||||
return Locator.GetProbe().transform.Find("CameraPivot").Find("Geometry");
|
||||
}
|
||||
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
var body = GetProbe();
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
var body = GetProbe();
|
||||
|
||||
SetSocket(Player.Camera.transform);
|
||||
Player.ProbeBody = body.gameObject;
|
||||
SetSocket(Player.Camera.transform);
|
||||
Player.ProbeBody = body.gameObject;
|
||||
|
||||
return body;
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var probe = GetProbe();
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var probe = GetProbe();
|
||||
|
||||
if (probe == null)
|
||||
{
|
||||
DebugLog.ToConsole("Error - Probe is null!", MessageType.Error);
|
||||
return default;
|
||||
}
|
||||
if (probe == null)
|
||||
{
|
||||
DebugLog.ToConsole("Error - Probe is null!", MessageType.Error);
|
||||
return default;
|
||||
}
|
||||
|
||||
var body = probe.InstantiateInactive();
|
||||
body.name = "RemoteProbeTransform";
|
||||
var body = probe.InstantiateInactive();
|
||||
body.name = "RemoteProbeTransform";
|
||||
|
||||
Destroy(body.GetComponentInChildren<ProbeAnimatorController>());
|
||||
Destroy(body.GetComponentInChildren<ProbeAnimatorController>());
|
||||
|
||||
PlayerToolsManager.CreateProbe(body, Player);
|
||||
PlayerToolsManager.CreateProbe(body, Player);
|
||||
|
||||
QSB.Helper.Events.Unity.RunWhen(() => (Player.ProbeLauncher != null), () => SetSocket(Player.ProbeLauncher.ToolGameObject.transform));
|
||||
Player.ProbeBody = body.gameObject;
|
||||
QSB.Helper.Events.Unity.RunWhen(() => (Player.ProbeLauncher != null), () => SetSocket(Player.ProbeLauncher.ToolGameObject.transform));
|
||||
Player.ProbeBody = body.gameObject;
|
||||
|
||||
return body;
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
private void SetSocket(Transform socket)
|
||||
{
|
||||
DebugLog.DebugWrite($"Setting DisabledSocket for {AttachedNetId} to {socket.name}");
|
||||
_disabledSocket = socket;
|
||||
}
|
||||
private void SetSocket(Transform socket)
|
||||
{
|
||||
DebugLog.DebugWrite($"Setting DisabledSocket for {AttachedNetId} to {socket.name}");
|
||||
_disabledSocket = socket;
|
||||
}
|
||||
|
||||
protected override void UpdateTransform()
|
||||
{
|
||||
base.UpdateTransform();
|
||||
if (Player == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Player is null for {AttachedNetId}!", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (_disabledSocket == null)
|
||||
{
|
||||
DebugLog.ToConsole($"DisabledSocket is null for {AttachedNetId}! (ProbeLauncher null? : {Player.ProbeLauncher == null})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (Player.GetState(State.ProbeActive) || ReferenceSector?.Sector == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (HasAuthority)
|
||||
{
|
||||
transform.position = ReferenceSector.Transform.InverseTransformPoint(_disabledSocket.position);
|
||||
return;
|
||||
}
|
||||
if (SyncedTransform.position == Vector3.zero)
|
||||
{
|
||||
return;
|
||||
}
|
||||
SyncedTransform.localPosition = ReferenceSector.Transform.InverseTransformPoint(_disabledSocket.position);
|
||||
}
|
||||
protected override void UpdateTransform()
|
||||
{
|
||||
base.UpdateTransform();
|
||||
if (Player == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Player is null for {AttachedNetId}!", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (_disabledSocket == null)
|
||||
{
|
||||
DebugLog.ToConsole($"DisabledSocket is null for {AttachedNetId}! (ProbeLauncher null? : {Player.ProbeLauncher == null})", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
if (Player.GetState(State.ProbeActive) || ReferenceSector?.Sector == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (HasAuthority)
|
||||
{
|
||||
transform.position = ReferenceSector.Transform.InverseTransformPoint(_disabledSocket.position);
|
||||
return;
|
||||
}
|
||||
if (SyncedTransform.position == Vector3.zero)
|
||||
{
|
||||
return;
|
||||
}
|
||||
SyncedTransform.localPosition = ReferenceSector.Transform.InverseTransformPoint(_disabledSocket.position);
|
||||
}
|
||||
|
||||
public override bool IsReady => Locator.GetProbe() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& Player.IsReady
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
public override bool IsReady => Locator.GetProbe() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& Player.IsReady
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
}
|
||||
|
@ -7,59 +7,59 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TransformSync
|
||||
{
|
||||
public class PlayerTransformSync : TransformSync
|
||||
{
|
||||
public static PlayerTransformSync LocalInstance { get; private set; }
|
||||
public class PlayerTransformSync : TransformSync
|
||||
{
|
||||
public static PlayerTransformSync LocalInstance { get; private set; }
|
||||
|
||||
static PlayerTransformSync()
|
||||
{
|
||||
DebugLog.DebugWrite("Constructor", MessageType.Info);
|
||||
AnimControllerPatch.Init();
|
||||
}
|
||||
static PlayerTransformSync()
|
||||
{
|
||||
DebugLog.DebugWrite("Constructor", MessageType.Info);
|
||||
AnimControllerPatch.Init();
|
||||
}
|
||||
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
|
||||
private Transform GetPlayerModel()
|
||||
{
|
||||
return Locator.GetPlayerTransform().Find("Traveller_HEA_Player_v2");
|
||||
}
|
||||
private Transform GetPlayerModel()
|
||||
{
|
||||
return Locator.GetPlayerTransform().Find("Traveller_HEA_Player_v2");
|
||||
}
|
||||
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
var body = GetPlayerModel();
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
var body = GetPlayerModel();
|
||||
|
||||
GetComponent<AnimationSync>().InitLocal(body);
|
||||
GetComponent<InstrumentsManager>().InitLocal(body);
|
||||
GetComponent<AnimationSync>().InitLocal(body);
|
||||
GetComponent<InstrumentsManager>().InitLocal(body);
|
||||
|
||||
Player.Body = body.gameObject;
|
||||
Player.Body = body.gameObject;
|
||||
|
||||
return body;
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var body = Instantiate(GetPlayerModel());
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var body = Instantiate(GetPlayerModel());
|
||||
|
||||
GetComponent<AnimationSync>().InitRemote(body);
|
||||
GetComponent<InstrumentsManager>().InitRemote(body);
|
||||
GetComponent<AnimationSync>().InitRemote(body);
|
||||
GetComponent<InstrumentsManager>().InitRemote(body);
|
||||
|
||||
var marker = body.gameObject.AddComponent<PlayerHUDMarker>();
|
||||
marker.Init(Player);
|
||||
var marker = body.gameObject.AddComponent<PlayerHUDMarker>();
|
||||
marker.Init(Player);
|
||||
|
||||
Player.Body = body.gameObject;
|
||||
Player.Body = body.gameObject;
|
||||
|
||||
return body;
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
public override bool IsReady => Locator.GetPlayerTransform() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& Player.IsReady
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
public override bool IsReady => Locator.GetPlayerTransform() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& Player.IsReady
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
}
|
||||
|
@ -5,59 +5,59 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TransformSync
|
||||
{
|
||||
public class ShipTransformSync : TransformSync
|
||||
{
|
||||
public static ShipTransformSync LocalInstance { get; private set; }
|
||||
public class ShipTransformSync : TransformSync
|
||||
{
|
||||
public static ShipTransformSync LocalInstance { get; private set; }
|
||||
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
public override void OnStartLocalPlayer()
|
||||
{
|
||||
DebugLog.DebugWrite("OnStartLocalPlayer", MessageType.Info);
|
||||
LocalInstance = this;
|
||||
}
|
||||
|
||||
private Transform GetShipModel()
|
||||
{
|
||||
return Locator.GetShipTransform();
|
||||
}
|
||||
private Transform GetShipModel()
|
||||
{
|
||||
return Locator.GetShipTransform();
|
||||
}
|
||||
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
return GetShipModel().Find("Module_Cockpit/Geo_Cockpit/Cockpit_Geometry/Cockpit_Exterior");
|
||||
}
|
||||
protected override Transform InitLocalTransform()
|
||||
{
|
||||
return GetShipModel().Find("Module_Cockpit/Geo_Cockpit/Cockpit_Geometry/Cockpit_Exterior");
|
||||
}
|
||||
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var shipModel = GetShipModel();
|
||||
protected override Transform InitRemoteTransform()
|
||||
{
|
||||
var shipModel = GetShipModel();
|
||||
|
||||
var remoteTransform = new GameObject("RemoteShipTransform").transform;
|
||||
var remoteTransform = new GameObject("RemoteShipTransform").transform;
|
||||
|
||||
Instantiate(shipModel.Find("Module_Cockpit/Geo_Cockpit/Cockpit_Geometry/Cockpit_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Cabin/Geo_Cabin/Cabin_Geometry/Cabin_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Cabin/Geo_Cabin/Cabin_Tech/Cabin_Tech_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Supplies/Geo_Supplies/Supplies_Geometry/Supplies_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Engine/Geo_Engine/Engine_Geometry/Engine_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Cockpit/Geo_Cockpit/Cockpit_Geometry/Cockpit_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Cabin/Geo_Cabin/Cabin_Geometry/Cabin_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Cabin/Geo_Cabin/Cabin_Tech/Cabin_Tech_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Supplies/Geo_Supplies/Supplies_Geometry/Supplies_Exterior"), remoteTransform);
|
||||
Instantiate(shipModel.Find("Module_Engine/Geo_Engine/Engine_Geometry/Engine_Exterior"), remoteTransform);
|
||||
|
||||
var landingGearFront = Instantiate(shipModel.Find("Module_LandingGear/LandingGear_Front/Geo_LandingGear_Front"), remoteTransform);
|
||||
var landingGearLeft = Instantiate(shipModel.Find("Module_LandingGear/LandingGear_Left/Geo_LandingGear_Left"), remoteTransform);
|
||||
var landingGearRight = Instantiate(shipModel.Find("Module_LandingGear/LandingGear_Right/Geo_LandingGear_Right"), remoteTransform);
|
||||
var landingGearFront = Instantiate(shipModel.Find("Module_LandingGear/LandingGear_Front/Geo_LandingGear_Front"), remoteTransform);
|
||||
var landingGearLeft = Instantiate(shipModel.Find("Module_LandingGear/LandingGear_Left/Geo_LandingGear_Left"), remoteTransform);
|
||||
var landingGearRight = Instantiate(shipModel.Find("Module_LandingGear/LandingGear_Right/Geo_LandingGear_Right"), remoteTransform);
|
||||
|
||||
Destroy(landingGearFront.Find("LandingGear_FrontCollision").gameObject);
|
||||
Destroy(landingGearLeft.Find("LandingGear_LeftCollision").gameObject);
|
||||
Destroy(landingGearRight.Find("LandingGear_RightCollision").gameObject);
|
||||
Destroy(landingGearFront.Find("LandingGear_FrontCollision").gameObject);
|
||||
Destroy(landingGearLeft.Find("LandingGear_LeftCollision").gameObject);
|
||||
Destroy(landingGearRight.Find("LandingGear_RightCollision").gameObject);
|
||||
|
||||
landingGearFront.localPosition
|
||||
= landingGearLeft.localPosition
|
||||
= landingGearRight.localPosition
|
||||
+= Vector3.up * 3.762f;
|
||||
landingGearFront.localPosition
|
||||
= landingGearLeft.localPosition
|
||||
= landingGearRight.localPosition
|
||||
+= Vector3.up * 3.762f;
|
||||
|
||||
return remoteTransform;
|
||||
}
|
||||
return remoteTransform;
|
||||
}
|
||||
|
||||
public override bool IsReady => GetShipModel() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& Player.IsReady
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
public override bool IsReady => GetShipModel() != null
|
||||
&& Player != null
|
||||
&& QSBPlayerManager.PlayerExists(Player.PlayerId)
|
||||
&& Player.IsReady
|
||||
&& NetId.Value != uint.MaxValue
|
||||
&& NetId.Value != 0U;
|
||||
}
|
||||
}
|
||||
|
@ -6,131 +6,131 @@ using UnityEngine;
|
||||
|
||||
namespace QSB.TransformSync
|
||||
{
|
||||
public abstract class TransformSync : PlayerSyncObject
|
||||
{
|
||||
public abstract bool IsReady { get; }
|
||||
protected abstract Transform InitLocalTransform();
|
||||
protected abstract Transform InitRemoteTransform();
|
||||
public abstract class TransformSync : PlayerSyncObject
|
||||
{
|
||||
public abstract bool IsReady { get; }
|
||||
protected abstract Transform InitLocalTransform();
|
||||
protected abstract Transform InitRemoteTransform();
|
||||
|
||||
public Transform SyncedTransform { get; private set; }
|
||||
public QSBSector ReferenceSector { get; set; }
|
||||
public Transform SyncedTransform { get; private set; }
|
||||
public QSBSector ReferenceSector { get; set; }
|
||||
|
||||
private const float SmoothTime = 0.1f;
|
||||
private bool _isInitialized;
|
||||
private Vector3 _positionSmoothVelocity;
|
||||
private Quaternion _rotationSmoothVelocity;
|
||||
private bool _isVisible;
|
||||
private const float SmoothTime = 0.1f;
|
||||
private bool _isInitialized;
|
||||
private Vector3 _positionSmoothVelocity;
|
||||
private Quaternion _rotationSmoothVelocity;
|
||||
private bool _isVisible;
|
||||
|
||||
protected virtual void Awake()
|
||||
{
|
||||
DebugLog.DebugWrite($"Awake of {GetType().Name}", MessageType.Info);
|
||||
QSBPlayerManager.PlayerSyncObjects.Add(this);
|
||||
DontDestroyOnLoad(gameObject);
|
||||
QSBSceneManager.OnSceneLoaded += OnSceneLoaded;
|
||||
}
|
||||
protected virtual void Awake()
|
||||
{
|
||||
DebugLog.DebugWrite($"Awake of {GetType().Name}", MessageType.Info);
|
||||
QSBPlayerManager.PlayerSyncObjects.Add(this);
|
||||
DontDestroyOnLoad(gameObject);
|
||||
QSBSceneManager.OnSceneLoaded += OnSceneLoaded;
|
||||
}
|
||||
|
||||
protected virtual void OnDestroy()
|
||||
{
|
||||
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
|
||||
}
|
||||
protected virtual void OnDestroy()
|
||||
{
|
||||
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
|
||||
}
|
||||
|
||||
private void OnSceneLoaded(OWScene scene, bool isInUniverse)
|
||||
{
|
||||
_isInitialized = false;
|
||||
}
|
||||
private void OnSceneLoaded(OWScene scene, bool isInUniverse)
|
||||
{
|
||||
_isInitialized = false;
|
||||
}
|
||||
|
||||
protected void Init()
|
||||
{
|
||||
DebugLog.DebugWrite($"Init of {AttachedNetId} ({Player.PlayerId}.{GetType().Name})");
|
||||
SyncedTransform = HasAuthority ? InitLocalTransform() : InitRemoteTransform();
|
||||
_isInitialized = true;
|
||||
_isVisible = true;
|
||||
}
|
||||
protected void Init()
|
||||
{
|
||||
DebugLog.DebugWrite($"Init of {AttachedNetId} ({Player.PlayerId}.{GetType().Name})");
|
||||
SyncedTransform = HasAuthority ? InitLocalTransform() : InitRemoteTransform();
|
||||
_isInitialized = true;
|
||||
_isVisible = true;
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
if (!_isInitialized && IsReady)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else if (_isInitialized && !IsReady)
|
||||
{
|
||||
_isInitialized = false;
|
||||
return;
|
||||
}
|
||||
private void Update()
|
||||
{
|
||||
if (!_isInitialized && IsReady)
|
||||
{
|
||||
Init();
|
||||
}
|
||||
else if (_isInitialized && !IsReady)
|
||||
{
|
||||
_isInitialized = false;
|
||||
return;
|
||||
}
|
||||
|
||||
if (!_isInitialized)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (!_isInitialized)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (SyncedTransform == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - SyncedTransform {Player.PlayerId}.{GetType().Name} is null.", MessageType.Warning);
|
||||
return;
|
||||
}
|
||||
if (SyncedTransform == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Warning - SyncedTransform {Player.PlayerId}.{GetType().Name} is null.", MessageType.Warning);
|
||||
return;
|
||||
}
|
||||
|
||||
UpdateTransform();
|
||||
}
|
||||
UpdateTransform();
|
||||
}
|
||||
|
||||
protected virtual void UpdateTransform()
|
||||
{
|
||||
if (HasAuthority) // If this script is attached to the client's own body on the client's side.
|
||||
{
|
||||
if (ReferenceSector == null || ReferenceSector.Sector == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - ReferenceSector has null value for {Player.PlayerId}.{GetType().Name}", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
transform.position = ReferenceSector.Transform.InverseTransformPoint(SyncedTransform.position);
|
||||
transform.rotation = ReferenceSector.Transform.InverseTransformRotation(SyncedTransform.rotation);
|
||||
return;
|
||||
}
|
||||
protected virtual void UpdateTransform()
|
||||
{
|
||||
if (HasAuthority) // If this script is attached to the client's own body on the client's side.
|
||||
{
|
||||
if (ReferenceSector == null || ReferenceSector.Sector == null)
|
||||
{
|
||||
DebugLog.ToConsole($"Error - ReferenceSector has null value for {Player.PlayerId}.{GetType().Name}", MessageType.Error);
|
||||
return;
|
||||
}
|
||||
transform.position = ReferenceSector.Transform.InverseTransformPoint(SyncedTransform.position);
|
||||
transform.rotation = ReferenceSector.Transform.InverseTransformRotation(SyncedTransform.rotation);
|
||||
return;
|
||||
}
|
||||
|
||||
// If this script is attached to any other body, eg the representations of other players
|
||||
if (SyncedTransform.position == Vector3.zero)
|
||||
{
|
||||
Hide();
|
||||
}
|
||||
else
|
||||
{
|
||||
Show();
|
||||
}
|
||||
// If this script is attached to any other body, eg the representations of other players
|
||||
if (SyncedTransform.position == Vector3.zero)
|
||||
{
|
||||
Hide();
|
||||
}
|
||||
else
|
||||
{
|
||||
Show();
|
||||
}
|
||||
|
||||
SyncedTransform.localPosition = Vector3.SmoothDamp(SyncedTransform.localPosition, transform.position, ref _positionSmoothVelocity, SmoothTime);
|
||||
SyncedTransform.localRotation = QuaternionHelper.SmoothDamp(SyncedTransform.localRotation, transform.rotation, ref _rotationSmoothVelocity, Time.deltaTime);
|
||||
}
|
||||
SyncedTransform.localPosition = Vector3.SmoothDamp(SyncedTransform.localPosition, transform.position, ref _positionSmoothVelocity, SmoothTime);
|
||||
SyncedTransform.localRotation = QuaternionHelper.SmoothDamp(SyncedTransform.localRotation, transform.rotation, ref _rotationSmoothVelocity, Time.deltaTime);
|
||||
}
|
||||
|
||||
public void SetReferenceSector(QSBSector sector)
|
||||
{
|
||||
DebugLog.DebugWrite($"Setting {Player.PlayerId}.{GetType().Name} to {sector.Name}", MessageType.Info);
|
||||
_positionSmoothVelocity = Vector3.zero;
|
||||
ReferenceSector = sector;
|
||||
if (!HasAuthority)
|
||||
{
|
||||
SyncedTransform.SetParent(sector.Transform, true);
|
||||
transform.position = sector.Transform.InverseTransformPoint(SyncedTransform.position);
|
||||
transform.rotation = sector.Transform.InverseTransformRotation(SyncedTransform.rotation);
|
||||
}
|
||||
}
|
||||
public void SetReferenceSector(QSBSector sector)
|
||||
{
|
||||
DebugLog.DebugWrite($"Setting {Player.PlayerId}.{GetType().Name} to {sector.Name}", MessageType.Info);
|
||||
_positionSmoothVelocity = Vector3.zero;
|
||||
ReferenceSector = sector;
|
||||
if (!HasAuthority)
|
||||
{
|
||||
SyncedTransform.SetParent(sector.Transform, true);
|
||||
transform.position = sector.Transform.InverseTransformPoint(SyncedTransform.position);
|
||||
transform.rotation = sector.Transform.InverseTransformRotation(SyncedTransform.rotation);
|
||||
}
|
||||
}
|
||||
|
||||
private void Show()
|
||||
{
|
||||
if (!_isVisible)
|
||||
{
|
||||
SyncedTransform.gameObject.Show();
|
||||
_isVisible = true;
|
||||
}
|
||||
}
|
||||
private void Show()
|
||||
{
|
||||
if (!_isVisible)
|
||||
{
|
||||
SyncedTransform.gameObject.Show();
|
||||
_isVisible = true;
|
||||
}
|
||||
}
|
||||
|
||||
private void Hide()
|
||||
{
|
||||
if (_isVisible)
|
||||
{
|
||||
SyncedTransform.gameObject.Hide();
|
||||
_isVisible = false;
|
||||
}
|
||||
}
|
||||
private void Hide()
|
||||
{
|
||||
if (_isVisible)
|
||||
{
|
||||
SyncedTransform.gameObject.Hide();
|
||||
_isVisible = false;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
@ -9,75 +9,75 @@ using System.Reflection;
|
||||
|
||||
namespace QSB.WorldSync
|
||||
{
|
||||
public static class WorldRegistry
|
||||
{
|
||||
private static readonly List<WorldObject> WorldObjects = new List<WorldObject>();
|
||||
public static List<NomaiOrbTransformSync> OrbSyncList = new List<NomaiOrbTransformSync>();
|
||||
public static List<NomaiInterfaceOrb> OldOrbList = new List<NomaiInterfaceOrb>();
|
||||
public static List<CharacterDialogueTree> OldDialogueTrees = new List<CharacterDialogueTree>();
|
||||
public static class WorldRegistry
|
||||
{
|
||||
private static readonly List<WorldObject> WorldObjects = new List<WorldObject>();
|
||||
public static List<NomaiOrbTransformSync> OrbSyncList = new List<NomaiOrbTransformSync>();
|
||||
public static List<NomaiInterfaceOrb> OldOrbList = new List<NomaiInterfaceOrb>();
|
||||
public static List<CharacterDialogueTree> OldDialogueTrees = new List<CharacterDialogueTree>();
|
||||
|
||||
public static void AddObject(WorldObject worldObject)
|
||||
{
|
||||
if (WorldObjects.Contains(worldObject))
|
||||
{
|
||||
return;
|
||||
}
|
||||
WorldObjects.Add(worldObject);
|
||||
}
|
||||
public static void AddObject(WorldObject worldObject)
|
||||
{
|
||||
if (WorldObjects.Contains(worldObject))
|
||||
{
|
||||
return;
|
||||
}
|
||||
WorldObjects.Add(worldObject);
|
||||
}
|
||||
|
||||
public static IEnumerable<T> GetObjects<T>()
|
||||
{
|
||||
return WorldObjects.OfType<T>();
|
||||
}
|
||||
public static IEnumerable<T> GetObjects<T>()
|
||||
{
|
||||
return WorldObjects.OfType<T>();
|
||||
}
|
||||
|
||||
public static T GetObject<T>(int id) where T : WorldObject
|
||||
{
|
||||
return GetObjects<T>().FirstOrDefault(x => x.ObjectId == id);
|
||||
}
|
||||
public static T GetObject<T>(int id) where T : WorldObject
|
||||
{
|
||||
return GetObjects<T>().FirstOrDefault(x => x.ObjectId == id);
|
||||
}
|
||||
|
||||
public static void RemoveObjects<T>() where T : WorldObject
|
||||
{
|
||||
WorldObjects.RemoveAll(x => x.GetType() == typeof(T));
|
||||
}
|
||||
public static void RemoveObjects<T>() where T : WorldObject
|
||||
{
|
||||
WorldObjects.RemoveAll(x => x.GetType() == typeof(T));
|
||||
}
|
||||
|
||||
public static void HandleSlotStateChange(NomaiInterfaceSlot slot, NomaiInterfaceOrb affectingOrb, bool state)
|
||||
{
|
||||
QSBOrbSlot qsbSlot = null;
|
||||
NomaiOrbTransformSync orbSync = null;
|
||||
var slotList = GetObjects<QSBOrbSlot>();
|
||||
if (slotList.Count() == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
try
|
||||
{
|
||||
qsbSlot = slotList.First(x => x.InterfaceSlot == slot);
|
||||
orbSync = OrbSyncList.First(x => x.AttachedOrb == affectingOrb);
|
||||
if (orbSync.HasAuthority)
|
||||
{
|
||||
qsbSlot.HandleEvent(state);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
DebugLog.DebugWrite("Error - Exception when handling slot state change."
|
||||
+ Environment.NewLine + $"Slot name {slot.name} to {state}"
|
||||
+ Environment.NewLine + $"SlotList count : {slotList?.Count()}"
|
||||
+ Environment.NewLine + $"QSBOrbSlot null? : {qsbSlot == null}"
|
||||
+ Environment.NewLine + $"NomaiOrbTransformSync null? : {orbSync == null}", MessageType.Error);
|
||||
}
|
||||
}
|
||||
public static void HandleSlotStateChange(NomaiInterfaceSlot slot, NomaiInterfaceOrb affectingOrb, bool state)
|
||||
{
|
||||
QSBOrbSlot qsbSlot = null;
|
||||
NomaiOrbTransformSync orbSync = null;
|
||||
var slotList = GetObjects<QSBOrbSlot>();
|
||||
if (slotList.Count() == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
try
|
||||
{
|
||||
qsbSlot = slotList.First(x => x.InterfaceSlot == slot);
|
||||
orbSync = OrbSyncList.First(x => x.AttachedOrb == affectingOrb);
|
||||
if (orbSync.HasAuthority)
|
||||
{
|
||||
qsbSlot.HandleEvent(state);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
DebugLog.DebugWrite("Error - Exception when handling slot state change."
|
||||
+ Environment.NewLine + $"Slot name {slot.name} to {state}"
|
||||
+ Environment.NewLine + $"SlotList count : {slotList?.Count()}"
|
||||
+ Environment.NewLine + $"QSBOrbSlot null? : {qsbSlot == null}"
|
||||
+ Environment.NewLine + $"NomaiOrbTransformSync null? : {orbSync == null}", MessageType.Error);
|
||||
}
|
||||
}
|
||||
|
||||
public static void RaiseEvent(object instance, string eventName)
|
||||
{
|
||||
if (!(instance.GetType()
|
||||
.GetField(eventName, BindingFlags.Instance | BindingFlags.NonPublic)?
|
||||
.GetValue(instance) is MulticastDelegate multiDelegate))
|
||||
{
|
||||
return;
|
||||
}
|
||||
var delegateList = multiDelegate.GetInvocationList().ToList();
|
||||
delegateList.ForEach(x => x.DynamicInvoke(instance));
|
||||
}
|
||||
}
|
||||
public static void RaiseEvent(object instance, string eventName)
|
||||
{
|
||||
if (!(instance.GetType()
|
||||
.GetField(eventName, BindingFlags.Instance | BindingFlags.NonPublic)?
|
||||
.GetValue(instance) is MulticastDelegate multiDelegate))
|
||||
{
|
||||
return;
|
||||
}
|
||||
var delegateList = multiDelegate.GetInvocationList().ToList();
|
||||
delegateList.ForEach(x => x.DynamicInvoke(instance));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user