Merge pull request #294 from misternebula/so-many-fixes

So many fixes
This commit is contained in:
_nebula 2021-05-26 20:44:45 +01:00 committed by GitHub
commit ef8b23935f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
22 changed files with 477 additions and 94 deletions

View File

@ -21,11 +21,11 @@ namespace QSB.Animation.Player.Events
public override void OnReceiveRemote(bool server, AnimationTriggerMessage message) public override void OnReceiveRemote(bool server, AnimationTriggerMessage message)
{ {
if (!QSBCore.WorldObjectsReady) var animationSync = QSBPlayerManager.GetSyncObject<AnimationSync>(message.AttachedNetId);
if (!QSBCore.WorldObjectsReady || animationSync != null)
{ {
return; return;
} }
var animationSync = QSBPlayerManager.GetSyncObject<AnimationSync>(message.AttachedNetId);
animationSync.VisibleAnimator.SetTrigger(message.Name); animationSync.VisibleAnimator.SetTrigger(message.Name);
} }
} }

View File

@ -1,9 +1,11 @@
using Harmony; using Harmony;
using QSB.Events; using QSB.Events;
using QSB.Patches; using QSB.Patches;
using QSB.Utility;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Reflection.Emit; using System.Reflection.Emit;
using UnityEngine;
namespace QSB.DeathSync.Patches namespace QSB.DeathSync.Patches
{ {
@ -20,6 +22,8 @@ namespace QSB.DeathSync.Patches
QSBCore.HarmonyHelper.EmptyMethod<ShipEjectionSystem>("OnPressInteract"); QSBCore.HarmonyHelper.EmptyMethod<ShipEjectionSystem>("OnPressInteract");
QSBCore.HarmonyHelper.AddPostfix<ShipDamageController>("Awake", typeof(DeathPatches), nameof(DamageController_Exploded)); QSBCore.HarmonyHelper.AddPostfix<ShipDamageController>("Awake", typeof(DeathPatches), nameof(DamageController_Exploded));
QSBCore.HarmonyHelper.AddPrefix<DestructionVolume>("VanishShip", typeof(DeathPatches), nameof(DestructionVolume_VanishShip)); QSBCore.HarmonyHelper.AddPrefix<DestructionVolume>("VanishShip", typeof(DeathPatches), nameof(DestructionVolume_VanishShip));
QSBCore.HarmonyHelper.AddPrefix<HighSpeedImpactSensor>("FixedUpdate", typeof(DeathPatches), nameof(HighSpeedImpactSensor_FixedUpdate));
QSBCore.HarmonyHelper.AddPrefix<PlayerResources>("OnImpact", typeof(DeathPatches), nameof(PlayerResources_OnImpact));
} }
public override void DoUnpatches() public override void DoUnpatches()
@ -30,6 +34,150 @@ namespace QSB.DeathSync.Patches
QSBCore.HarmonyHelper.Unpatch<ShipEjectionSystem>("OnPressInteract"); QSBCore.HarmonyHelper.Unpatch<ShipEjectionSystem>("OnPressInteract");
QSBCore.HarmonyHelper.Unpatch<ShipDamageController>("Awake"); QSBCore.HarmonyHelper.Unpatch<ShipDamageController>("Awake");
QSBCore.HarmonyHelper.Unpatch<DestructionVolume>("VanishShip"); QSBCore.HarmonyHelper.Unpatch<DestructionVolume>("VanishShip");
QSBCore.HarmonyHelper.Unpatch<HighSpeedImpactSensor>("FixedUpdate");
QSBCore.HarmonyHelper.Unpatch<PlayerResources>("OnImpact");
}
public static bool PlayerResources_OnImpact(ImpactData impact, PlayerResources __instance, float ____currentHealth)
{
if (PlayerState.IsInsideShip())
{
return false;
}
var speed = Mathf.Clamp01((impact.speed - __instance.GetMinImpactSpeed()) / (__instance.GetMaxImpactSpeed() - __instance.GetMinImpactSpeed()));
var tookDamage = __instance.ApplyInstantDamage(100f * speed, InstantDamageType.Impact);
if (tookDamage && ____currentHealth <= 0f && !PlayerState.IsDead())
{
Locator.GetDeathManager().SetImpactDeathSpeed(impact.speed);
Locator.GetDeathManager().KillPlayer(DeathType.Impact);
DebugLog.DebugWrite(string.Concat(new object[]
{
"Player killed from impact with ",
impact.otherCollider,
" attached to ",
impact.otherCollider.attachedRigidbody.gameObject.name
}));
}
return false;
}
public static bool HighSpeedImpactSensor_FixedUpdate(
HighSpeedImpactSensor __instance,
bool ____isPlayer,
ref bool ____dead,
ref bool ____dieNextUpdate,
OWRigidbody ____body,
ref float ____impactSpeed,
float ____sqrCheckSpeedThreshold,
RaycastHit[] ____raycastHits,
SectorDetector ____sectorDetector,
float ____radius,
Vector3 ____localOffset
)
{
if (____isPlayer && (PlayerState.IsAttached() || PlayerState.IsInsideShuttle() || PlayerState.UsingNomaiRemoteCamera()))
{
return false;
}
if (____dieNextUpdate && !____dead)
{
____dead = true;
____dieNextUpdate = false;
if (__instance.gameObject.CompareTag("Player"))
{
Locator.GetDeathManager().SetImpactDeathSpeed(____impactSpeed);
Locator.GetDeathManager().KillPlayer(DeathType.Impact);
}
else if (__instance.gameObject.CompareTag("Ship"))
{
__instance.GetComponent<ShipDamageController>().Explode(false);
}
}
if (____isPlayer && PlayerState.IsInsideShip())
{
var shipCenter = Locator.GetShipTransform().position + (Locator.GetShipTransform().up * 2f);
var distanceFromShip = Vector3.Distance(____body.GetPosition(), shipCenter);
if (distanceFromShip > 8f)
{
____body.SetPosition(shipCenter);
DebugLog.DebugWrite("MOVE PLAYER BACK TO SHIP CENTER");
}
if (!____dead)
{
var a = ____body.GetVelocity() - Locator.GetShipBody().GetPointVelocity(____body.GetPosition());
if (a.sqrMagnitude > ____sqrCheckSpeedThreshold)
{
____impactSpeed = a.magnitude;
____body.AddVelocityChange(-a);
DebugLog.DebugWrite("Would have killed player...");
//____dieNextUpdate = true;
DebugLog.DebugWrite(string.Concat(new object[]
{
"HIGH SPEED IMPACT: ",
__instance.name,
" hit the Ship at ",
____impactSpeed,
"m/s Dist from ship: ",
distanceFromShip
}));
}
}
return false;
}
var passiveReferenceFrame = ____sectorDetector.GetPassiveReferenceFrame();
if (!____dead && passiveReferenceFrame != null)
{
var relativeVelocity = ____body.GetVelocity() - passiveReferenceFrame.GetOWRigidBody().GetPointVelocity(____body.GetPosition());
if (relativeVelocity.sqrMagnitude > ____sqrCheckSpeedThreshold)
{
var hitCount = Physics.RaycastNonAlloc(__instance.transform.TransformPoint(____localOffset), relativeVelocity, ____raycastHits, (relativeVelocity.magnitude * Time.deltaTime) + ____radius, OWLayerMask.physicalMask, QueryTriggerInteraction.Ignore);
for (var i = 0; i < hitCount; i++)
{
if (____raycastHits[i].rigidbody.mass > 10f && !____raycastHits[i].rigidbody.Equals(____body.GetRigidbody()))
{
var owRigidbody = ____raycastHits[i].rigidbody.GetComponent<OWRigidbody>();
if (owRigidbody == null)
{
DebugLog.ToConsole("Rigidbody does not have attached OWRigidbody!!!", OWML.Common.MessageType.Error);
Debug.Break();
}
else
{
relativeVelocity = ____body.GetVelocity() - owRigidbody.GetPointVelocity(____body.GetPosition());
var a2 = Vector3.Project(relativeVelocity, ____raycastHits[i].normal);
if (a2.sqrMagnitude > ____sqrCheckSpeedThreshold)
{
____body.AddVelocityChange(-a2);
____impactSpeed = a2.magnitude;
if (!PlayerState.IsInsideTheEye())
{
____dieNextUpdate = true;
}
DebugLog.DebugWrite(string.Concat(new object[]
{
"HIGH SPEED IMPACT: ",
__instance.name,
" hit ",
____raycastHits[i].rigidbody.name,
" at ",
____impactSpeed,
"m/s RF: ",
passiveReferenceFrame.GetOWRigidBody().name
}));
break;
}
}
}
}
}
}
return false;
} }
public static bool PreFinishDeathSequence(DeathType deathType) public static bool PreFinishDeathSequence(DeathType deathType)

