Cast PUN RPC from GameObject to Specific Player.

Options

Hi all!

I am trying to solve a problem I am facing.

I have a "Room" GameObject that listens for an OnTriggerEnter2D when a player enters a room. The server spawns objects and should only enable blocking walls for the client that enters the room. My understanding is that this is because the method I'm trying to call must be on the Player GameObject, but how can I create those blockers if that's the case?

Thank you!

public void OnTriggerEnter2D(Collider2D col)
{
    if (!col.CompareTag("Player")) return;

    PhotonView playerView = col.gameObject.GetPhotonView();

    if (!PhotonNetwork.IsMasterClient || _spawned) return;
    
    playerView.RPC(nameof(ToggleBlockers), playerView.Controller, true);
}

[PunRPC]
public void ToggleBlockers(bool value)
{
    foreach (GameObject wallBlocker in WallBlockers)
        wallBlocker.gameObject.SetActive(value);
}


Answers

  • Tobias
    Options

    I don't know if I follow. Could you elaborate what the goal is?

    I thought: If you need to do something when a new player joins, why don't you just use the OnPlayerJoined callback, which runs everywhere? No need to use an RPC, unless you need some logic to figure out when to actually enable or disable something.

    In general, you might be better off without an RPC. Don't focus on those this much. What you really want is some synced game state telling the players to enable / disable stuff. This is as well or better done with Custom Properties.

  • scala232
    Options

    That was hard. Not the best approach, but works great with my game scale. A lot of code has been cut, keep that in mind.

    public class NetworkRoomAssigner : MonoBehaviour
    {
        public GameObject RoomInitializerPrefab;
    
        private void Start()
        {
            if (!PhotonNetwork.IsMasterClient) return;
            
            GameObject room = PhotonNetwork.Instantiate(RoomInitializerPrefab.name, gameObject.transform.position, Quaternion.identity);
        }
    }
    
    public class RoomInitializer : MonoBehaviour
    {
        private PhotonView _photonView;
    
        private void Start()
        {
           _photonView = PhotonView.Get(this);
        }
    
        public void OnTriggerEnter2D(Collider2D col)
        {      
            if (_enemyCount > 0)
                _photonView.RPC(nameof(ToggleBlockers), col.gameObject.GetPhotonView().Controller, true);
        }
    
        [PunRPC]
        public void ToggleBlockers(bool value)
        {
            GameObject[] WallBlockers = GameObject.FindGameObjectsWithTag("WallBlocker");
    
            foreach (GameObject wallBlocker in WallBlockers)
            {
                wallBlocker.GetComponent<SpriteRenderer>().enabled = value;
                wallBlocker.GetComponent<BoxCollider2D>().enabled = value;
            }
        }
    }