Very simple IPunObservable throwing InvalidCastException

Hello.. I've been working on this problem for a few hours now but can't quite seem to find a solution. As the title states, I have a script in my basic car racing game with a very simple implementation of IPunObservable. It has a single stream variable (int), and it's throwing an InvalidCastException.

The code:
public class CarController : MonoBehaviourPun, IPunObservable
{
    public int currentLap;

    public void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info)
    {
        if (stream.IsWriting)
        {
            stream.SendNext(currentLap);
        }
        else
        {
            this.currentLap = (int)stream.ReceiveNext();
        }
    }
}

The error:
InvalidCastException: Specified cast is not valid.
CarController.OnPhotonSerializeView (Photon.Pun.PhotonStream stream, Photon.Pun.PhotonMessageInfo info) (at Assets/Scripts/CarController.cs:356)

Line 356 being:
this.currentLap = (int)stream.ReceiveNext();

From what I can see, I'm using PUN 2.30.

I cut out a lot of the guts of the code as I felt they weren't necessary to discuss the issue. Does anyone have a good idea of what I could be doing wrong here? Thank you for any help.

Comments

  • pixelknight
    edited June 2021
    I made a few changes to the code, and managed to get the problem to subside for now. I don't know the ACTUAL answer to this issue, however I can provide what I did to fix it.

    I ended up creating an entirely new class called RaceStats to isolate the issue. It still implements IPunObservable.
    public class RaceStats : MonoBehaviourPun, IPunObservable
    {
    

    I made currentLap into a private variable, and added SerializeField so that I could watch it in the inspector.
    [SerializeField] int currentLap;
    

    In my update statement, I wrapped the code which defines currentLap in a photonView.IsMine checker, which my previous implementation did, so I don't think this was the solution, I just wanted to make sure.
    // Update is called once per frame
        void Update()
        {
            if (photonView.IsMine)
            {
                currentLap = gameObject.GetComponent<CarController>().currentLap;
            }
        }
    

    The serialization code didn't change.
    public void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info)
        {
            if (stream.IsWriting)
            {
                stream.SendNext(currentLap);
            }
            else
            {
                this.currentLap = (int)stream.ReceiveNext();
            }
        }
    

    I haven't officially tested private vs public variables in the stream but will most likely edit the post when I do so. From what I can see, it seems that that would be the only solution to my problem because besides moving to a new class, it was the only thing that I changed.
  • You could run the debugger attached to Unity and it will break on the error. Look up what's in the stream instead of an Int. This may give you a hint where you sent this value and why it's not an int.
  • Tobias wrote: »
    You could run the debugger attached to Unity and it will break on the error. Look up what's in the stream instead of an Int. This may give you a hint where you sent this value and why it's not an int.

    For sure. Thank you for your input. I remember switching it to float to see what was going on and when I printed the stream object it ended up showing some float value like "7.043" or something (I was streaming the MPH of the vehicle). Still was having the same error casting to (float) but if I come across this issue again i wll do as you suggested thank you.