View File

@ -30,6 +30,7 @@ namespace QSB.DeathSync
private ShipCockpitController _cockpitController; private ShipCockpitController _cockpitController;
private PlayerSpacesuit _spaceSuit; private PlayerSpacesuit _spaceSuit;
private ShipTractorBeamSwitch _shipTractorBeam; private ShipTractorBeamSwitch _shipTractorBeam;
private SuitPickupVolume[] _suitPickupVolumes;
public void Awake() => Instance = this; public void Awake() => Instance = this;
@ -40,6 +41,8 @@ namespace QSB.DeathSync
_spaceSuit = Locator.GetPlayerSuit(); _spaceSuit = Locator.GetPlayerSuit();
_playerSpawner = FindObjectOfType<PlayerSpawner>(); _playerSpawner = FindObjectOfType<PlayerSpawner>();
_shipTractorBeam = FindObjectOfType<ShipTractorBeamSwitch>(); _shipTractorBeam = FindObjectOfType<ShipTractorBeamSwitch>();
_suitPickupVolumes = FindObjectsOfType<SuitPickupVolume>();
_fluidDetector = Locator.GetPlayerCamera().GetComponentInChildren<FluidDetector>(); _fluidDetector = Locator.GetPlayerCamera().GetComponentInChildren<FluidDetector>();
_playerSpawnPoint = GetSpawnPoint(); _playerSpawnPoint = GetSpawnPoint();
@ -88,6 +91,33 @@ namespace QSB.DeathSync
_playerResources.SetValue("_isSuffocating", false); _playerResources.SetValue("_isSuffocating", false);
_playerResources.DebugRefillResources(); _playerResources.DebugRefillResources();
_spaceSuit.RemoveSuit(true); _spaceSuit.RemoveSuit(true);
foreach (var pickupVolume in _suitPickupVolumes)
{
var containsSuit = pickupVolume.GetValue<bool>("_containsSuit");
var allowReturn = pickupVolume.GetValue<bool>("_allowSuitReturn");
if (!containsSuit && allowReturn)
{
var interactVolume = pickupVolume.GetValue<MultipleInteractionVolume>("_interactVolume");
var pickupSuitIndex = pickupVolume.GetValue<int>("_pickupSuitCommandIndex");
pickupVolume.SetValue("_containsSuit", true);
interactVolume.ChangePrompt(UITextType.SuitUpPrompt, pickupSuitIndex);
var suitGeometry = pickupVolume.GetValue<GameObject>("_suitGeometry");
var suitCollider = pickupVolume.GetValue<OWCollider>("_suitOWCollider");
var toolGeometries = pickupVolume.GetValue<GameObject[]>("_toolGeometry");
suitGeometry.SetActive(true);
suitCollider.SetActivation(true);
foreach (var geo in toolGeometries)
{
geo.SetActive(true);
}
}
}
} }
public void ResetShip() public void ResetShip()

View File

