Позвольте мне сначала сказать, что я новичок в Unity и особенно в сетях.
Итак, в течение нескольких недель я пробовал несколько разных способов заставить это работать, но я действительно не могу понять это. Я также борюсь с командами и RPC, поэтому я действительно не знаю, как их правильно использовать.
То, что я хотел бы спросить, - как мне заставить мой объект игрока и соответствующие объекты, которые появляются вместе с ним, появляться и правильно заполнять все ссылки на переменные?
Как и в случае, когда я хочу, чтобы объект порождался, порождают реального контролируемого игрока, и все скрипты получают информацию, необходимую для функционирования, и я хочу, чтобы это происходило несколько раз для разных игроков.
В настоящее время происходит то, что все работает идеально для хоста, включая просмотр правильных переменных в нужных местах для клиента, но все для клиента в основном не работает. Они не могут двигаться, атаковать, видеть изменение собственного имени объекта и т. Д., Но они могут видеть перемещение хоста.
Я пробовал несколько разных способов сделать это с переменным провалом. Некоторые позволяют игроку двигаться, но не атаковать, некоторые просто не работают вообще. Я посмотрел на довольно много угроз на RPC против команд и на то, как они работают, и я все это понимаю
Поскольку я несколько раз пытался переделать это, это может показаться беспорядком.
Следующее - самое близкое, что я могу сделать, что хочу. Камеры - проблема в этом, так как игроки запутываются, какую камеру им следует использовать, но у меня было лучше в предыдущей. Я пропустил материал, который не нуждается в исправлении или не имеет отношения к основной проблеме.
Мой скрипт игрока
public class Player : NetworkBehaviour {
[SerializeField]
GameManager managerRef;
bool spawned;
public string idName;
public GameObject mySword;
public GameObject myShield;
public GameObject myCamera;
public GameObject myPlayer;
void Start() {
if (isLocalPlayer) {
managerRef = FindObjectOfType<GameManager>();
spawned = false;
CmdCallCounter();
CmdRegCam();
}
}
private void Update() {
managerRef = FindObjectOfType<GameManager>();
if (isServer) {
if (Input.GetKeyDown(KeyCode.L)) {
CmdStartGame();
}
}
if (isLocalPlayer && !spawned) {
if (managerRef.canSpawn) {
spawned = true;
CmdSpawn(this.gameObject, idName);
}
}
[Command]
public void CmdSpawn(GameObject connection, string id) {
//Player
GameObject go = Instantiate(managerRef.playerPrefab);
go.name = "Warrior" + id;
NetworkServer.SpawnWithClientAuthority(go, connection);
myPlayer = ClientScene.FindLocalObject(go.GetComponent<NetworkIdentity>().netId);
//Sword
if (managerRef.sword != null) {
GameObject goSword = Instantiate(managerRef.sword);
goSword.name = managerRef.sword.name + id;
NetworkServer.SpawnWithClientAuthority(goSword, connection);
mySword = ClientScene.FindLocalObject(goSword.GetComponent<NetworkIdentity>().netId);
CmdDisableObject(goSword);
} else {
Debug.LogError("No sword found");
}
//Shield
if (managerRef.shield != null) {
GameObject goShield = Instantiate(managerRef.shield);
goShield.name = managerRef.shield.name + id;
NetworkServer.SpawnWithClientAuthority(goShield, connection);
myShield = ClientScene.FindLocalObject(goShield.GetComponent<NetworkIdentity>().netId);
;
} else {
Debug.LogError("No shield found");
}
managerRef.RpcCheckVars(
this.gameObject.GetComponent<NetworkIdentity>(),
mySword.GetComponent<NetworkIdentity>(),
myShield.GetComponent<NetworkIdentity>(),
myPlayer.GetComponent<NetworkIdentity>(),
myCamera.GetComponent<NetworkIdentity>()
);
}
[Command]
public void CmdRegCam() {
myCamera = Instantiate(managerRef.cameraPrefab);
NetworkServer.SpawnWithClientAuthority(myCamera, this.gameObject);
NetworkIdentity cameraID = myCamera.GetComponent<NetworkIdentity>();
managerRef.RpcRegisterCam(cameraID, this.gameObject.GetComponent<NetworkIdentity>());
}
[Command]
public void CmdCallCounter() {
managerRef.RpcRenameMe(this.gameObject.GetComponent<NetworkIdentity>().netId);
idName = managerRef.counter.ToString();
}
[Command]
public void CmdStartGame() {
managerRef.canSpawn = true;
}
}
Мой менеджер скриптов
public class GameManager : NetworkBehaviour {
public GameObject sword;
public GameObject shield;
public GameObject playerPrefab;
public GameObject cameraPrefab;
[SyncVar]
public int counter;
[SyncVar]
public float timer;
[SyncVar]
public bool canSpawn;
private void Start() {
counter = 0;
timer = 0;
canSpawn = false;
}
void Update() {
if (isServer) {
timer += Time.deltaTime;
}
}
[ClientRpc]
public void RpcRenameMe(NetworkInstanceId thePlayerID) {
counter++;
GameObject player = NetworkServer.FindLocalObject(thePlayerID);
player.name = player.name + counter.ToString();
player.GetComponent<Player>().idName = counter.ToString();
}
[ClientRpc]
public void RpcCheckVars(NetworkIdentity playerID, NetworkIdentity swordID, NetworkIdentity shieldID, NetworkIdentity crawlerID, NetworkIdentity cameraID) {
GameObject player = NetworkServer.FindLocalObject(playerID.netId);
Player playerVars = player.GetComponent<Player>();
Debug.Log(player.gameObject.transform.name);
GameObject swordVars = NetworkServer.FindLocalObject(swordID.netId);
swordVars.GetComponent<AimWeapon>().playerRef = playerVars;
GameObject shieldVars = NetworkServer.FindLocalObject(shieldID.netId);
shieldVars.GetComponent<ShieldAim>().playerRef = playerVars;
Debug.Log(playerVars.mySword.name);
GameObject crawlerVars = NetworkServer.FindLocalObject(crawlerID.netId);
GameObject camera = NetworkServer.FindLocalObject(cameraID.netId);
crawlerID.GetComponent<BasicCrawler>().camera = camera;
crawlerID.GetComponent<BasicCrawler>().playerRef = player;
camera.GetComponent<CameraMove>().myPlayer = playerVars.myPlayer;
//find id of warrior
GameObject warriorObject = NetworkServer.FindLocalObject(crawlerID.netId);
warriorObject.GetComponent<WarriorCombat>().sword = playerVars.mySword.GetComponent<Rigidbody>();
warriorObject.GetComponent<WarriorCombat>().shield = playerVars.myShield.GetComponent<Rigidbody>();
warriorObject.GetComponent<WarriorCombat>().playerRef = playerVars;
//the variables I need set
//sword playerref
//shield playerref
//basiccrawler camera
//basiccrawler playerref
//camera myplayerref
//warriorcombat-
//sword
//shield
//playerref
}
[ClientRpc]
public void RpcRegisterCam(NetworkIdentity cameraID, NetworkIdentity playerID) {
GameObject camera = NetworkServer.FindLocalObject(cameraID.netId);
GameObject player = NetworkServer.FindLocalObject(playerID.netId);
player.GetComponent<Player>().myCamera = camera;
camera.name = camera.name + counter.ToString();
}
}
Я ожидал, что мои игроки получат переменные, отправленные в их сценарии, и все они будут работать как хост, но в настоящее время они не могут ни двигаться, ни делать что-либо, и в этой конкретной итерации они наблюдают за камерой хоста, тогда как Хост наблюдает за неподвижной камерой новейшего клиента.
РЕДАКТИРОВАТЬ: Bump