private void UpdateTransform() { Transform t = transform; switch (_mode) { case Mode.Direct: { t.position = _latestPosition; t.rotation = _latestRotation; break; } case Mode.Lerp: t.position = Vector3.Lerp(t.position, _latestPosition, _lerpFactor * Time.deltaTime); t.rotation = Quaternion.Lerp(t.rotation, _latestRotation, _lerpFactor * Time.deltaTime); if (Vector3.Distance(t.position, _latestPosition) > _jumpThreshold) { t.position = _latestPosition; t.rotation = _latestRotation; } break; case Mode.Predicted: { t.position = _predictedPosition.Get(Server.Time); t.rotation = _predictedRotation.Get(Server.Time); break; } case Mode.PredictedLerp: { if (!_predictedPosition.ReceivedOnce) { break; } Vector3 predictedPosition = _predictedPosition.Get(Server.Time); Quaternion predictedRotation = _predictedRotation.Get(Server.Time); if (!_predictedPosition.ReceivedTwice || Vector3.Distance(t.position, predictedPosition) > _jumpThreshold) { t.position = predictedPosition; t.rotation = predictedRotation; break; } t.position = Vector3.Lerp(t.position, predictedPosition, _lerpFactor * Time.deltaTime); t.rotation = Quaternion.Lerp(t.rotation, predictedRotation, _lerpFactor * Time.deltaTime); break; } default: enabled = false; throw new Exception($"Unknown client side prediction mode {_mode}. Disabled script."); } Updated?.Invoke(this); }
private static void RunTest(ulong t1, Quaternion rot1, ulong t2, Quaternion rot2, ulong t3, Quaternion expectation) { var predictedQuaternion = new PredictedQuaternion(); predictedQuaternion.ReceiveValue(t1, rot1); predictedQuaternion.ReceiveValue(t2, rot2); Assert.AreEqual(0, Quaternion.Angle(expectation, predictedQuaternion.Get(t3))); }