Writing a kNet Client

Writing a kNet Client

To write a client application for kNet, proceed through the following steps:

  1. include "kNet.h". Make sure this include is positioned before include <windows.h>, or alternatively add a project-wide define _WINSOCKAPI_. See WS2Include.h for more details.
  2. Instantiate a Network object. Make sure this object stays alive for the duration that the server is running.
  3. Define a class that implements the IMessageHandler interface. See MessageConnection Event Listener for more details.
  4. Connect to a kNet server by calling Network::Connect. You need to know the hostname and listen port of the server, as well as whether the server is in TCP or UDP mode. This method immediately returns a MessageConnection object, but that connection might not have been established yet.
  5. a) Polled mode:Drive the application through your own main client loop, and periodically call MessageConnection::ProcessMessages to receive new data from the server.
    b) Event mode: Call MessageConnection::RunModalClient to have the MessageConnection object start up its own event-based processing loop. It will notify about new connections through the listener object your registered when connecting. To return from the event loop, call MessageConnection::Disconnect.

MessageConnection Event Listener

For each MessageConnection that is created, the application needs to associate a listener object to manage the messages that are received.

When a new message comes in from the other end of the connection, the MessageConnection worker thread places it into an internal message queue. To process this queue, the application should periodically call MessageConnection::ProcessMessages. This will cause IMessageHandler::HandleMessage to be called for each message in the queue, after which the message is destroyed.

This concept of processing incoming messages through a message listener is demonstrated in the next sample.

A Client Application Example

HelloClient.cpp: An example client that connects to a server to read a "Hello" string. See A Server Application Example for the matching server code.
#include "kNet.h"

// Define a MessageID for our a custom message.
const message_id_t cHelloMessageID = 10;

// This object gets called whenever new data is received.
class MessageListener : public IMessageHandler
{
public:
   void HandleMessage(MessageConnection *source, message_id_t id, const char *data, size_t numBytes)
   {
      if (id == cHelloMessageID)
      {
         // Read what we received. 
         DataDeserializer dd(data, numBytes);
         std::cout << "Server says: " << dd.ReadString() << std::endl;
         
         source->Disconnect();
      } 
   }
};

int main(int argc, char **argv)
{
   if (argc < 2)
   {
      std::cout << "Usage: " << argv[0] << " server-ip" << std::endl;
      return 0;
   }
   Network network;
   MessageListener listener;
   const unsigned short cServerPort = 1234;
   MessageConnection *connection = network.Connect(argv[1], cServerPort, SocketOverUDP, &listener);

   // Run the main client loop.
   connection->RunModalClient();
   
   return 0;
}
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines