【问题标题】:Clients cannot spawn object on server - Unity mirror networking c#客户端无法在服务器上生成对象 - Unity 镜像网络 c#
【发布时间】:2020-07-06 19:01:38
【问题描述】:

我已经为此苦苦挣扎了一两天了。由于某种原因 NetworkServer.Spawn() 似乎不起作用。据我了解,可以从客户端调用 NetworkServer.Spawn() 以在服务器上生成和对象,并且从服务器上,该对象会在所有客户端上生成。目前,当客户端射击时,它只会出现在该客户端上(而不是在服务器上),而当主机射击时,弹丸会在主机和客户端上生成。

代码顶部有一个 using Mirror 标签,该脚本源自 Networkbehaviour。下面这段代码是在客户端调用的:

void Shoot()
{
        //Spawn porjectile on local machine
        GameObject shot = Instantiate(projectile) as GameObject;

        //Set shot projectile position
        shot.transform.position = projectilePoint.position;
        shot.transform.rotation = transform.rotation;

        //Set projectile component of the shot projectile
        Projectile shotProjectile = shot.GetComponent<Projectile>();

        //Set properties of shot projectile
        shotProjectile.damage = damage;
        shotProjectile.direction = projectilePoint.position - transform.position;
        shotProjectile.speed = projectileTravelSpeed;
        shotProjectile.team = team;
        shotProjectile.shotBy = gameObject;

        NetworkServer.Spawn(shot);
    
}

有没有人知道为什么射弹没有从客户端生成在服务器上?一个代码示例(在 c# 中)也会很有帮助。

【问题讨论】:

标签: c# unity-networking


【解决方案1】:

NetworkServer.Spawn() 只能在服务器上调用。它使GameObject 被发送给所有客户端,因此他们可以看到它,与之交互等等。因此,您需要从客户端调用服务器上的一个函数,该函数将为您提供Spawn() 您的对象。

[Client]
void Shoot()
{
    //Call spawn on server
    CmdShoot(projectile, projectilePoint.position, transform.rotation);
}

[Command]
void CmdShoot(GameObject projectile, Vector3 position, Quaternion rotation)
{

    GameObject shot = Instantiate(projectile) as GameObject;

    //Set shot projectile position
    shot.transform.position = projectilePoint.position;
    shot.transform.rotation = transform.rotation;

    //Set projectile component of the shot projectile
    Projectile shotProjectile = shot.GetComponent<Projectile>();

    //Set properties of shot projectile
    shotProjectile.damage = damage;
    shotProjectile.direction = projectilePoint.position - transform.position;
    shotProjectile.speed = projectileTravelSpeed;
    shotProjectile.team = team;
    shotProjectile.shotBy = gameObject;

    NetworkServer.Spawn(shot);
    RpcOnShoot();
}

[ClientRpc]
void RpcOnShoot()
{
    //Called on all clients
}

或者调用NetworkServer.SpawnWithClientAuthority(),如果你希望实例化对象具有客户端权限(然后客户端需要设置shotProjectiles属性)。

【讨论】:

  • RpcOnShoot() 中有什么内容?是否有必要,或者命令会自动为每个客户端创建对象?
  • RpcOnShoot() 具有 [ClientRpc] 属性,因此在服务器上调用时会在所有客户端上调用(也可以仅从服务器调用)。如果您想在实例化之后立即做某事,这不是必需的,但很有用。是的,虽然它将在服务器上实例化,但在调用 NetworkServer.Spawn(shot) 之后,该对象将在每个客户端上创建。
  • 是否真的可以传递一个游戏对象,如 CmdShoot(GameObject projectile, Vector3 position, Quaternion rotation)?无论我做什么,projectile 在服务器端都是一个空引用。
猜你喜欢
  • 2020-12-15
  • 1970-01-01
  • 2012-11-05
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-06-22
  • 1970-01-01
  • 2012-04-26
相关资源
最近更新 更多