Unity Photon WASD working but Virtual Joystick won't work after another player has joined the network...? How can i sync joystick.

``**PlayerController
`public class PlayerController : MonoBehaviour
{ //Photon.MonoBehaviour
private GameObject sceneCam;
public GameObject plCamera;
public GameObject joystick;
public GameObject pistolObject;
public float walkSpeed = 30f;
Rigidbody2D _rigidbody2D;
Vector2 rot;
Vector2 vector;
Quaternion rotation;
PhotonView photonView;

void Start () 
{
    
}

void Awake()
{
    _rigidbody2D = gameObject.GetComponent<Rigidbody2D>();
    photonView = GetComponent<PhotonView>();
    _tr = gameObject.GetComponent<Transform>();

    if(photonView.isMine)
    {
    sceneCam = GameObject.Find("MainCamera");

    //joystick = GameObject.Find("JoystickCanvas");
    //joystick.SetActive(true);
    //sceneCam.SetActive(false);
    //plCamera.SetActive(true);
    GetComponent<PlayerController>().enabled = true;
    }
    photonView = GetComponent<PhotonView>();
}

void Update () 
{
    Movement();
    if (photonView.isMine)
    {
    Debug.Log("photonView Working");
    }
}

void FixedUpdate()
{
    Movement();
    if(photonView.isMine == false )
    {
        return;
    }
    Move(vector, rotation);
    Rotate(rotation);
}

private void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info)
{
if(stream.isWriting)
{
Debug.Log(“OnPhotonSerializeView”);
stream.SendNext(transform.position);
stream.SendNext(transform.rotation);
stream.SendNext(walkSpeed);
stream.SendNext(_rigidbody2D.position);
stream.SendNext(_rigidbody2D.rotation);
stream.SendNext(_rigidbody2D.velocity);
}
else
{
Debug.Log(“OnPhotonSerializeView”);
vector = (Vector3)stream.ReceiveNext();
rotation = (Quaternion)stream.ReceiveNext();
walkSpeed = (float)stream.ReceiveNext();

    transform.position = (Vector3)stream.ReceiveNext ();
    transform.rotation = (Quaternion)stream.ReceiveNext ();
}

}

public void Move(Vector2 vector, Quaternion rotation)
{
    
    
    rot = vector ;
    if (rot != Vector2.zero)
        _rigidbody2D.AddForce(rot * walkSpeed, ForceMode2D.Force);

    gameObject.transform.rotation = rotation;
    
}

public void Rotate(Quaternion rotation)
{
    pistolObject.transform.rotation = rotation;
}

JOYSTICK CODE

**using UnityEngine;
using System.Collections;
using System.Collections.Generic;

public class TouchController : MonoBehaviour {

[HideInInspector]
public PlayerController playerController;
public LeftJoystick leftJoyStick;
public RightJoystick rightJoyStick;

void Start () {
    Input.multiTouchEnabled = true;
}
void Update () {
    MovingControllerUpdate();
    RotatingControllerUpdate();
}
public void MovingControllerUpdate() {

    Vector2 p = leftJoyStick.GetInputDirection();
    if ((p.x > -0.2f && p.x < 0.2) && (p.y > -0.2f && p.y < 0.2))
        return;

    float angle = Mathf.Atan(p.y / p.x) * Mathf.Rad2Deg;
    if (p.x < 0)
    {
        if (p.y < 0)
        {
            angle -= 180;
        }
        else
        {
            angle += 180;
        }
    }
    //playerController.Shoot();

    //Debug.Log("Angle : " + angle + " sw : " + Screen.width + " mw : " + Input.mousePosition.x);

    playerController.Move(leftJoyStick.GetInputDirection(), Quaternion.AngleAxis(angle, Vector3.forward)); 
}
public void RotatingControllerUpdate()
{
    Vector2 p = rightJoyStick.GetInputDirection();
    if ((p.x > -0.2f && p.x < 0.2) && (p.y > -0.2f && p.y < 0.2))
        return;
    
    float angle = Mathf.Atan(p.y / p.x) * Mathf.Rad2Deg;
    if (p.x < 0)
    {
        if (p.y < 0)
        {
            angle -= 180;
        }
        else
        {
            angle += 180;
        }
    }
    //playerController.Shoot();

    //Debug.Log("Angle : " + angle + " sw : " + Screen.width + " mw : " + Input.mousePosition.x);
    playerController.Rotate(Quaternion.AngleAxis(angle, Vector3.forward));
    

}

}

Hi,

I’m not sure how to describe the problems I have seen in the code snippets, so I’m trying to describe how you can set up the scripts to make it work.

First thing is, that you should check the isMine condition of the PhotonView component, whenever you handle Input. An example related to your code snippets:

public void Update()
{
    if (!photon.isMine)
        return;

    Move();
    Rotate();
}

Checking the isMine condition makes sure, that only Input from the Owner of the object gets processed.

The next is about synchronizing the object. Here you basically have two options. The first one is - as far as I can see - what you tried in the first code snippet: using RPCs. When using this approach, you are using the PhotonView component and call the RPC(...) function which calls a certain function in the same script on the same object. When using PUN, this function needs to have the [PunRPC] attribute. An example:

// RPC somewhere in code
photonView.RPC("DoSomething", PhotonTargets.Others);

// Function that gets called
[PunRPC]
public void DoSomething() { }

This way you basically can do the synchronization. There is however a more elegant way to do this by adding a PhotonTransformView component (or a custom OnPhotonSerializeView solution) which is observed by the PhotonView component. Using the PhotonTransformView component also has the advantage of integrated Inter- and Extrapolation options you can take a look at.

in my case , playerController become null after other player joined. It happened because current player object is refreshed by new joined player object. there is work around that check playerController is null before use . if null add reference of playerController again.