@ -11,17 +11,11 @@ namespace QSB.OrbSync.TransformSync
public static List<NomaiOrbTransformSync> OrbTransformSyncs = new List<NomaiOrbTransformSync>(); public static List<NomaiOrbTransformSync> OrbTransformSyncs = new List<NomaiOrbTransformSync>();
private int _index => OrbTransformSyncs.IndexOf(this); private int _index => OrbTransformSyncs.IndexOf(this);
private bool _isReady;
public override void OnStartClient() public override void OnStartClient() => OrbTransformSyncs.Add(this);
{
QSBSceneManager.OnSceneLoaded += (OWScene scene, bool inUniverse) => _isReady = false;
OrbTransformSyncs.Add(this);
}
protected override void OnDestroy() protected override void OnDestroy()
{ {
QSBSceneManager.OnSceneLoaded -= (OWScene scene, bool inUniverse) => _isReady = false;
OrbTransformSyncs.Remove(this); OrbTransformSyncs.Remove(this);
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded; QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
} }
@ -34,6 +28,11 @@ namespace QSB.OrbSync.TransformSync
private GameObject GetTransform() private GameObject GetTransform()
{ {
if (_index == -1)
{
DebugLog.ToConsole($"Error - Index cannot be found.", OWML.Common.MessageType.Error);
return null;
}
if (QSBWorldSync.OldOrbList == null || QSBWorldSync.OldOrbList.Count <= _index) if (QSBWorldSync.OldOrbList == null || QSBWorldSync.OldOrbList.Count <= _index)
{ {
DebugLog.ToConsole($"Error - OldOrbList is null or does not contain index {_index}.", OWML.Common.MessageType.Error); DebugLog.ToConsole($"Error - OldOrbList is null or does not contain index {_index}.", OWML.Common.MessageType.Error);

View File

@ -20,7 +20,9 @@ namespace QSB.Player
var localInstance = PlayerTransformSync.LocalInstance; var localInstance = PlayerTransformSync.LocalInstance;
if (localInstance == null) if (localInstance == null)
{ {
DebugLog.ToConsole($"Error - Trying to get LocalPlayerId when the local PlayerTransformSync instance is null.", MessageType.Error); var method = new StackTrace().GetFrame(1).GetMethod();
DebugLog.ToConsole($"Error - Trying to get LocalPlayerId when the local PlayerTransformSync instance is null." +
$"{Environment.NewLine} Called from {method.DeclaringType.Name}.{method.Name} ", MessageType.Error);
return uint.MaxValue; return uint.MaxValue;
} }
if (localInstance.NetIdentity == null) if (localInstance.NetIdentity == null)

View File

@ -64,7 +64,7 @@ namespace QSB
public static AssetBundle NetworkAssetBundle { get; private set; } public static AssetBundle NetworkAssetBundle { get; private set; }
public static AssetBundle InstrumentAssetBundle { get; private set; } public static AssetBundle InstrumentAssetBundle { get; private set; }
public static AssetBundle ConversationAssetBundle { get; private set; } public static AssetBundle ConversationAssetBundle { get; private set; }
public static bool WorldObjectsReady => WorldObjectManager.AllReady; public static bool WorldObjectsReady => WorldObjectManager.AllReady && IsInMultiplayer && PlayerTransformSync.LocalInstance != null;
public static bool IsServer => QNetworkServer.active; public static bool IsServer => QNetworkServer.active;
public static bool IsInMultiplayer => QNetworkManager.singleton.isNetworkActive; public static bool IsInMultiplayer => QNetworkManager.singleton.isNetworkActive;
public static string QSBVersion => Helper.Manifest.Version; public static string QSBVersion => Helper.Manifest.Version;
@ -176,15 +176,23 @@ namespace QSB
{ {
GUI.Label(new Rect(420, offset3, 200f, 20f), $"In control of ship? : {ship.HasAuthority}"); GUI.Label(new Rect(420, offset3, 200f, 20f), $"In control of ship? : {ship.HasAuthority}");
offset3 += _debugLineSpacing; offset3 += _debugLineSpacing;
GUI.Label(new Rect(420, offset3, 200f, 20f), $"Ship sector : {(ship.ReferenceSector == null ? "NULL" : ship.ReferenceSector.Name)}"); GUI.Label(new Rect(420, offset3, 400f, 20f), $"Ship sector : {(ship.ReferenceSector == null ? "NULL" : ship.ReferenceSector.Name)}");
offset3 += _debugLineSpacing; offset3 += _debugLineSpacing;
GUI.Label(new Rect(420, offset3, 400f, 20f), $"Ship relative velocity : {ship.AttachedObject.GetRelativeVelocity(ship.ReferenceTransform.GetAttachedOWRigidbody())}"); if (ship.ReferenceTransform != null)
offset3 += _debugLineSpacing; {
offset3 += _debugLineSpacing; GUI.Label(new Rect(420, offset3, 400f, 20f), $"Ship relative velocity : {ship.GetRelativeVelocity()}");
GUI.Label(new Rect(420, offset3, 400f, 20f), $"Ship velocity mag. : {ship.GetVelocityChangeMagnitude()}"); offset3 += _debugLineSpacing;
GUI.Label(new Rect(420, offset3, 400f, 20f), $"Ship velocity mag. : {ship.GetVelocityChangeMagnitude()}");
offset3 += _debugLineSpacing;
}
GUI.Label(new Rect(420, offset3, 200f, 20f), $"Ship sectors :");
offset3 += _debugLineSpacing; offset3 += _debugLineSpacing;
foreach (var sector in ship.SectorSync.SectorList)
{
GUI.Label(new Rect(420, offset3, 400f, 20f), $"- {sector.Name}");
offset3 += _debugLineSpacing;
}
} }
var offset2 = 10f; var offset2 = 10f;
@ -217,6 +225,16 @@ namespace QSB
GUI.Label(new Rect(220, offset, 400f, 20f), $"- Thrusting : {player.JetpackAcceleration?.IsThrusting}"); GUI.Label(new Rect(220, offset, 400f, 20f), $"- Thrusting : {player.JetpackAcceleration?.IsThrusting}");
offset += _debugLineSpacing; offset += _debugLineSpacing;
} }
GUI.Label(new Rect(220, offset, 200f, 20f), $"QM Illuminated : {Locator.GetQuantumMoon().IsIlluminated()}");
offset += _debugLineSpacing;
GUI.Label(new Rect(220, offset, 200f, 20f), $"QM Visible by :");
offset += _debugLineSpacing;
var tracker = Locator.GetQuantumMoon().GetValue<ShapeVisibilityTracker>("_visibilityTracker");
foreach (var player in QSBPlayerManager.GetPlayersWithCameras())
{
GUI.Label(new Rect(220, offset, 200f, 20f), $" - {player.PlayerId} : {tracker.GetType().GetMethod("IsInFrustum", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(tracker, new object[] { player.Camera.GetFrustumPlanes() })}");
offset += _debugLineSpacing;
}
if (SocketedObjToDebug == -1) if (SocketedObjToDebug == -1)
{ {

View File

@ -11,6 +11,8 @@ namespace QSB
public bool CanEditName { get; set; } public bool CanEditName { get; set; }
public string PlayerName { get; private set; } public string PlayerName { get; private set; }
// TODO : Could delete a lot of this - shouldnt be possible to not have a profile and still play
private readonly string[] _defaultNames = { private readonly string[] _defaultNames = {
"Arkose", "Arkose",
"Chert", "Chert",

View File

@ -435,7 +435,7 @@ namespace QSB.QuantumSync.Patches
fogAlpha = Mathf.InverseLerp(____fogThickness + ____fogRolloffDistance, ____fogThickness, distanceFromFog); fogAlpha = Mathf.InverseLerp(____fogThickness + ____fogRolloffDistance, ____fogThickness, distanceFromFog);
if (distanceFromFog < 0f) if (distanceFromFog < 0f)
{ {
if ((bool)__instance.GetType().GetMethod("IsLockedByProbeSnapshot", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, null) || QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, true)) if ((bool)__instance.GetType().GetMethod("IsLockedByProbeSnapshot", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, null) || QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, true).First)
{ {
____isPlayerInside = true; ____isPlayerInside = true;
__instance.GetType().GetMethod("SetSurfaceState", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, new object[] { ____stateIndex }); __instance.GetType().GetMethod("SetSurfaceState", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, new object[] { ____stateIndex });
@ -456,7 +456,7 @@ namespace QSB.QuantumSync.Patches
if (____stateIndex != 5) if (____stateIndex != 5)
{ {
____isPlayerInside = false; ____isPlayerInside = false;
if (!(bool)__instance.GetType().GetMethod("IsLockedByProbeSnapshot", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, null) && !QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, true)) if (!(bool)__instance.GetType().GetMethod("IsLockedByProbeSnapshot", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, null) && !QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, true).First)
{ {
__instance.GetType().GetMethod("Collapse", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, new object[] { true }); __instance.GetType().GetMethod("Collapse", BindingFlags.NonPublic | BindingFlags.Instance).Invoke(__instance, new object[] { true });
} }

View File

@ -41,7 +41,7 @@ namespace QSB.QuantumSync.Patches
public static bool ShapeIsVisibleUsingCameraFrustum(ShapeVisibilityTracker __instance, ref bool __result) public static bool ShapeIsVisibleUsingCameraFrustum(ShapeVisibilityTracker __instance, ref bool __result)
{ {
__result = QuantumManager.IsVisibleUsingCameraFrustum(__instance, false); __result = QuantumManager.IsVisibleUsingCameraFrustum(__instance, false).First;
return false; return false;
} }

View File

@ -1,8 +1,9 @@
using OWML.Common; using OWML.Common;
using QSB.Events; using QSB.Events;
using QSB.Patches; using QSB.Patches;
using QSB.Player;
using QSB.Utility; using QSB.Utility;
using System.Diagnostics; using System.Linq;
using System.Reflection; using System.Reflection;
using UnityEngine; using UnityEngine;
@ -40,16 +41,36 @@ namespace QSB.QuantumSync.Patches
GameObject[] ____deactivateAtEye GameObject[] ____deactivateAtEye
) )
{ {
if (QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, skipInstantVisibilityCheck) && !QuantumManager.Shrine.IsPlayerInDarkness()) var isVisibleOutput = QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, skipInstantVisibilityCheck);
//var moonVisible = isVisibleOutput.First;
var moonVisiblePlayers = isVisibleOutput.Second;
var inMoonPlayers = QSBPlayerManager.PlayerList.Where(x => x.IsInMoon);
var inShrinePlayers = QSBPlayerManager.PlayerList.Where(x => x.IsInShrine);
//var outMoonPlayers = QSBPlayerManager.PlayerList.Where(x => !x.IsInMoon);
var outShrinePlayers = QSBPlayerManager.PlayerList.Where(x => !x.IsInShrine);
var shrineLit = QuantumManager.Shrine.IsPlayerInDarkness();
// If any of the players in the moon are not in the shrine
if (inMoonPlayers.Any(x => !x.IsInShrine))
{ {
if (!skipInstantVisibilityCheck)
{
var method = new StackTrace().GetFrame(3).GetMethod();
DebugLog.ToConsole($"Warning - Tried to change moon state while still observed. Called by {method.DeclaringType}.{method.Name}", MessageType.Warning);
}
__result = false; __result = false;
return false; return false;
} }
// If any of the players outside the shrine can see the moon
if (outShrinePlayers.Any(moonVisiblePlayers.Contains))
{
__result = false;
return false;
}
// If there are players in the shrine and the shrine is not lit
if(inShrinePlayers.Count() != 0 && !shrineLit)
{
__result = false;
return false;
}
var flag = false; var flag = false;
if (____isPlayerInside && ____hasSunCollapsed) if (____isPlayerInside && ____hasSunCollapsed)
{ {
@ -98,7 +119,7 @@ namespace QSB.QuantumSync.Patches
{ {
Physics.SyncTransforms(); Physics.SyncTransforms();
} }
if (__instance.IsPlayerEntangled() || !QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, skipInstantVisibilityCheck)) if (__instance.IsPlayerEntangled() || !QuantumManager.IsVisibleUsingCameraFrustum((ShapeVisibilityTracker)____visibilityTracker, skipInstantVisibilityCheck).First)
{ {
____moonBody.transform.position = position; ____moonBody.transform.position = position;
if (!Physics.autoSyncTransforms) if (!Physics.autoSyncTransforms)

View File

@ -76,19 +76,22 @@ namespace QSB.QuantumSync
} }
} }
public static bool IsVisibleUsingCameraFrustum(ShapeVisibilityTracker tracker, bool ignoreLocalCamera) public static Tuple<bool, List<PlayerInfo>> IsVisibleUsingCameraFrustum(ShapeVisibilityTracker tracker, bool ignoreLocalCamera)
{ {
var playersWithCameras = QSBPlayerManager.GetPlayersWithCameras(!ignoreLocalCamera); var playersWithCameras = QSBPlayerManager.GetPlayersWithCameras(!ignoreLocalCamera);
if (playersWithCameras.Count == 0) if (playersWithCameras.Count == 0)
{ {
DebugLog.ToConsole($"Warning - Trying to run IsVisibleUsingCameraFrustum when there are no players!", MessageType.Warning); DebugLog.ToConsole($"Warning - Trying to run IsVisibleUsingCameraFrustum when there are no players!", MessageType.Warning);
return false; return new Tuple<bool, List<PlayerInfo>>(false, null);
} }
if (!tracker.gameObject.activeInHierarchy) if (!tracker.gameObject.activeInHierarchy)
{ {
return false; return new Tuple<bool, List<PlayerInfo>>(false, null);
} }
var frustumMethod = tracker.GetType().GetMethod("IsInFrustum", BindingFlags.NonPublic | BindingFlags.Instance); var frustumMethod = tracker.GetType().GetMethod("IsInFrustum", BindingFlags.NonPublic | BindingFlags.Instance);
var playersWhoCanSee = new List<PlayerInfo>();
var foundPlayers = false;
foreach (var player in playersWithCameras) foreach (var player in playersWithCameras)
{ {
if (player.Camera == null) if (player.Camera == null)
@ -99,16 +102,18 @@ namespace QSB.QuantumSync
var isInFrustum = (bool)frustumMethod.Invoke(tracker, new object[] { player.Camera.GetFrustumPlanes() }); var isInFrustum = (bool)frustumMethod.Invoke(tracker, new object[] { player.Camera.GetFrustumPlanes() });
if (isInFrustum) if (isInFrustum)
{ {
return true; playersWhoCanSee.Add(player);
foundPlayers = true;
} }
} }
return false;
return new Tuple<bool, List<PlayerInfo>>(foundPlayers, playersWhoCanSee);
} }
public static bool IsVisible(ShapeVisibilityTracker tracker, bool ignoreLocalCamera) public static bool IsVisible(ShapeVisibilityTracker tracker, bool ignoreLocalCamera)
{ {
return tracker.gameObject.activeInHierarchy return tracker.gameObject.activeInHierarchy
&& IsVisibleUsingCameraFrustum(tracker, ignoreLocalCamera) && IsVisibleUsingCameraFrustum(tracker, ignoreLocalCamera).First
&& QSBPlayerManager.GetPlayersWithCameras(!ignoreLocalCamera) && QSBPlayerManager.GetPlayersWithCameras(!ignoreLocalCamera)
.Any(x => VisibilityOccluder.CanYouSee(tracker, x.Camera.mainCamera.transform.position)); .Any(x => VisibilityOccluder.CanYouSee(tracker, x.Camera.mainCamera.transform.position));
} }

View File

@ -19,7 +19,7 @@ namespace QSB.RoastingSync.Patches
public override void DoUnpatches() public override void DoUnpatches()
{ {
// TODO : add unpatches
} }
public static bool Marshmallow_SpawnMallow() public static bool Marshmallow_SpawnMallow()

View File

@ -1,8 +1,6 @@
using OWML.Common; using OWML.Common;
using QSB.SectorSync.WorldObjects; using QSB.SectorSync.WorldObjects;
using QSB.Syncs; using QSB.Syncs;
using QSB.Syncs.RigidbodySync;
using QSB.Syncs.TransformSync;
using QSB.Utility; using QSB.Utility;
using QSB.WorldSync; using QSB.WorldSync;
using QuantumUNET; using QuantumUNET;
@ -21,11 +19,12 @@ namespace QSB.SectorSync
private void OnEnable() => RepeatingManager.Repeatings.Add(this); private void OnEnable() => RepeatingManager.Repeatings.Add(this);
private void OnDisable() => RepeatingManager.Repeatings.Remove(this); private void OnDisable() => RepeatingManager.Repeatings.Remove(this);
public List<ISectoredSync<Component>> SectoredSyncs = new List<ISectoredSync<Component>>(); public List<ISectoredSync<Transform>> SectoredTransformSyncs = new List<ISectoredSync<Transform>>();
public List<ISectoredSync<OWRigidbody>> SectoredRigidbodySyncs = new List<ISectoredSync<OWRigidbody>>();
public void Invoke() public void Invoke()
{ {
foreach (var sync in SectoredSyncs) foreach (var sync in SectoredTransformSyncs)
{ {
if (sync.AttachedObject == null) if (sync.AttachedObject == null)
{ {
@ -38,6 +37,20 @@ namespace QSB.SectorSync
CheckTransformSyncSector(sync); CheckTransformSyncSector(sync);
} }
} }
foreach (var sync in SectoredRigidbodySyncs)
{
if (sync.AttachedObject == null)
{
continue;
}
if ((sync as QNetworkBehaviour).HasAuthority
&& sync.AttachedObject.gameObject.activeInHierarchy
&& sync.IsReady)
{
CheckTransformSyncSector(sync);
}
}
} }
public override void Awake() public override void Awake()

View File

@ -86,8 +86,10 @@ namespace QSB.SectorSync
return null; return null;
} }
var listToCheck = SectorList.Count(x => x.ShouldSyncTo(_targetType)) == 0 var numSectorsCurrentlyIn = SectorList.Count(x => x.ShouldSyncTo(_targetType));
? QSBWorldSync.GetWorldObjects<QSBSector>()
var listToCheck = numSectorsCurrentlyIn == 0
? QSBWorldSync.GetWorldObjects<QSBSector>().Where(x => !x.IsFakeSector)
: SectorList; : SectorList;
/* Explanation of working out which sector to sync to : /* Explanation of working out which sector to sync to :
@ -113,7 +115,9 @@ namespace QSB.SectorSync
var ordered = activeNotNullNotBlacklisted var ordered = activeNotNullNotBlacklisted
.OrderBy(sector => CalculateSectorScore(sector, trans, _attachedOWRigidbody)); .OrderBy(sector => CalculateSectorScore(sector, trans, _attachedOWRigidbody));
// TODO : clean up this shit???
if ( if (
numSectorsCurrentlyIn != 0 &&
// if any fake sectors are *roughly* in the same place as other sectors - we want fake sectors to override other sectors // if any fake sectors are *roughly* in the same place as other sectors - we want fake sectors to override other sectors
QSBSectorManager.Instance.FakeSectors.Any( QSBSectorManager.Instance.FakeSectors.Any(
x => OWMath.ApproxEquals(Vector3.Distance(x.Position, trans.position), Vector3.Distance(ordered.FirstOrDefault().Position, trans.position), 0.01f) x => OWMath.ApproxEquals(Vector3.Distance(x.Position, trans.position), Vector3.Distance(ordered.FirstOrDefault().Position, trans.position), 0.01f)

View File

@ -29,13 +29,11 @@ namespace QSB.ShipSync.TransformSync
{ {
if (HasAuthority && ShipManager.Instance.CurrentFlyer != QSBPlayerManager.LocalPlayerId) if (HasAuthority && ShipManager.Instance.CurrentFlyer != QSBPlayerManager.LocalPlayerId)
{ {
DebugLog.DebugWrite($"Warning - Local player has ship authority, but is not the current flyer!", OWML.Common.MessageType.Warning);
return; return;
} }
if (!HasAuthority && ShipManager.Instance.CurrentFlyer == QSBPlayerManager.LocalPlayerId) if (!HasAuthority && ShipManager.Instance.CurrentFlyer == QSBPlayerManager.LocalPlayerId)
{ {
DebugLog.DebugWrite($"Warning - Local player does not have ship authority, but is the current flyer!", OWML.Common.MessageType.Warning);
return; return;
} }
@ -45,5 +43,6 @@ namespace QSB.ShipSync.TransformSync
public override TargetType Type => TargetType.Ship; public override TargetType Type => TargetType.Ship;
public override bool UseInterpolation => true; public override bool UseInterpolation => true;
protected override float DistanceLeeway => 20f;
} }
} }

View File

@ -2,7 +2,6 @@
using QSB.SectorSync.WorldObjects; using QSB.SectorSync.WorldObjects;
using QSB.WorldSync; using QSB.WorldSync;
using QuantumUNET.Transport; using QuantumUNET.Transport;
using System.Collections.Generic;
namespace QSB.Syncs.RigidbodySync namespace QSB.Syncs.RigidbodySync
{ {
@ -15,14 +14,14 @@ namespace QSB.Syncs.RigidbodySync
public override void Start() public override void Start()
{ {
SectorSync = gameObject.AddComponent<SectorSync.SectorSync>(); SectorSync = gameObject.AddComponent<SectorSync.SectorSync>();
QSBSectorManager.Instance.SectoredSyncs.Add((ISectoredSync<UnityEngine.Component>)this); QSBSectorManager.Instance.SectoredRigidbodySyncs.Add(this);
base.Start(); base.Start();
} }
protected override void OnDestroy() protected override void OnDestroy()
{ {
base.OnDestroy(); base.OnDestroy();
QSBSectorManager.Instance.SectoredSyncs.Remove((ISectoredSync<UnityEngine.Component>)this); QSBSectorManager.Instance.SectoredRigidbodySyncs.Remove(this);
if (SectorSync != null) if (SectorSync != null)
{ {
Destroy(SectorSync); Destroy(SectorSync);
@ -104,7 +103,7 @@ namespace QSB.Syncs.RigidbodySync
public void SetReferenceSector(QSBSector sector) public void SetReferenceSector(QSBSector sector)
{ {
ReferenceSector = sector; ReferenceSector = sector;
SetReferenceTransform(sector.Transform); SetReferenceTransform(sector?.Transform);
} }
} }
} }

View File

@ -1,4 +1,5 @@
using OWML.Common; using OWML.Common;
using OWML.Utils;
using QSB.Utility; using QSB.Utility;
using QuantumUNET.Components; using QuantumUNET.Components;
using QuantumUNET.Transport; using QuantumUNET.Transport;
@ -14,6 +15,10 @@ namespace QSB.Syncs.RigidbodySync
public abstract bool IsReady { get; } public abstract bool IsReady { get; }
public abstract bool UseInterpolation { get; } public abstract bool UseInterpolation { get; }
protected virtual float DistanceLeeway { get; } = 5f;
private float _previousDistance;
private const float SmoothTime = 0.1f;
protected bool _isInitialized; protected bool _isInitialized;
protected IntermediaryTransform _intermediaryTransform; protected IntermediaryTransform _intermediaryTransform;
protected Vector3 _velocity; protected Vector3 _velocity;
@ -21,6 +26,8 @@ namespace QSB.Syncs.RigidbodySync
protected Vector3 _prevVelocity; protected Vector3 _prevVelocity;
protected Vector3 _prevAngularVelocity; protected Vector3 _prevAngularVelocity;
private string _logName => $"{NetId}:{GetType().Name}"; private string _logName => $"{NetId}:{GetType().Name}";
private Vector3 _positionSmoothVelocity;
private Quaternion _rotationSmoothVelocity;
protected abstract OWRigidbody GetRigidbody(); protected abstract OWRigidbody GetRigidbody();
@ -61,18 +68,6 @@ namespace QSB.Syncs.RigidbodySync
* We can't store the last two on the IntermediaryTransform, so they come from fields. * We can't store the last two on the IntermediaryTransform, so they come from fields.
*/ */
// Get world position from IT.
// Get world rotation from IT.
// Get velocity from field.
// Get angular velocity from field.
// Send all.
// Set _prev fields.
var worldPos = _intermediaryTransform.GetPosition(); var worldPos = _intermediaryTransform.GetPosition();
var worldRot = _intermediaryTransform.GetRotation(); var worldRot = _intermediaryTransform.GetRotation();
var velocity = _velocity; var velocity = _velocity;
@ -82,6 +77,7 @@ namespace QSB.Syncs.RigidbodySync
SerializeRotation(writer, worldRot); SerializeRotation(writer, worldRot);
writer.Write(velocity); writer.Write(velocity);
writer.Write(angularVelocity); writer.Write(angularVelocity);
_prevPosition = worldPos; _prevPosition = worldPos;
_prevRotation = worldRot; _prevRotation = worldRot;
_prevVelocity = velocity; _prevVelocity = velocity;
@ -153,6 +149,11 @@ namespace QSB.Syncs.RigidbodySync
return; return;
} }
if (ReferenceTransform == null)
{
return;
}
UpdateTransform(); UpdateTransform();
base.Update(); base.Update();
@ -164,7 +165,7 @@ namespace QSB.Syncs.RigidbodySync
{ {
_intermediaryTransform.EncodePosition(AttachedObject.transform.position); _intermediaryTransform.EncodePosition(AttachedObject.transform.position);
_intermediaryTransform.EncodeRotation(AttachedObject.transform.rotation); _intermediaryTransform.EncodeRotation(AttachedObject.transform.rotation);
_velocity = AttachedObject.GetRelativeVelocity(ReferenceTransform.GetAttachedOWRigidbody()); _velocity = GetRelativeVelocity();
_angularVelocity = AttachedObject.GetRelativeAngularVelocity(ReferenceTransform.GetAttachedOWRigidbody()); _angularVelocity = AttachedObject.GetRelativeAngularVelocity(ReferenceTransform.GetAttachedOWRigidbody());
return; return;
} }
@ -177,12 +178,41 @@ namespace QSB.Syncs.RigidbodySync
return; return;
} }
AttachedObject.transform.position = targetPos; if (UseInterpolation)
AttachedObject.transform.rotation = targetRot; {
AttachedObject.SetVelocity(ReferenceTransform.GetAttachedOWRigidbody().GetVelocity() + _velocity); AttachedObject.SetPosition(SmartPositionSmoothDamp(AttachedObject.transform.position, targetPos));
AttachedObject.SetRotation(QuaternionHelper.SmoothDamp(AttachedObject.transform.rotation, targetRot, ref _rotationSmoothVelocity, SmoothTime));
}
else
{
AttachedObject.SetPosition(targetPos);
AttachedObject.SetRotation(targetRot);
}
SetVelocity(AttachedObject, ReferenceTransform.GetAttachedOWRigidbody().GetPointVelocity(targetPos) + _velocity);
AttachedObject.SetAngularVelocity(ReferenceTransform.GetAttachedOWRigidbody().GetAngularVelocity() + _angularVelocity); AttachedObject.SetAngularVelocity(ReferenceTransform.GetAttachedOWRigidbody().GetAngularVelocity() + _angularVelocity);
} }
private void SetVelocity(OWRigidbody rigidbody, Vector3 newVelocity)
{
var isRunningKinematic = rigidbody.RunningKinematicSimulation();
var currentVelocity = rigidbody.GetValue<Vector3>("_currentVelocity");
if (isRunningKinematic)
{
var kinematicRigidbody = rigidbody.GetValue<KinematicRigidbody>("_kinematicRigidbody");
kinematicRigidbody.velocity = newVelocity + Locator.GetCenterOfTheUniverse().GetStaticFrameWorldVelocity();
}
else
{
var normalRigidbody = rigidbody.GetValue<Rigidbody>("_rigidbody");
normalRigidbody.velocity = newVelocity + Locator.GetCenterOfTheUniverse().GetStaticFrameWorldVelocity();
}
rigidbody.SetValue("_lastVelocity", currentVelocity);
rigidbody.SetValue("_currentVelocity", newVelocity);
}
public void SetReferenceTransform(Transform transform) public void SetReferenceTransform(Transform transform)
{ {
if (ReferenceTransform == transform) if (ReferenceTransform == transform)
@ -193,6 +223,21 @@ namespace QSB.Syncs.RigidbodySync
_intermediaryTransform.SetReferenceTransform(transform); _intermediaryTransform.SetReferenceTransform(transform);
} }
// TODO : remove .Distance
private Vector3 SmartPositionSmoothDamp(Vector3 currentPosition, Vector3 targetPosition)
{
var distance = Vector3.Distance(currentPosition, targetPosition);
if (distance > _previousDistance + DistanceLeeway)
{
DebugLog.DebugWrite($"Warning - {AttachedObject.name} moved too far!", MessageType.Warning);
_previousDistance = distance;
return targetPosition;
}
_previousDistance = distance;
return Vector3.SmoothDamp(currentPosition, targetPosition, ref _positionSmoothVelocity, SmoothTime);
}
// TODO : optimize by using sqrMagnitude
public override bool HasMoved() public override bool HasMoved()
{ {
var displacementMagnitude = (_intermediaryTransform.GetPosition() - _prevPosition).magnitude; var displacementMagnitude = (_intermediaryTransform.GetPosition() - _prevPosition).magnitude;
@ -201,6 +246,7 @@ namespace QSB.Syncs.RigidbodySync
{ {
return true; return true;
} }
if (Quaternion.Angle(_intermediaryTransform.GetRotation(), _prevRotation) > 1E-03f) if (Quaternion.Angle(_intermediaryTransform.GetRotation(), _prevRotation) > 1E-03f)
{ {
return true; return true;
@ -212,6 +258,7 @@ namespace QSB.Syncs.RigidbodySync
{ {
return true; return true;
} }
if (angularVelocityChangeMagnitude > 1E-03f) if (angularVelocityChangeMagnitude > 1E-03f)
{ {
return true; return true;
@ -223,9 +270,16 @@ namespace QSB.Syncs.RigidbodySync
public float GetVelocityChangeMagnitude() public float GetVelocityChangeMagnitude()
=> (_velocity - _prevVelocity).magnitude; => (_velocity - _prevVelocity).magnitude;
public Vector3 GetRelativeVelocity()
=> ReferenceTransform.GetAttachedOWRigidbody().GetPointVelocity(AttachedObject.transform.position) - AttachedObject.GetVelocity();
private void OnRenderObject() private void OnRenderObject()
{ {
if (!QSBCore.WorldObjectsReady || !QSBCore.DebugMode || !QSBCore.ShowLinesInDebug || !IsReady) if (!QSBCore.WorldObjectsReady
|| !QSBCore.DebugMode
|| !QSBCore.ShowLinesInDebug
|| !IsReady
|| ReferenceTransform == null)
{ {
return; return;
} }
@ -235,6 +289,8 @@ namespace QSB.Syncs.RigidbodySync
var color = HasMoved() ? Color.green : Color.yellow; var color = HasMoved() ? Color.green : Color.yellow;
Popcron.Gizmos.Cube(AttachedObject.transform.position, AttachedObject.transform.rotation, Vector3.one / 2, color); Popcron.Gizmos.Cube(AttachedObject.transform.position, AttachedObject.transform.rotation, Vector3.one / 2, color);
Popcron.Gizmos.Line(AttachedObject.transform.position, ReferenceTransform.position, Color.cyan); Popcron.Gizmos.Line(AttachedObject.transform.position, ReferenceTransform.position, Color.cyan);
Popcron.Gizmos.Line(AttachedObject.transform.position, AttachedObject.transform.position + GetRelativeVelocity(), Color.blue);
} }
} }
} }

View File

@ -16,8 +16,36 @@ namespace QSB.Syncs.TransformSync
public abstract class BaseTransformSync : QNetworkTransform, ISync<Transform> public abstract class BaseTransformSync : QNetworkTransform, ISync<Transform>
{ {
public uint AttachedNetId => NetIdentity?.NetId.Value ?? uint.MaxValue; public uint AttachedNetId
public uint PlayerId => NetIdentity.RootIdentity?.NetId.Value ?? NetIdentity.NetId.Value; {
get
{
if (NetIdentity == null)
{
DebugLog.ToConsole($"Error - Trying to get AttachedNetId with null NetIdentity! Type:{GetType().Name} GrandType:{GetType().GetType().Name}", MessageType.Error);
return uint.MaxValue;
}
return NetIdentity.NetId.Value;
}
}
public uint PlayerId
{
get
{
if (NetIdentity == null)
{
DebugLog.ToConsole($"Error - Trying to get PlayerId with null NetIdentity! Type:{GetType().Name} GrandType:{GetType().GetType().Name}", MessageType.Error);
return uint.MaxValue;
}
return NetIdentity.RootIdentity != null
? NetIdentity.RootIdentity.NetId.Value
: AttachedNetId;
}
}
public PlayerInfo Player => QSBPlayerManager.GetPlayer(PlayerId); public PlayerInfo Player => QSBPlayerManager.GetPlayer(PlayerId);
public Transform ReferenceTransform { get; set; } public Transform ReferenceTransform { get; set; }
@ -53,7 +81,7 @@ namespace QSB.Syncs.TransformSync
{ {
if (!HasAuthority && AttachedObject != null) if (!HasAuthority && AttachedObject != null)
{ {
Destroy(AttachedObject); Destroy(AttachedObject.gameObject);
} }
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded; QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
} }
@ -69,7 +97,7 @@ namespace QSB.Syncs.TransformSync
} }
if (!HasAuthority && AttachedObject != null) if (!HasAuthority && AttachedObject != null)
{ {
Destroy(AttachedObject); Destroy(AttachedObject.gameObject);
} }
AttachedObject = HasAuthority ? InitLocalTransform() : InitRemoteTransform(); AttachedObject = HasAuthority ? InitLocalTransform() : InitRemoteTransform();
_isInitialized = true; _isInitialized = true;
@ -149,6 +177,11 @@ namespace QSB.Syncs.TransformSync
return; return;
} }
if (ReferenceTransform == null)
{
return;
}
UpdateTransform(); UpdateTransform();
base.Update(); base.Update();
@ -196,7 +229,7 @@ namespace QSB.Syncs.TransformSync
_intermediaryTransform.SetReferenceTransform(transform); _intermediaryTransform.SetReferenceTransform(transform);
if (AttachedObject == null) if (AttachedObject == null)
{ {
DebugLog.ToConsole($"Warning - AttachedObject was null for {_logName} when trying to set reference transform to {transform.name}. Waiting until not null...", MessageType.Warning); DebugLog.ToConsole($"Warning - AttachedObject was null for {_logName} when trying to set reference transform to {transform?.name}. Waiting until not null...", MessageType.Warning);
QSBCore.UnityEvents.RunWhen( QSBCore.UnityEvents.RunWhen(
() => AttachedObject != null, () => AttachedObject != null,
() => ReparentAttachedObject(transform)); () => ReparentAttachedObject(transform));
@ -234,12 +267,11 @@ namespace QSB.Syncs.TransformSync
private void OnRenderObject() private void OnRenderObject()
{ {
if (!QSBCore.WorldObjectsReady || !QSBCore.DebugMode || !QSBCore.ShowLinesInDebug || !IsReady) if (!QSBCore.WorldObjectsReady
{ || !QSBCore.DebugMode
return; || !QSBCore.ShowLinesInDebug
} || !IsReady
|| ReferenceTransform == null)
if (ReferenceTransform == null)
{ {
return; return;
} }

View File

@ -2,7 +2,6 @@
using QSB.SectorSync.WorldObjects; using QSB.SectorSync.WorldObjects;
using QSB.WorldSync; using QSB.WorldSync;
using QuantumUNET.Transport; using QuantumUNET.Transport;
using System.Collections.Generic;
using UnityEngine; using UnityEngine;
namespace QSB.Syncs.TransformSync namespace QSB.Syncs.TransformSync
@ -16,14 +15,14 @@ namespace QSB.Syncs.TransformSync
public override void Start() public override void Start()
{ {
SectorSync = gameObject.AddComponent<SectorSync.SectorSync>(); SectorSync = gameObject.AddComponent<SectorSync.SectorSync>();
QSBSectorManager.Instance.SectoredSyncs.Add((ISectoredSync<UnityEngine.Component>)this); QSBSectorManager.Instance.SectoredTransformSyncs.Add(this);
base.Start(); base.Start();
} }
protected override void OnDestroy() protected override void OnDestroy()
{ {
base.OnDestroy(); base.OnDestroy();
QSBSectorManager.Instance.SectoredSyncs.Remove((ISectoredSync<UnityEngine.Component>)this); QSBSectorManager.Instance.SectoredTransformSyncs.Remove(this);
if (SectorSync != null) if (SectorSync != null)
{ {
Destroy(SectorSync); Destroy(SectorSync);
@ -105,7 +104,7 @@ namespace QSB.Syncs.TransformSync
public void SetReferenceSector(QSBSector sector) public void SetReferenceSector(QSBSector sector)
{ {
ReferenceSector = sector; ReferenceSector = sector;
SetReferenceTransform(sector.Transform); SetReferenceTransform(sector?.Transform);
} }
} }
} }

View File

@ -11,8 +11,36 @@ namespace QSB.Syncs.TransformSync
{ {
public abstract class UnparentedBaseTransformSync : QNetworkTransform, ISync<GameObject> public abstract class UnparentedBaseTransformSync : QNetworkTransform, ISync<GameObject>
{ {
public uint AttachedNetId => NetIdentity?.NetId.Value ?? uint.MaxValue; public uint AttachedNetId
public uint PlayerId => NetIdentity.RootIdentity?.NetId.Value ?? NetIdentity.NetId.Value; {
get
{
if (NetIdentity == null)
{
DebugLog.ToConsole($"Error - Trying to get AttachedNetId with null NetIdentity! Type:{GetType().Name} GrandType:{GetType().GetType().Name}", MessageType.Error);
return uint.MaxValue;
}
return NetIdentity.NetId.Value;
}
}
public uint PlayerId
{
get
{
if (NetIdentity == null)
{
DebugLog.ToConsole($"Error - Trying to get PlayerId with null NetIdentity! Type:{GetType().Name} GrandType:{GetType().GetType().Name}", MessageType.Error);
return uint.MaxValue;
}
return NetIdentity.RootIdentity != null
? NetIdentity.RootIdentity.NetId.Value
: AttachedNetId;
}
}
public PlayerInfo Player => QSBPlayerManager.GetPlayer(PlayerId); public PlayerInfo Player => QSBPlayerManager.GetPlayer(PlayerId);
public Transform ReferenceTransform { get; set; } public Transform ReferenceTransform { get; set; }
@ -47,7 +75,7 @@ namespace QSB.Syncs.TransformSync
{ {
if (!HasAuthority && AttachedObject != null) if (!HasAuthority && AttachedObject != null)
{ {
Destroy(AttachedObject); Destroy(AttachedObject.gameObject);
} }
QSBSceneManager.OnSceneLoaded -= OnSceneLoaded; QSBSceneManager.OnSceneLoaded -= OnSceneLoaded;
} }
@ -130,6 +158,11 @@ namespace QSB.Syncs.TransformSync
return; return;
} }
if (ReferenceTransform == null)
{
return;
}
UpdateTransform(); UpdateTransform();
base.Update(); base.Update();
@ -177,11 +210,13 @@ namespace QSB.Syncs.TransformSync
_intermediaryTransform.SetReferenceTransform(transform); _intermediaryTransform.SetReferenceTransform(transform);
} }
// TODO : remove .Distance
private Vector3 SmartSmoothDamp(Vector3 currentPosition, Vector3 targetPosition) private Vector3 SmartSmoothDamp(Vector3 currentPosition, Vector3 targetPosition)
{ {
var distance = Vector3.Distance(currentPosition, targetPosition); var distance = Vector3.Distance(currentPosition, targetPosition);
if (distance > _previousDistance + DistanceLeeway) if (distance > _previousDistance + DistanceLeeway)
{ {
DebugLog.DebugWrite($"Warning - {AttachedObject.name} moved too far!", MessageType.Warning);
_previousDistance = distance; _previousDistance = distance;
return targetPosition; return targetPosition;
} }
@ -191,7 +226,11 @@ namespace QSB.Syncs.TransformSync
private void OnRenderObject() private void OnRenderObject()
{ {
if (!QSBCore.WorldObjectsReady || !QSBCore.DebugMode || !QSBCore.ShowLinesInDebug || !IsReady) if (!QSBCore.WorldObjectsReady
|| !QSBCore.DebugMode
|| !QSBCore.ShowLinesInDebug
|| !IsReady
|| ReferenceTransform == null)
{ {
return; return;
} }

View File

@ -7,17 +7,10 @@ namespace QSB.TimeSync.Patches
{ {
public override QSBPatchTypes Type => QSBPatchTypes.OnNonServerClientConnect; public override QSBPatchTypes Type => QSBPatchTypes.OnNonServerClientConnect;
public static bool OnStartOfTimeLoopPrefix(ref PlayerCameraEffectController __instance) public override void DoPatches()
{ => QSBCore.HarmonyHelper.EmptyMethod<OWInput>("OnStartOfTimeLoop");
if (__instance.gameObject.CompareTag("MainCamera") && QSBSceneManager.CurrentScene != OWScene.EyeOfTheUniverse)
{
__instance.Invoke("WakeUp");
}
return false;
}
public override void DoPatches() => QSBCore.HarmonyHelper.AddPrefix<PlayerCameraEffectController>("OnStartOfTimeLoop", typeof(WakeUpPatches), nameof(OnStartOfTimeLoopPrefix)); public override void DoUnpatches()
=> QSBCore.HarmonyHelper.Unpatch<OWInput>("OnStartOfTimeLoop");
public override void DoUnpatches() => QSBCore.HarmonyHelper.Unpatch<PlayerCameraEffectController>("OnStartOfTimeLoop");
} }
} }

View File

@ -1,4 +1,5 @@
using OWML.Common; using OWML.Common;
using OWML.Utils;
using QSB.DeathSync; using QSB.DeathSync;
using QSB.Events; using QSB.Events;
using QSB.TimeSync.Events; using QSB.TimeSync.Events;
@ -27,6 +28,7 @@ namespace QSB.TimeSync
private float _serverTime; private float _serverTime;
private bool _isFirstFastForward = true; private bool _isFirstFastForward = true;
private int _serverLoopCount; private int _serverLoopCount;
private bool _hasWokenUp;
public override void OnStartLocalPlayer() => LocalInstance = this; public override void OnStartLocalPlayer() => LocalInstance = this;
@ -60,6 +62,7 @@ namespace QSB.TimeSync
{ {
RespawnOnDeath.Instance.Init(); RespawnOnDeath.Instance.Init();
} }
_hasWokenUp = true;
} }
public void OnDestroy() public void OnDestroy()
@ -71,8 +74,13 @@ namespace QSB.TimeSync
private void OnSceneLoaded(OWScene scene, bool isInUniverse) private void OnSceneLoaded(OWScene scene, bool isInUniverse)
{ {
DebugLog.DebugWrite($"ONSCENELOADED"); DebugLog.DebugWrite($"ONSCENELOADED");
_hasWokenUp = false;
if (isInUniverse) if (isInUniverse)
{ {
if (scene == OWScene.EyeOfTheUniverse)
{
_hasWokenUp = true;
}
Init(); Init();
} }
else else
@ -158,6 +166,7 @@ namespace QSB.TimeSync
{ {
Locator.GetActiveCamera().enabled = false; Locator.GetActiveCamera().enabled = false;
} }
OWInput.ChangeInputMode(InputMode.None);
_state = State.FastForwarding; _state = State.FastForwarding;
OWTime.SetMaxDeltaTime(0.033333335f); OWTime.SetMaxDeltaTime(0.033333335f);
OWTime.SetFixedTimestep(0.033333335f); OWTime.SetFixedTimestep(0.033333335f);
@ -173,6 +182,7 @@ namespace QSB.TimeSync
} }
DebugLog.DebugWrite($"START PAUSING (Target:{_serverTime} Current:{Time.timeSinceLevelLoad})", MessageType.Info); DebugLog.DebugWrite($"START PAUSING (Target:{_serverTime} Current:{Time.timeSinceLevelLoad})", MessageType.Info);
Locator.GetActiveCamera().enabled = false; Locator.GetActiveCamera().enabled = false;
OWInput.ChangeInputMode(InputMode.None);
OWTime.SetTimeScale(0f); OWTime.SetTimeScale(0f);
_state = State.Pausing; _state = State.Pausing;
SpinnerUI.Show(); SpinnerUI.Show();
@ -194,8 +204,22 @@ namespace QSB.TimeSync
TimeSyncUI.Stop(); TimeSyncUI.Stop();
QSBEventManager.FireEvent(EventNames.QSBPlayerStatesRequest); QSBEventManager.FireEvent(EventNames.QSBPlayerStatesRequest);
RespawnOnDeath.Instance.Init(); RespawnOnDeath.Instance.Init();
if (OWInput.GetInputMode() == InputMode.None)
{
OWInput.RestorePreviousInputs();
}
if (!_hasWokenUp)
{
WakeUp();
OWInput.ChangeInputMode(InputMode.Character);
}
} }
private void WakeUp()
=> Locator.GetPlayerCamera().GetComponent<PlayerCameraEffectController>().Invoke("WakeUp");
public void Update() public void Update()
{ {
if (IsServer) if (IsServer)