- Home /
Local (non network) camera for multiplayer game
I have followed this (paladinstudio link) tutorial about how making a small multiplaye game.
Now I want each player to control the camera better.
According to this or this answer, the best way to do it is not to create a different camera for each player, but to make the main camera follow your player in a local way.
I do think this is the best way because it limits the number of network components in the game, but there are a few things I can't work out :
If the camera doesn't have any network component (like a photon view), how can it find the player when he gets spawned ?
Since the player is a prefab, the camera cannot have a reference to a player, can it ? In a potential CameraController script I mean.
I work in C#. What scripts can I use and what do these scripts have to be attached to ?
Answer by Kalissar · Jun 14, 2014 at 03:51 PM
I found a way to do it, I hope it's not too ugly. The pros, as said above, is that there is only 1 camera actually instanciated so that, unlike all the other solutions I have come accross, you don't have to disable every other camera/audio source that dioesn't belong to you.
Architecture : MainCamera, with a CameraController script attached. The script has a GameObject target variable.
Only thing left is to assignate this target when the player gets instantiated :
void OnJoinedRoom()
{
Debug.Log("Connected to Room");
// Spawn player
GameObject player = PhotonNetwork.Instantiate(playerPrefab.name, new Vector3 (0.5f, 5.0f, 0.5f), Quaternion.identity, 0);
GameObject camera = GameObject.FindWithTag ("MainCamera");
if (camera != null)
{
CameraController followScript = camera.GetComponent("CameraController") as CameraController;
if (followScript != null){
followScript.target = player;
}
}
}
And here is the cameracontroller script, it's very simple, it was only for some test purpose :
public class CameraController : MonoBehaviour {
public GameObject target;
private Vector3 offset;
// Use this for initialization
void Start () {
offset = transform.position;
}
// Update is called once per frame
void LateUpdate () {
if (target != null){
transform.position = target.transform.position + offset;
}
}
}
Hope it will help some people
Do I also have to place the prefab Player in the component as well? It keeps asking me to assigned the target variable first, because it's unassigned. Thank you for your answer!
EDIT: Yes, you have to place the prefab.
Answer by Aerozo · Jun 14, 2014 at 03:50 PM
If you have a look in the first block of code above the "State Synchronization" title, you'll see:
if (photonView.isMine)
InputMovement();
Essentially if photonView.isMine
is true, it means that this Player object is the one you spawned on the server and that should be your player.
So easiest way to do what you want is it to change the above it to something like this:
if (photonView.isMine) {
InputMovement();
//Find camera and set the camera target to this object
}
Hope this helps, comment if it's unclear.
I thought about this one. Problem with this is that the "find camera and set target to this" would be done every frame, which is not optimal because we need to do it only once. Of course it would work, but i'm trying to work on a clean basis and I really think this is not the way to go.