private void SimulateFromStateInterpolationHermite(StateMessage LastStateMsg, StateMessage CurrentStateMsg) { //Debug.Log("hermite ~!"); float speedof = 6f; journeyLength = Vector3.Distance(LastStateMsg.getPosition(), CurrentStateMsg.getPosition()); float distCovered = Vector3.Distance(LastStateMsg.getPosition(), cube_rigidbody.position); float fractionOfJourney = (distCovered / journeyLength); if ((fractionOfJourney + 0.1f) < 1) { //Debug.Log(" fract of journey " + fractionOfJourney); fractionOfJourney += 0.1f; Vector3 hermite = Hermite(LastStateMsg.getPosition(), CurrentStateMsg.getPosition(), fractionOfJourney); Debug.Log("my postion " + transform.position + " hermite postion " + hermite + " goal " + CurrentStateMsg.getPosition() + " dist coverd " + distCovered + " fract of journey " + fractionOfJourney); cube_rigidbody.position = hermite; } else { fractionOfJourney = 1f; Debug.Log("my postion " + transform.position + " hermite postion " + CurrentStateMsg.getPosition() + " goal " + CurrentStateMsg.getPosition() + " dist coverd " + distCovered + " fract of journey " + fractionOfJourney); cube_rigidbody.position = CurrentStateMsg.getPosition(); } //transform.position = hermite; cube_rigidbody.rotation = Quaternion.Slerp(LastStateMsg.getRotation(), CurrentStateMsg.getRotation(), Time.time * speedof); //cube_rigidbody.velocity = Hermite(LastStateMsg.getVelocity(), CurrentStateMsg.getVelocity(), fractionOfJourney); cube_rigidbody.velocity = CurrentStateMsg.getVelocity(); cube_rigidbody.angularVelocity = CurrentStateMsg.getVelocity_Angular(); }
private void SimulateInterpolationHermite4(float interpolationFraction) { // if (InterpolationBuffer.Count >= 3 && !interpolationg) { SM1.setPosition(cube_rigidbody.position); SM1.setRotation(cube_rigidbody.rotation); SM1.setVelocity_Ang(cube_rigidbody.angularVelocity); SM2 = InterpolationBuffer.Dequeue(); SM3 = InterpolationBuffer.Dequeue(); SM4 = InterpolationBuffer.Dequeue(); journeyLength = interpolationFraction; Debug.Log("Interpolation starts sm1 " + SM1.getPosition() + "sm2 " + SM2.getPosition() + "sm3 " + SM3.getPosition() + "sm4 " + SM4.getPosition() + "buffer size " + InterpolationBuffer.Count); interpolationg = true; } if (interpolationg) { Vector3 IntPos = Hermite4(SM1.getPosition(), SM2.getPosition(), SM3.getPosition(), SM4.getPosition(), journeyLength); //Debug.Log("Interpolation in sm1 " + SM1.getPosition() + "sm2 " + SM2.getPosition() + "sm3 " + SM3.getPosition() + "sm4 " + SM4.getPosition()); Debug.Log("my postion " + cube_rigidbody.position + " hermite postion " + IntPos + " goal " + SM4.getPosition() + " fract of journey " + journeyLength); cube_rigidbody.position = IntPos; if (journeyLength >= 1f) { interpolationg = false; } else if (journeyLength >= 0.66f) { cube_rigidbody.rotation = Quaternion.Slerp(SM3.getRotation(), SM4.getRotation(), ((journeyLength - 0.66f) / 0.33f)); cube_rigidbody.velocity = SM3.getVelocity(); cube_rigidbody.angularVelocity = SM3.getVelocity_Angular(); } else if (journeyLength >= 0.33f) { cube_rigidbody.rotation = Quaternion.Slerp(SM2.getRotation(), SM3.getRotation(), ((journeyLength - 0.33f) / 0.33f)); cube_rigidbody.velocity = SM2.getVelocity(); cube_rigidbody.angularVelocity = SM2.getVelocity_Angular(); } else if (journeyLength >= 0.0f) { cube_rigidbody.rotation = Quaternion.Slerp(SM1.getRotation(), SM2.getRotation(), (journeyLength / 0.33f)); cube_rigidbody.velocity = SM1.getVelocity(); cube_rigidbody.angularVelocity = SM1.getVelocity_Angular(); } journeyLength += interpolationFraction; } }
private void SimulateFromState(StateMessage stateMessage) //spróbuj zrobić dla state { cube_rigidbody.position = stateMessage.getPosition(); cube_rigidbody.rotation = stateMessage.getRotation(); cube_rigidbody.velocity = stateMessage.getVelocity(); cube_rigidbody.angularVelocity = stateMessage.getVelocity_Angular(); this.timer += Time.deltaTime; while (this.timer >= Time.fixedDeltaTime) { this.timer -= Time.fixedDeltaTime; this.AddForcesToPlayer(currentInput); Physics.Simulate(Time.fixedDeltaTime); tick_number++; } }
void RewindState() { if (newStateMessages.Count > 0) { while (newStateMessages.Count != 0) { StateMessage state_msg = newStateMessages.Dequeue(); //uint buffer_slot = state_msg.tick_number % (uint)history.Count; Vector3 position_error = new Vector3(); position_error = state_msg.getPosition() - unConfirmedPredictions.Peek().getPosition(); float rotation_error = 1.0f - Quaternion.Dot(state_msg.getRotation(), unConfirmedPredictions.Peek().getRotation()); if (position_error.sqrMagnitude > 0.0000001f || rotation_error > 0.00001f) { // capture the current predicted pos for smoothing Vector3 prev_pos = cube_rigidbody.position + this.client_pos_error; Quaternion prev_rot = cube_rigidbody.rotation * this.client_rot_error; // rewind & replay Debug.Log("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! rewind"); cube_rigidbody.position = state_msg.getPosition(); cube_rigidbody.rotation = state_msg.getRotation(); cube_rigidbody.velocity = state_msg.getVelocity(); cube_rigidbody.angularVelocity = state_msg.getVelocity_Angular(); int rewind_tick_number = (int)state_msg.tick_number; while (rewind_tick_number < tick_number) { StateMessage replay = unConfirmedPredictions.Dequeue(); AddForcesToPlayer(replay.getInput()); //for smoothig not applay dirrectly Physics.Simulate(Time.fixedDeltaTime); if (rewind_tick_number != state_msg.tick_number) { replay.setPosition(transform.position); replay.setRotation(transform.rotation); history.Add(replay); unConfirmedPredictions.Enqueue(replay); } ++rewind_tick_number; } // if more than 2ms apart, just snap if ((prev_pos - cube_rigidbody.position).sqrMagnitude >= 4.0f) { this.client_pos_error = Vector3.zero; this.client_rot_error = Quaternion.identity; } else { this.client_pos_error = prev_pos - cube_rigidbody.position; this.client_rot_error = Quaternion.Inverse(cube_rigidbody.rotation) * prev_rot; } } } } }
private void PredictCorrection() { if (newStateMessages.Count > 0) { StateMessage server_state = newStateMessages.Dequeue(); StateMessage client_state = unConfirmedPredictions.Dequeue(); if (bufferpurge) { if (client_state.tick_number != server_state.tick_number || newStateMessages.Count > 5) { float skipped_packs = 0; if (client_state.tick_number == server_state.tick_number) { Debug.Log("cool"); } if (newStateMessages.Count > 5) //purging buffer { while (newStateMessages.Count > 5) { server_state = newStateMessages.Dequeue(); } while (unConfirmedPredictions.Count > 5) { history.Add(client_state); client_state = unConfirmedPredictions.Dequeue(); } for (int i = 0; i < unConfirmedPredictions.Count; i++) { if (client_state.tick_number <= server_state.tick_number) { Debug.Log("found sam number"); break; } history.Add(client_state); client_state = unConfirmedPredictions.Dequeue(); } } } } float distance = Vector3.Distance(server_state.getPosition(), client_state.getPosition()); if (distance > 0.25f) { client_rot_error = Quaternion.Inverse(client_state.getRotation()) * server_state.getRotation(); client_pos_error = server_state.getPosition() - client_state.getPosition(); float lerpPercent = 0.1f; if (!bufferpurge) { lerpPercent = unConfirmedPredictions.Count / 5; if (lerpPercent > 1) { lerpPercent = Mathf.Ceil(lerpPercent); lerpPercent = 0.1f / lerpPercent; } else { lerpPercent = 0.1f; } } Quaternion rotation_correction = Quaternion.Slerp(Quaternion.identity, client_rot_error, lerpPercent); Vector3 correction = Vector3.Lerp(Vector3.zero, client_pos_error, lerpPercent); cube_rigidbody.position += correction; cube_rigidbody.rotation *= rotation_correction; cube_rigidbody.velocity = server_state.getVelocity(); cube_rigidbody.angularVelocity = server_state.getVelocity_Angular(); } else { //snap cube_rigidbody.position = server_state.getPosition(); cube_rigidbody.rotation = server_state.getRotation(); history.Add(client_state); //correcto } } }