Smoother sync: predict remote objects/cars from their velocity, 30 updates/s for objects and players
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
+19
-5
@@ -37,6 +37,8 @@ namespace MSCO
|
||||
|
||||
public Vector3 TargetPos;
|
||||
public Quaternion TargetRot;
|
||||
public Vector3 TargetVel; // Geschwindigkeit beim Besitzer: damit wird die Position vorausberechnet
|
||||
public float TargetTime; // wann TargetPos ankam
|
||||
public float LastRecvTime;
|
||||
public float AvatarHoldTime = -100f; // zuletzt von der Hand eines Mitspielers platziert
|
||||
|
||||
@@ -63,7 +65,8 @@ namespace MSCO
|
||||
static readonly string[] IgnoredRoots = { "PLAYER", "TRAFFIC", "NPC_CARS" };
|
||||
|
||||
const float MaxSmallItemMass = 60f; // schwerere Dinge ohne ITEM/PART-Tag sind Teil der Welt
|
||||
const float SendInterval = 1f / 15f;
|
||||
const float SendInterval = 1f / 30f; // unbewegte Objekte werden ohnehin nicht gesendet
|
||||
const float MaxExtrapolation = 0.25f; // höchstens so weit (Sekunden) in die Zukunft vorausrechnen
|
||||
const float KeepAliveInterval = 1f;
|
||||
const float ScanInterval = 3f;
|
||||
const float FirstScanDelay = 3f;
|
||||
@@ -307,15 +310,20 @@ namespace MSCO
|
||||
if (!IsRemoteOwned(b) || b.Rb == null || b.Attached) continue;
|
||||
if (b.IsVehicle && Time.time >= b.NextPartScan) HoldParts(b);
|
||||
if (Time.time - b.AvatarHoldTime < 0.2f) continue; // sitzt gerade in der Hand eines Mitspielers
|
||||
if ((b.Rb.position - b.TargetPos).sqrMagnitude > SnapDistance * SnapDistance)
|
||||
// Dort, wo das Objekt beim Besitzer JETZT ungefähr ist: letzte Position + Geschwindigkeit * Alter.
|
||||
// Ohne das hinken schnelle Objekte (fahrende Autos) immer einen Paketabstand hinterher und ruckeln.
|
||||
float age = Mathf.Min(Time.time - b.TargetTime, MaxExtrapolation);
|
||||
Vector3 predicted = b.TargetPos + b.TargetVel * age;
|
||||
if ((b.Rb.position - predicted).sqrMagnitude > SnapDistance * SnapDistance)
|
||||
{
|
||||
b.Rb.transform.position = b.TargetPos;
|
||||
b.Rb.transform.position = predicted;
|
||||
b.Rb.transform.rotation = b.TargetRot;
|
||||
}
|
||||
else
|
||||
{
|
||||
b.Rb.MovePosition(Vector3.Lerp(b.Rb.position, b.TargetPos, 0.35f));
|
||||
b.Rb.MoveRotation(Quaternion.Slerp(b.Rb.rotation, b.TargetRot, 0.35f));
|
||||
float follow = b.IsVehicle ? 0.5f : 0.35f;
|
||||
b.Rb.MovePosition(Vector3.Lerp(b.Rb.position, predicted, follow));
|
||||
b.Rb.MoveRotation(Quaternion.Slerp(b.Rb.rotation, b.TargetRot, follow));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -342,6 +350,8 @@ namespace MSCO
|
||||
b.Rb.transform.rotation = rot;
|
||||
b.TargetPos = pos;
|
||||
b.TargetRot = rot;
|
||||
b.TargetVel = Vector3.zero;
|
||||
b.TargetTime = Time.time;
|
||||
b.AvatarHoldTime = Time.time;
|
||||
}
|
||||
|
||||
@@ -381,6 +391,8 @@ namespace MSCO
|
||||
FreezeForRemote(b);
|
||||
b.TargetPos = b.Rb.position;
|
||||
b.TargetRot = b.Rb.rotation;
|
||||
b.TargetVel = Vector3.zero;
|
||||
b.TargetTime = Time.time;
|
||||
}
|
||||
b.OwnerId = ownerId;
|
||||
}
|
||||
@@ -492,6 +504,8 @@ namespace MSCO
|
||||
SetRemote(b, from, b.OwnerId == from && b.OwnerActive);
|
||||
b.TargetPos = pos;
|
||||
b.TargetRot = rot;
|
||||
b.TargetVel = vel.sqrMagnitude < 90f * 90f ? vel : Vector3.zero;
|
||||
b.TargetTime = Time.time;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user