I am working on a dash mechanism for 2D multiplayer game in unity with photon fusion. My requirement is that when the player presses LShift, they will move at a lower speed and a UI to charge the slider will be shown. The player can hold LMb to their desired charge and release to dash. Later which I want my player to move with default speed. Also the player by pressing RMb, can cancel the charge on or before charging so that he/she doesn’t dash and move with default speed.
Everything works completely fine expect for the dashing part as it gives a jerky movement especially on the client. The below is the code I have for the same.
using UnityEngine;
using Fusion;
public class Player : NetworkBehaviour
{
public Rigidbody2D PlayerRigidbody;
private float _dashSpeed = DataUtils.DashSpeed; // Speed of the dash
private float _lastDashTime = -Mathf.Infinity;
private Vector2 _movement;
public float minDuration; // Minimum ability duration
public float maxDuration = DataUtils.MaxDashDuration; // Maximum ability duration
public CharacterCanvasBase Canvas;
public override void FixedUpdateNetwork()
{
// player direction input to dash
_movement = DirectionInput;
// below is psuedo code
if (LShiftPressed)
{
StartCoroutine(Dash());
}
}
private IEnumerator Dash()
{
_lastDashTime = Time.time;
Vector2 startDashPosition = PlayerRigidbody.position;
Vector2 dashDirection = _movement.normalized;
// Check if the player is moving. If not, dash downward
if (dashDirection == Vector2.zero)
{
dashDirection = Vector2.down; // Or any default direction you prefer
}
// Get charge level to determine dash speed and possibly duration
float chargeLevel = Canvas.GetComponent<HexCanvas>().ChargeController.GetChargeProgress();
float adjustedDuration = minDuration + (maxDuration - minDuration) * Mathf.Pow(chargeLevel, 2);
float dashEndTime = Time.time + adjustedDuration;
while (Time.time < dashEndTime)
{
float dashProgress = (Time.time - _lastDashTime) / adjustedDuration;
RPC_DashMove(startDashPosition, dashDirection, dashProgress, _dashSpeed * adjustedDuration);
yield return null;
}
}
[Rpc(RpcSources.All, RpcTargets.All)]
public void RPC_DashMove(Vector2 startDashPosition, Vector2 dashDirection, float dashProgress, float dashSpeed)
{
PlayerRigidbody.MovePosition(Vector2.Lerp(startDashPosition, startDashPosition + dashDirection * dashSpeed, dashProgress));
}
}
I tried interpolating the NetworkRigidbody2d component to all the available interpolation data sources(Auto, snapshots, predicted, no interpolation) in photon fusion.
Initially, I have tried DashMove to run locally. But while dashing, the state authority overrides the player position especially on the client. So I made it an RPC. The thing with RPCs is that they’re not tick based instead time based. Potentially, this jerkiness is coz of trying to dash using an RPC.
Later I have also tried making the state authority to handle the dash locally which should be synced across all the clients. But it is snapping the player to the final dash position.
What is the right approach?
levitate is a new contributor to this site. Take care in asking for clarification, commenting, and answering.
Check out our Code of Conduct.