Thursday, June 9, 2011

Foray into Photon - Part 2

So we have our server up and running with our blank server that does nothing but inform us when we have successfully received an operation. Next we will want to create an empty Unity3d project for us to begin our client. Once you have an empty project, go ahead and create a place for your scenes and scripts. First you will want to create a folder called Plugins. Unity3d looks for this folder and any dlls inside are added as a reference to your project. You will want to go into Photon/lib and find the PhotonUnity3D.dll and drag it into your Plugins folder.

From here you will want to save your scene and add a couple C# scripts: Login and Game.

Since this is a simple client we won't be doing much with it other than connecting to and disconnecting from the server. If you look at the Photon Client Overview you will see that in order to connect to the server you need to implement the IPhotonPeerListener, Create a Peer with the server address, connect, call Service often (10 times/sec according to the doc) So lets do that now.

Lets start with Game. First remove the start and update calls and remove MonoBehavior. We instead want it to inherit from IPhotonPeerListener and we want to go ahead and implement the interface and remove the NotImplementedException code. This will give us 4 functions, DebugReturn, EventAction, OperationResult, and PeerStatusCallback. For now we will leave everything blank except PeerStatusCallback. We want to create a string to hold what our status is and our PhotonPeer for later:


using System;
using ExitGames.Client.Photon;


public class Game : IPhotonPeerListener
{


    PhotonPeer peer;


    public string status = "disconnected";


    public void DebugReturn(DebugLevel level, string message)
    {
    }


    public void EventAction(byte eventCode, System.Collections.Hashtable photonEvent)
    {
    }


    public void OperationResult(byte opCode, int returnCode, System.Collections.Hashtable returnValues, short invocID)
    {
    }


    public void PeerStatusCallback(StatusCode statusCode)
    {
        switch (statusCode)
        {
            case StatusCode.Connect:
                {
                    status = "connected";
                    break;
                }


            case StatusCode.Disconnect:
            case StatusCode.DisconnectByServer:
            case StatusCode.DisconnectByServerLogic:
            case StatusCode.DisconnectByServerUserLimit:
            case StatusCode.TimeoutDisconnect:
                {
                    status = "disconnected";
                    break;
                }


            default:
                {
                    status = "unexpected";
                    break;
                }
        }
    }
}

All this does is receive a status code from Photon any time the connection status changes and puts it in our string for later. Easy enough. Next we will need 3 more functions to handle getting us set up:

    public void Initialize(PhotonPeer peer, string serverAddress, string applicationName)
    {
        this.peer = peer;
        peer.Connect(serverAddress, applicationName);
    }

    public void Disconnect()
    {
        peer.Disconnect();
    }

    public void Update()
    {
        peer.Service();
    }

These functions handle calls we are going to make and they provide us with the other steps the Overview told us we needed to do - call service, call connect, and disconnect when we are done so we free up the connection slot. Initialize will be called by our Login script when we press the connect button on the GUI. Disconnect will be called by OnApplicationQuit. Update will be called by our Update in Login so it'll get called every frame.

Now lets flip over to the login script. First we will need a Game object inside our Login script so we can call those functions later. In Start we will instantiate our Game object, and update will call our Game.Update:

using UnityEngine;
using System.Collections;
using System;
using ExitGames.Client.Photon;

public class Login : MonoBehaviour
{

    Game engine;

    // Use this for initialization
    void Start()
    {
        Application.runInBackground = true;
        engine = new Game();
    }

    // Update is called once per frame
    void Update()
    {
        try
        {
            this.engine.Update();
        }
        catch (Exception e)
        {
            Debug.Log(e);
        }
    }
}

And now that we have Start and Update we need to add our OnGUI and OnApplicationQuit functions:

    ///
    /// The on application quit.
    ///
    public void OnApplicationQuit()
    {
        try
        {
            this.engine.Disconnect();
        }
        catch (Exception e)
        {
            Debug.Log(e);
        }
    }

    public void OnGUI()
    {
        if (GUI.Button(new Rect(100, 60, 100, 30), "Connect"))
        {
            PhotonPeer peer = new PhotonPeer(this.engine, false);

            engine.Initialize(peer, "localhost:5055", "AegisBorn");
        }
        GUI.Label(new Rect(100, 100, 300, 300), engine.status);
    }

OnApplicationQuit just tells our Game to Disconnect, which tells the PhotonPeer to disconnect and drops us from the server.

OnGUI creates a button that when pressed creates a new peer and passes that to our engine and tells the engine to connect to localhost and access the AegisBorn application. It also shows a message that states our status as updated through Game.PeerStatusCallback.

If you run this in unity you will see a button and the program starts as disconnected. when you click the button it will connect to Photon and return a status of connected.

Next time we will begin creating an operation and sending it to the server and updating our status to show when we get a response back from the server.

No comments: