Bad collision detection in client's view when using Networking (Mirror)
Hi there!
I'm a programmer on amateur level trying to make a multiplayer online game. So I downloaded Mirror from Asset store. In their Pong example I sometimes noticed that the ball doesn't bounce right away from the racket in the clients view. Instead it get's stuck for a while inside the racket which happens when you hit the ball with the short side of the racket while moving (sorry, not so clear in the first image although I've made the racket and ball bigger and transparent so it's easier to see). On the other hand, if you hit the ball in the host's view it bounces off as predicted (see image). Is there anything one could do to get better collision detection?
Details: The racket's collision detection is set on continues and the ball's collision detection is set on discreet. Changing them doesn't fix the problem. Sync interval is set on 0 for both ball and racket.
Images:
// BALL'S SCRIPT
using UnityEngine;
namespace Mirror.Examples.Pong { public class Ball : NetworkBehaviour { public float speed = 30; public Rigidbody2D rigidbody2d;
public override void OnStartServer()
{
base.OnStartServer();
// only simulate ball physics on server
rigidbody2d.simulated = true;
// Serve the ball from left player
rigidbody2d.velocity = Vector2.right * speed;
}
float HitFactor(Vector2 ballPos, Vector2 racketPos, float racketHeight)
{
// ascii art:
// || 1 <- at the top of the racket
// ||
// || 0 <- at the middle of the racket
// ||
// || -1 <- at the bottom of the racket
return (ballPos.y - racketPos.y) / racketHeight;
}
// only call this on server
[ServerCallback]
void OnCollisionEnter2D(Collision2D col)
{
// Note: 'col' holds the collision information. If the
// Ball collided with a racket, then:
// col.gameObject is the racket
// col.transform.position is the racket's position
// col.collider is the racket's collider
// did we hit a racket? then we need to calculate the hit factor
if (col.transform.GetComponent<Player>())
{
// Calculate y direction via hit Factor
float y = HitFactor(transform.position,
col.transform.position,
col.collider.bounds.size.y);
// Calculate x direction via opposite collision
float x = col.relativeVelocity.x > 0 ? 1 : -1;
// Calculate direction, make length=1 via .normalized
Vector2 dir = new Vector2(x, y).normalized;
// Set Velocity with dir * speed
rigidbody2d.velocity = dir * speed;
}
}
}
}
// RACKET'S SCRIPT
using UnityEngine;
namespace Mirror.Examples.Pong
{
public class Player : NetworkBehaviour
{
public float speed = 30;
public Rigidbody2D rigidbody2d;
// need to use FixedUpdate for rigidbody
void FixedUpdate()
{
// only let the local player control the racket.
// don't control other player's rackets
if (isLocalPlayer)
rigidbody2d.velocity = new Vector2(0, Input.GetAxisRaw("Vertical")) * speed * Time.fixedDeltaTime;
}
}
}