[英]Player ReSpawn Logic Unity Multiplayer
我正在通过 Unity Multiplayer 系统学习多人游戏实现。 所以我遇到了为初学者编写的非常好的教程: Introduction to a Simple Multiplayer Example
从本教程中,我无法理解此页面内容: Death and Respawning
通过这段代码,他们在教程中谈论我们的玩家将重生(玩家将在 0 position 处转换并且生命值将为 100)并且玩家可以再次开始战斗。
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.Networking;
using System.Collections;
public class Health : NetworkBehaviour {
public const int maxHealth = 100;
[SyncVar(hook = "OnChangeHealth")]
public int currentHealth = maxHealth;
public RectTransform healthBar;
public void TakeDamage(int amount)
{
if (!isServer)
return;
currentHealth -= amount;
if (currentHealth <= 0)
{
currentHealth = maxHealth;
// called on the Server, but invoked on the Clients
RpcRespawn();
}
}
void OnChangeHealth (int currentHealth )
{
healthBar.sizeDelta = new Vector2(currentHealth , healthBar.sizeDelta.y);
}
[ClientRpc]
void RpcRespawn()
{
if (isLocalPlayer)
{
// move back to zero location
transform.position = Vector3.zero;
}
}
}
根据我的想法 -> 所有客户端都在执行 ClientRPC,因此本地玩家的所有设备都将在出生点 position 处移动,并且健康状况会变满。 按照本教程 -> 只有自己的玩家出生点 position 和健康得到更新。
那么为什么会发生我无法理解的事情呢? 实际上,RPC 会调用所有客户端,然后所有客户端都应要求在开始时移动 position 并获得完全健康。 请给我一些解释。
正如您在该图像上看到的,您需要考虑网络系统不是“共享”房间,它们实际上是在您自己房间中复制其他系统的所有内容。 知道了这一点,现在您可以理解,如果从播放器1发送Rpc,则Rpc将在播放器1上执行,而播放器1将在播放器2的房间中复制。
正如您可以在文档上看到的那样,原因是[ClientRpc]属性:
是可以放在NetworkBehaviour类的方法上的属性,以允许从服务器在客户端上调用它们。
因此,由于玩家1房间是主机(服务器+客户端),而玩家2是客户端,则它将在2个房间的主机上执行,但在第一个房间进行评估。
编辑:这意味着,例如,当播放器1死亡时,它将调用RPC函数,并且(因为它是RPC)他在房间2上的副本(Player1-Copy)将执行相同的操作。
根据我的理解,respawnprefab 必须在 ServerRpc 上实例化,实际的重生逻辑(改变玩家的变换)应该在 ClientRpc 中给出。
private void Die()
{
isDead = true;
//Disable Components
for (int i = 0; i < disableOnDeath.Length; i++)
{
disableOnDeath[i].enabled = false;
}
Collider _col = GetComponent<Collider>();
if (_col != null)
{
_col.enabled = false;
}
Debug.Log(transform.name + " is Dead");
//call respawn method
StartCoroutine(Respawn(transform.name));
}
private IEnumerator Respawn(string _playerID)
{
yield return new WaitForSeconds(GameManager.instance.matchSettings.respawnDelay);
SpawningServerRpc(_playerID);
}
[ServerRpc(RequireOwnership = false)]
void SpawningServerRpc(string _playerID)
{
Transform spawnedPointTransform = Instantiate(spawnPoint);
spawnedPointTransform.GetComponent<NetworkObject>().Spawn(true);
SpawnClientRpc(_playerID);
}
[ClientRpc]
void SpawnClientRpc(string _playerID)
{
Player _player = GameManager.GetPlayer(_playerID);
Debug.Log("The player who dies is:" + _player.transform.name);
_player.transform.position = spawnPoint.position;
Debug.Log("I am Respawned" + _player.name + "Position:" + _player.transform.position);
SetDefaults();
}
希望这对你有帮助。 干杯
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.