![]() |
Generate a fully connected mesh, while automatically choosing a host based on the longest running system. Peer to peer games typically need one peer to act as a host for unique events. For example, the host may send out game end notifications or may control the AI. FullyConnectedMesh2 can be used to automatically determine the host after connection. Overview:
SetConnectOnNewRemoteConnection(), if true will call RakPeer::Connect() on remote systems when ID_REMOTE_NEW_INCOMING_CONNECTION through the ConnectionGraph2 plugin. However, this usually won't work since most systems are behind routers. Therefore, you will usually manually connect to other systems. SetAutoparticipateConnections() will usually be called with false, because you usually do some type of player validation before accepting a player into a game. Until host calculation has completed, GetHostSystem() will return your own guid and GetConnectedHost() will return UNASSIGNED_RAKNET_GUID. You will get ID_FCM2_NEW_HOST as soon as the host is known. The host will generally be whichever system has been running the longest of all systems added with AddParticipant(). If you immediately have to know who is the host on gameplay start, do not start gameplay until you get ID_FCM2_NEW_HOST at least once. Code example: case ID_NEW_INCOMING_CONNECTION: case ID_CONNECTION_REQUEST_ACCEPTED: { fullyconnectedmesh->AddParticipant(packet->guid); if (fullyconnectedmesh->GetConnectedHost()!=UNASSIGNED_RAKNET_GUID) { // Already know the host, so can add connection to the game immediately AddGameParticipant(packet->guid); } // else do not know host yet, wait for ID_FCM2_NEW_HOST before calling AddGameParticipant() } case ID_FCM2_NEW_HOST: { RakNet::BitStream bs(packet->data,packet->length,false); bs.IgnoreBytes(1); RakNetGUID oldhost; bs.Read(oldhost); // If oldHost is the same as the new host (packet->guid) then this is the first time we got this message if (oldhost==packet->guid) { // Game is ready to start, because we now know the host for the first time SignalGameStart(); // Add as game participants systems previously added to FullyConnectedMesh2 // from ID_NEW_INCOMING_CONNECTION and ID_CONNECTION_REQUEST_ACCEPTED DataStructures::List<RakNetGUID> participantList; fullyconnectedmesh->GetParticipantList(participantList); for (unsigned int i=0; i < participantList.Size(); i++) AddGameParticipant(participantList[i]); } } GetParticipantList() and GetHostOrder() can be used to find out which systems were added with AddParticipant(). If the game does not immediately start networked, you should call ResetHostCalculation() to reinitialize the host timer when network play is now relevant. Otherwise, a user could play a game in single player, connect to a network session, and then be considered the host because his system was running the longest, although he was the last to join the network session. A good time to call ResetHostCalculation() is just before attempting to join a network room or lobby. Reading the host: ID_FCM2_NEW_HOST has the RakNetGUID of the old host encoded in the network stream. The new host is written to the systemAddress and guid members of the Packet. If the old host and new host are the same, then there was no old host (this is the first host calculation). case ID_FCM2_NEW_HOST: { if (packet->guid==rakPeer->GetMyGUID()) printf("Got new host (ourselves)"); else printf("Got new host %s, GUID=%s", packet->systemAddress.ToString(true), packet->guid.ToString()); RakNet::BitStream bs(packet->data,packet->length,false); bs.IgnoreBytes(1); RakNetGUID oldHost; bs.Read(oldHost); // If the old host is different, then this message was due to losing connection to the host. if (oldHost!=packet->guid) printf(". Oldhost Guid=%s\n", oldHost.ToString()); else printf("\n"); } break;See Samples/FCMHost for a demonstration of this plugin |
![]() |