Added simple player disconnect functionality

This commit is contained in:
xethm55 2012-09-28 00:32:05 -04:00
parent 37120edb73
commit f173281614
4 changed files with 58 additions and 2 deletions

View File

@ -14,6 +14,26 @@ Client::Client()
Client::~Client() Client::~Client()
{ {
// Send disconnect message
sf::Packet client_packet;
sf::Uint8 packet_type = PLAYER_DISCONNECT;
client_packet.clear();
client_packet << packet_type;
client_packet << current_player;
m_net_client->sendData(client_packet, true);
// No time out needed here, since the
// message will timeout after a couple of attempts
// then exit anyway.
while(m_net_client->pendingMessages())
{
m_net_client->Receive();
m_net_client->Transmit();
// temporary for now. otherwise this thread consumed way too processing
sf::sleep(sf::seconds(0.005)); // 5 milli-seconds
}
m_net_client->Destroy(); m_net_client->Destroy();
} }
@ -100,13 +120,15 @@ void Client::update(double elapsed_time)
{ {
case PLAYER_CONNECT: case PLAYER_CONNECT:
{ {
sf::Uint32 players_address = 0u;
sf::Uint8 pindex; sf::Uint8 pindex;
std::string name = ""; std::string name = "";
client_packet >> pindex; client_packet >> pindex;
client_packet >> name; client_packet >> name;
client_packet >> players_address;
// Should be a much better way of doing this. // Should be a much better way of doing this.
// Perhaps generate a random number // Perhaps generate a random number
if(name == current_player_name) if((sf::Uint32)((sf::Uint64)(&m_players)) == players_address)
{ {
current_player = pindex; current_player = pindex;
} }
@ -138,7 +160,11 @@ void Client::update(double elapsed_time)
} }
case PLAYER_DISCONNECT: case PLAYER_DISCONNECT:
{ {
// This will remove the player once the disconnect algorithm is implemented sf::Uint8 player_index;
// This completely removes the player from the game
// Deletes member from the player list
client_packet >> player_index;
m_players.erase(player_index);
break; break;
} }
case PLAYER_DEATH: case PLAYER_DEATH:
@ -218,11 +244,17 @@ void Client::update(double elapsed_time)
} }
else if(!registered_player) else if(!registered_player)
{ {
// Needs to be 32 bit so that the packet << overload will work.
sf::Uint32 players_address = (sf::Uint32)((sf::Uint64)(&m_players));
sf::Uint8 packet_type = PLAYER_CONNECT; sf::Uint8 packet_type = PLAYER_CONNECT;
client_packet.clear(); client_packet.clear();
client_packet << packet_type; client_packet << packet_type;
client_packet << current_player; client_packet << current_player;
client_packet << current_player_name; client_packet << current_player_name;
// Send the address of the players map. This will server as a unique
// identifier and prevent users with the same name from controlling
// each other.
client_packet << players_address;
m_net_client->sendData(client_packet, true); m_net_client->sendData(client_packet, true);
registered_player = true; registered_player = true;
} }

View File

@ -388,6 +388,11 @@ void Network::Reset()
message_timer.restart(); message_timer.restart();
} }
bool Network::pendingMessages()
{
return (transmit_queue.size() > 0);
}
sf::Packet& operator <<(sf::Packet& Packet, const Network_Messages_T& NMT) sf::Packet& operator <<(sf::Packet& Packet, const Network_Messages_T& NMT)
{ {
sf::Uint8 net_msg_t = (sf::Uint8)NMT; sf::Uint8 net_msg_t = (sf::Uint8)NMT;
@ -401,3 +406,4 @@ sf::Packet& operator >>(sf::Packet& Packet, Network_Messages_T& NMT)
NMT = (Network_Messages_T)net_msg_t; NMT = (Network_Messages_T)net_msg_t;
return Packet; return Packet;
} }

View File

@ -87,6 +87,7 @@ class Network{
static void Transmit(); static void Transmit();
static void Receive(); static void Receive();
static void Reset(); static void Reset();
static bool pendingMessages();
}; };
sf::Packet& operator <<(sf::Packet& Packet, const Network_Messages_T& NMT); sf::Packet& operator <<(sf::Packet& Packet, const Network_Messages_T& NMT);

View File

@ -58,12 +58,14 @@ void Server::update( double elapsed_time )
{ {
case PLAYER_CONNECT: case PLAYER_CONNECT:
{ {
sf::Uint32 players_address = 0u;
refptr<Player> p = new Player(); refptr<Player> p = new Player();
std::string pname; std::string pname;
sf::Uint8 pindex; sf::Uint8 pindex;
server_packet >> pindex; server_packet >> pindex;
server_packet >> pname; server_packet >> pname;
server_packet >> players_address;
// When a player connects, we need to associate // When a player connects, we need to associate
// that player with a new ID. find first unused id // that player with a new ID. find first unused id
// player zero means a player does not exist. // player zero means a player does not exist.
@ -82,10 +84,12 @@ void Server::update( double elapsed_time )
// Alert all connected clients of all the connected players. // Alert all connected clients of all the connected players.
for(std::map<sf::Uint8, refptr<Player> >::iterator piter = m_players.begin(); piter != m_players.end(); piter++) for(std::map<sf::Uint8, refptr<Player> >::iterator piter = m_players.begin(); piter != m_players.end(); piter++)
{ {
sf::Uint32 paddress = ((piter->first == pindex) ? players_address : 0u);
server_packet.clear(); server_packet.clear();
server_packet << ptype; server_packet << ptype;
server_packet << piter->first; server_packet << piter->first;
server_packet << piter->second->name; server_packet << piter->second->name;
server_packet << paddress;
// Send correct starting locations so that they match // Send correct starting locations so that they match
// the other players screens. // the other players screens.
server_packet << piter->second->direction; server_packet << piter->second->direction;
@ -114,8 +118,21 @@ void Server::update( double elapsed_time )
} }
case PLAYER_DISCONNECT: case PLAYER_DISCONNECT:
{ {
sf::Uint8 pindex;
std::size_t num_erased = 0;
// This completely removes the player from the game // This completely removes the player from the game
// Deletes member from the player list // Deletes member from the player list
server_packet >> pindex;
num_erased = m_players.erase(pindex);
if(1 == num_erased)
{
// Player existed, alert all connected clients.
server_packet.clear();
server_packet << ptype;
server_packet << pindex;
m_net_server->sendData(server_packet, true);
}
break; break;
} }
case PLAYER_DEATH: case PLAYER_DEATH: