Synchronize on network game start, so that everyone has received all avatars and player names before the game starts. Store all computer players in a separate list on the server for name retrieval.
This commit is contained in:
@@ -395,16 +395,6 @@ AbstractClientStateReceiving::Process(ClientThread &client)
|
||||
NetPacketPlayerInfo::Data infoData;
|
||||
tmpPacket->ToNetPacketPlayerInfo()->GetData(infoData);
|
||||
client.SetPlayerInfo(infoData.playerId, infoData.playerInfo);
|
||||
// Retrieve avatar if needed.
|
||||
if (infoData.playerInfo.hasAvatar && !client.GetAvatarManager().HasAvatar(infoData.playerInfo.avatar))
|
||||
{
|
||||
boost::shared_ptr<NetPacket> retrieveAvatar(new NetPacketRetrieveAvatar);
|
||||
NetPacketRetrieveAvatar::Data retrieveAvatarData;
|
||||
retrieveAvatarData.requestId = infoData.playerId;
|
||||
retrieveAvatarData.avatar = infoData.playerInfo.avatar;
|
||||
static_cast<NetPacketRetrieveAvatar *>(retrieveAvatar.get())->SetData(retrieveAvatarData);
|
||||
client.GetSender().Send(client.GetContext().GetSocket(), retrieveAvatar);
|
||||
}
|
||||
}
|
||||
else if (tmpPacket->ToNetPacketRemovedFromGame())
|
||||
{
|
||||
@@ -651,33 +641,9 @@ ClientStateWaitGame::InternalProcess(ClientThread &client, boost::shared_ptr<Net
|
||||
{
|
||||
int retVal = MSG_SOCK_INTERNAL_PENDING;
|
||||
|
||||
if (packet->ToNetPacketGameStart())
|
||||
if (packet->ToNetPacketStartEvent())
|
||||
{
|
||||
// Start the network game as client.
|
||||
NetPacketGameStart::Data gameStartData;
|
||||
packet->ToNetPacketGameStart()->GetData(gameStartData);
|
||||
|
||||
client.SetStartData(gameStartData.startData);
|
||||
|
||||
// Set player numbers using the game start data slots.
|
||||
NetPacketGameStart::PlayerSlotList::const_iterator slot_i = gameStartData.playerSlots.begin();
|
||||
NetPacketGameStart::PlayerSlotList::const_iterator slot_end = gameStartData.playerSlots.end();
|
||||
int num = 0;
|
||||
|
||||
while (slot_i != slot_end)
|
||||
{
|
||||
unsigned playerId = (*slot_i).playerId;
|
||||
boost::shared_ptr<PlayerData> tmpPlayer = client.GetPlayerDataByUniqueId(playerId);
|
||||
if (!tmpPlayer.get())
|
||||
throw ClientException(ERR_NET_UNKNOWN_PLAYER_ID, 0);
|
||||
tmpPlayer->SetNumber(num);
|
||||
|
||||
++num;
|
||||
++slot_i;
|
||||
}
|
||||
|
||||
client.SetState(ClientStateWaitHand::Instance());
|
||||
retVal = MSG_NET_GAME_CLIENT_START;
|
||||
client.SetState(ClientStateSynchronizeStart::Instance());
|
||||
}
|
||||
else if (packet->ToNetPacketPlayerJoined())
|
||||
{
|
||||
@@ -719,6 +685,103 @@ ClientStateWaitGame::InternalProcess(ClientThread &client, boost::shared_ptr<Net
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
ClientStateSynchronizeStart &
|
||||
ClientStateSynchronizeStart::Instance()
|
||||
{
|
||||
static ClientStateSynchronizeStart state;
|
||||
return state;
|
||||
}
|
||||
|
||||
ClientStateSynchronizeStart::ClientStateSynchronizeStart()
|
||||
{
|
||||
}
|
||||
|
||||
ClientStateSynchronizeStart::~ClientStateSynchronizeStart()
|
||||
{
|
||||
}
|
||||
|
||||
int
|
||||
ClientStateSynchronizeStart::Process(ClientThread &client)
|
||||
{
|
||||
int retVal = AbstractClientStateReceiving::Process(client);
|
||||
|
||||
if (client.IsSynchronized())
|
||||
{
|
||||
boost::shared_ptr<NetPacket> startAck(new NetPacketStartEventAck);
|
||||
client.GetSender().Send(client.GetContext().GetSocket(), startAck);
|
||||
client.SetState(ClientStateWaitStart::Instance());
|
||||
}
|
||||
|
||||
return retVal;
|
||||
}
|
||||
|
||||
int
|
||||
ClientStateSynchronizeStart::InternalProcess(ClientThread &client, boost::shared_ptr<NetPacket> packet)
|
||||
{
|
||||
int retVal = MSG_SOCK_INTERNAL_PENDING;
|
||||
|
||||
if (packet->ToNetPacketGameStart())
|
||||
throw ClientException(ERR_NET_START_TIMEOUT, 0);
|
||||
|
||||
return retVal;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
ClientStateWaitStart &
|
||||
ClientStateWaitStart::Instance()
|
||||
{
|
||||
static ClientStateWaitStart state;
|
||||
return state;
|
||||
}
|
||||
|
||||
ClientStateWaitStart::ClientStateWaitStart()
|
||||
{
|
||||
}
|
||||
|
||||
ClientStateWaitStart::~ClientStateWaitStart()
|
||||
{
|
||||
}
|
||||
|
||||
int
|
||||
ClientStateWaitStart::InternalProcess(ClientThread &client, boost::shared_ptr<NetPacket> packet)
|
||||
{
|
||||
int retVal = MSG_SOCK_INTERNAL_PENDING;
|
||||
|
||||
if (packet->ToNetPacketGameStart())
|
||||
{
|
||||
// Start the network game as client.
|
||||
NetPacketGameStart::Data gameStartData;
|
||||
packet->ToNetPacketGameStart()->GetData(gameStartData);
|
||||
|
||||
client.SetStartData(gameStartData.startData);
|
||||
|
||||
// Set player numbers using the game start data slots.
|
||||
NetPacketGameStart::PlayerSlotList::const_iterator slot_i = gameStartData.playerSlots.begin();
|
||||
NetPacketGameStart::PlayerSlotList::const_iterator slot_end = gameStartData.playerSlots.end();
|
||||
int num = 0;
|
||||
|
||||
while (slot_i != slot_end)
|
||||
{
|
||||
unsigned playerId = (*slot_i).playerId;
|
||||
boost::shared_ptr<PlayerData> tmpPlayer = client.GetPlayerDataByUniqueId(playerId);
|
||||
if (!tmpPlayer.get())
|
||||
throw ClientException(ERR_NET_UNKNOWN_PLAYER_ID, 0);
|
||||
tmpPlayer->SetNumber(num);
|
||||
|
||||
++num;
|
||||
++slot_i;
|
||||
}
|
||||
|
||||
client.SetState(ClientStateWaitHand::Instance());
|
||||
retVal = MSG_NET_GAME_CLIENT_START;
|
||||
}
|
||||
|
||||
return retVal;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
ClientStateWaitHand &
|
||||
ClientStateWaitHand::Instance()
|
||||
{
|
||||
|
||||
@@ -381,7 +381,7 @@ ClientThread::RequestPlayerInfo(unsigned id)
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::SetPlayerInfo(unsigned id, const PlayerInfo &info)
|
||||
ClientThread::SetPlayerInfo(unsigned id, const PlayerInfo &info, bool retrieveAvatar)
|
||||
{
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_playerInfoMapMutex);
|
||||
@@ -404,6 +404,23 @@ ClientThread::SetPlayerInfo(unsigned id, const PlayerInfo &info)
|
||||
}
|
||||
}
|
||||
|
||||
// Retrieve avatar if needed.
|
||||
if (retrieveAvatar && info.hasAvatar && !GetAvatarManager().HasAvatar(info.avatar))
|
||||
{
|
||||
boost::shared_ptr<NetPacket> retrieveAvatar(new NetPacketRetrieveAvatar);
|
||||
NetPacketRetrieveAvatar::Data retrieveAvatarData;
|
||||
retrieveAvatarData.requestId = id;
|
||||
retrieveAvatarData.avatar = info.avatar;
|
||||
static_cast<NetPacketRetrieveAvatar *>(retrieveAvatar.get())->SetData(retrieveAvatarData);
|
||||
GetSender().Send(GetContext().GetSocket(), retrieveAvatar);
|
||||
|
||||
// Insert empty value in list to synchronize waiting.
|
||||
m_tempAvatarMap[id] = boost::shared_ptr<AvatarData>();
|
||||
}
|
||||
|
||||
// Remove from request list.
|
||||
m_playerInfoRequestList.remove(id);
|
||||
|
||||
// Notify GUI
|
||||
GetCallback().SignalNetClientPlayerChanged(id, info.playerName);
|
||||
|
||||
@@ -464,7 +481,7 @@ ClientThread::CompleteTempAvatarData(unsigned playerId)
|
||||
m_tempAvatarMap.erase(pos);
|
||||
|
||||
// Update player info, but never re-request avatar.
|
||||
SetPlayerInfo(playerId, tmpPlayerInfo);
|
||||
SetPlayerInfo(playerId, tmpPlayerInfo, false);
|
||||
}
|
||||
|
||||
const ClientContext &
|
||||
@@ -822,3 +839,9 @@ ClientThread::SetSessionEstablished(bool flag)
|
||||
m_sessionEstablished = flag;
|
||||
}
|
||||
|
||||
bool
|
||||
ClientThread::IsSynchronized() const
|
||||
{
|
||||
return (m_playerInfoRequestList.empty() && m_tempAvatarMap.empty());
|
||||
}
|
||||
|
||||
|
||||
@@ -49,6 +49,7 @@ using namespace std;
|
||||
#define NET_TYPE_KICK_PLAYER 0x0040
|
||||
#define NET_TYPE_LEAVE_CURRENT_GAME 0x0041
|
||||
#define NET_TYPE_START_EVENT 0x0042
|
||||
#define NET_TYPE_START_EVENT_ACK 0x0043
|
||||
#define NET_TYPE_GAME_START 0x0050
|
||||
#define NET_TYPE_HAND_START 0x0051
|
||||
#define NET_TYPE_PLAYERS_TURN 0x0052
|
||||
@@ -297,6 +298,12 @@ struct GCC_PACKED NetPacketStartEventData
|
||||
u_int16_t reserved;
|
||||
};
|
||||
|
||||
struct GCC_PACKED NetPacketStartEventAckData
|
||||
{
|
||||
NetPacketHeader head;
|
||||
u_int32_t reserved;
|
||||
};
|
||||
|
||||
struct GCC_PACKED NetPacketGameStartData
|
||||
{
|
||||
NetPacketHeader head;
|
||||
@@ -646,6 +653,9 @@ NetPacket::Create(char *data, unsigned &dataSize)
|
||||
case NET_TYPE_START_EVENT:
|
||||
tmpPacket = boost::shared_ptr<NetPacket>(new NetPacketStartEvent);
|
||||
break;
|
||||
case NET_TYPE_START_EVENT_ACK:
|
||||
tmpPacket = boost::shared_ptr<NetPacket>(new NetPacketStartEventAck);
|
||||
break;
|
||||
case NET_TYPE_GAME_START:
|
||||
tmpPacket = boost::shared_ptr<NetPacket>(new NetPacketGameStart);
|
||||
break;
|
||||
@@ -913,6 +923,12 @@ NetPacket::ToNetPacketStartEvent() const
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const NetPacketStartEventAck *
|
||||
NetPacket::ToNetPacketStartEventAck() const
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const NetPacketGameStart *
|
||||
NetPacket::ToNetPacketGameStart() const
|
||||
{
|
||||
@@ -2641,7 +2657,7 @@ NetPacketKickPlayer::InternalCheck(const NetPacketHeader*) const
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
NetPacketLeaveCurrentGame::NetPacketLeaveCurrentGame()
|
||||
: NetPacket(NET_TYPE_LEAVE_CURRENT_GAME, sizeof(NetPacketLeaveCurrentGame), sizeof(NetPacketLeaveCurrentGame))
|
||||
: NetPacket(NET_TYPE_LEAVE_CURRENT_GAME, sizeof(NetPacketLeaveCurrentGameData), sizeof(NetPacketLeaveCurrentGameData))
|
||||
{
|
||||
}
|
||||
|
||||
@@ -2735,6 +2751,43 @@ NetPacketStartEvent::InternalCheck(const NetPacketHeader*) const
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
NetPacketStartEventAck::NetPacketStartEventAck()
|
||||
: NetPacket(NET_TYPE_START_EVENT_ACK, sizeof(NetPacketStartEventAckData), sizeof(NetPacketStartEventAckData))
|
||||
{
|
||||
}
|
||||
|
||||
NetPacketStartEventAck::~NetPacketStartEventAck()
|
||||
{
|
||||
}
|
||||
|
||||
boost::shared_ptr<NetPacket>
|
||||
NetPacketStartEventAck::Clone() const
|
||||
{
|
||||
boost::shared_ptr<NetPacket> newPacket(new NetPacketStartEventAck);
|
||||
try
|
||||
{
|
||||
newPacket->SetRawData(GetRawData());
|
||||
} catch (const NetException &)
|
||||
{
|
||||
// Need to return the new packet anyway.
|
||||
}
|
||||
return newPacket;
|
||||
}
|
||||
|
||||
const NetPacketStartEventAck *
|
||||
NetPacketStartEventAck::ToNetPacketStartEventAck() const
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
void
|
||||
NetPacketStartEventAck::InternalCheck(const NetPacketHeader*) const
|
||||
{
|
||||
// Nothing to do.
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
NetPacketGameStart::NetPacketGameStart()
|
||||
: NetPacket(NET_TYPE_GAME_START, sizeof(NetPacketGameStartData), MAX_PACKET_SIZE)
|
||||
{
|
||||
|
||||
@@ -46,6 +46,7 @@ using namespace std;
|
||||
#define SERVER_SHOW_CARDS_DELAY_SEC 2
|
||||
#define SERVER_PLAYER_TIMEOUT_ADD_DELAY_SEC 2
|
||||
#define SERVER_COMPUTER_ACTION_DELAY_SEC 2
|
||||
#define SERVER_START_GAME_TIMEOUT_SEC 10
|
||||
|
||||
#define SERVER_COMPUTER_PLAYER_NAME "Computer"
|
||||
|
||||
@@ -286,35 +287,41 @@ ServerGameStateInit::HandleNewSession(ServerGameThread &server, SessionWrapper s
|
||||
int
|
||||
ServerGameStateInit::InternalProcess(ServerGameThread &server, SessionWrapper session, boost::shared_ptr<NetPacket> packet)
|
||||
{
|
||||
int retVal = MSG_SOCK_INIT_DONE;
|
||||
int retVal = MSG_SOCK_INTERNAL_PENDING;
|
||||
|
||||
if (packet->ToNetPacketStartEvent())
|
||||
{
|
||||
NetPacketStartEvent::Data startData;
|
||||
packet->ToNetPacketStartEvent()->GetData(startData);
|
||||
|
||||
server.ResetComputerPlayerList();
|
||||
|
||||
if (startData.fillUpWithCpuPlayers)
|
||||
// Only admins are allowed to start the game.
|
||||
if (session.playerData->GetRights() == PLAYER_RIGHTS_ADMIN)
|
||||
{
|
||||
int remainingSlots = server.GetGameData().maxNumberOfPlayers - server.GetCurNumberOfPlayers();
|
||||
for (int i = 1; i <= remainingSlots; i++)
|
||||
NetPacketStartEvent::Data startData;
|
||||
packet->ToNetPacketStartEvent()->GetData(startData);
|
||||
|
||||
// Fill up with computer players.
|
||||
server.ResetComputerPlayerList();
|
||||
|
||||
if (startData.fillUpWithCpuPlayers)
|
||||
{
|
||||
boost::shared_ptr<PlayerData> tmpPlayerData(
|
||||
new PlayerData(server.GetLobbyThread().GetNextUniquePlayerId(), 0, PLAYER_TYPE_COMPUTER, PLAYER_RIGHTS_NORMAL));
|
||||
int remainingSlots = server.GetGameData().maxNumberOfPlayers - server.GetCurNumberOfPlayers();
|
||||
for (int i = 1; i <= remainingSlots; i++)
|
||||
{
|
||||
boost::shared_ptr<PlayerData> tmpPlayerData(
|
||||
new PlayerData(server.GetLobbyThread().GetNextUniquePlayerId(), 0, PLAYER_TYPE_COMPUTER, PLAYER_RIGHTS_NORMAL));
|
||||
|
||||
ostringstream name;
|
||||
name << SERVER_COMPUTER_PLAYER_NAME << i;
|
||||
tmpPlayerData->SetName(name.str());
|
||||
server.AddComputerPlayer(tmpPlayerData);
|
||||
ostringstream name;
|
||||
name << SERVER_COMPUTER_PLAYER_NAME << i;
|
||||
tmpPlayerData->SetName(name.str());
|
||||
server.AddComputerPlayer(tmpPlayerData);
|
||||
|
||||
// Send "Player Joined" to other fully connected clients.
|
||||
server.SendToAllPlayers(CreateNetPacketPlayerJoined(*tmpPlayerData), SessionData::Game);
|
||||
// Send "Player Joined" to other fully connected clients.
|
||||
server.SendToAllPlayers(CreateNetPacketPlayerJoined(*tmpPlayerData), SessionData::Game);
|
||||
}
|
||||
}
|
||||
}
|
||||
// Wait for all players to confirm start of game.
|
||||
server.SendToAllPlayers(boost::shared_ptr<NetPacket>(packet->Clone()), SessionData::Game);
|
||||
|
||||
server.InternalStartGame();
|
||||
server.SetState(SERVER_START_GAME_STATE::Instance());
|
||||
server.SetState(ServerGameStateWaitAck::Instance());
|
||||
}
|
||||
}
|
||||
else if (packet->ToNetPacketKickPlayer())
|
||||
{
|
||||
@@ -365,6 +372,64 @@ AbstractServerGameStateRunning::HandleNewSession(ServerGameThread &server, Sessi
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
boost::thread_specific_ptr<ServerGameStateWaitAck> ServerGameStateWaitAck::Ptr;
|
||||
|
||||
ServerGameStateWaitAck &
|
||||
ServerGameStateWaitAck::Instance()
|
||||
{
|
||||
if (!Ptr.get())
|
||||
Ptr.reset(new ServerGameStateWaitAck);
|
||||
|
||||
return *Ptr;
|
||||
}
|
||||
|
||||
ServerGameStateWaitAck::ServerGameStateWaitAck()
|
||||
{
|
||||
}
|
||||
|
||||
ServerGameStateWaitAck::~ServerGameStateWaitAck()
|
||||
{
|
||||
}
|
||||
|
||||
int
|
||||
ServerGameStateWaitAck::Process(ServerGameThread &server)
|
||||
{
|
||||
int retVal;
|
||||
|
||||
if (GetTimer().elapsed().total_seconds() >= SERVER_START_GAME_TIMEOUT_SEC)
|
||||
{
|
||||
// On timeout: start anyway.
|
||||
server.SetState(SERVER_START_GAME_STATE::Instance());
|
||||
retVal = MSG_SOCK_INIT_DONE;
|
||||
}
|
||||
else
|
||||
retVal = AbstractServerGameStateReceiving::Process(server);
|
||||
|
||||
return retVal;
|
||||
}
|
||||
|
||||
int
|
||||
ServerGameStateWaitAck::InternalProcess(ServerGameThread &server, SessionWrapper session, boost::shared_ptr<NetPacket> packet)
|
||||
{
|
||||
int retVal = MSG_SOCK_INTERNAL_PENDING;
|
||||
|
||||
if (packet->ToNetPacketStartEventAck())
|
||||
{
|
||||
session.sessionData->SetReadyFlag();
|
||||
if (server.GetSessionManager().CountReadySessions() == server.GetSessionManager().GetRawSessionCount())
|
||||
{
|
||||
// Everyone is ready.
|
||||
server.SetState(SERVER_START_GAME_STATE::Instance());
|
||||
retVal = MSG_SOCK_INIT_DONE;
|
||||
}
|
||||
retVal = MSG_SOCK_INIT_DONE;
|
||||
}
|
||||
|
||||
return retVal;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
boost::thread_specific_ptr<ServerGameStateStartGame> ServerGameStateStartGame::Ptr;
|
||||
|
||||
ServerGameStateStartGame &
|
||||
@@ -387,6 +452,8 @@ ServerGameStateStartGame::~ServerGameStateStartGame()
|
||||
int
|
||||
ServerGameStateStartGame::Process(ServerGameThread &server)
|
||||
{
|
||||
server.InternalStartGame();
|
||||
|
||||
boost::shared_ptr<NetPacket> answer(new NetPacketGameStart);
|
||||
|
||||
NetPacketGameStart::Data gameStartData;
|
||||
|
||||
@@ -152,6 +152,7 @@ ServerGameThread::Main()
|
||||
GetSender().SignalTermination();
|
||||
GetSender().Join(SENDER_THREAD_TERMINATE_TIMEOUT);
|
||||
|
||||
ResetComputerPlayerList();
|
||||
GetLobbyThread().RemoveGame(GetId());
|
||||
}
|
||||
|
||||
@@ -273,14 +274,27 @@ ServerGameThread::IsRunning() const
|
||||
void
|
||||
ServerGameThread::AddComputerPlayer(boost::shared_ptr<PlayerData> player)
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_computerPlayerListMutex);
|
||||
m_computerPlayerList.push_back(player);
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_computerPlayerListMutex);
|
||||
m_computerPlayerList.push_back(player);
|
||||
}
|
||||
GetLobbyThread().AddComputerPlayer(player);
|
||||
}
|
||||
|
||||
void
|
||||
ServerGameThread::ResetComputerPlayerList()
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_computerPlayerListMutex);
|
||||
|
||||
PlayerDataList::iterator i = m_computerPlayerList.begin();
|
||||
PlayerDataList::iterator end = m_computerPlayerList.end();
|
||||
|
||||
while (i != end)
|
||||
{
|
||||
GetLobbyThread().RemoveComputerPlayer(*i);
|
||||
++i;
|
||||
}
|
||||
|
||||
m_computerPlayerList.clear();
|
||||
}
|
||||
|
||||
|
||||
@@ -176,6 +176,20 @@ ServerLobbyThread::HandleGameRetrieveAvatar(SessionWrapper session, const NetPac
|
||||
HandleNetPacketRetrieveAvatar(session, tmpPacket);
|
||||
}
|
||||
|
||||
void
|
||||
ServerLobbyThread::AddComputerPlayer(boost::shared_ptr<PlayerData> player)
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_computerPlayersMutex);
|
||||
m_computerPlayers.insert(PlayerDataMap::value_type(player->GetUniqueId(), player));
|
||||
}
|
||||
|
||||
void
|
||||
ServerLobbyThread::RemoveComputerPlayer(boost::shared_ptr<PlayerData> player)
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_computerPlayersMutex);
|
||||
m_computerPlayers.erase(player->GetUniqueId());
|
||||
}
|
||||
|
||||
void
|
||||
ServerLobbyThread::RemoveGame(unsigned id)
|
||||
{
|
||||
@@ -446,6 +460,13 @@ ServerLobbyThread::HandleNetPacketRetrievePlayerInfo(SessionWrapper session, con
|
||||
boost::shared_ptr<PlayerData> tmpPlayer = m_sessionManager.GetSessionByUniquePlayerId(request.playerId).playerData;
|
||||
if (!tmpPlayer.get())
|
||||
tmpPlayer = m_gameSessionManager.GetSessionByUniquePlayerId(request.playerId).playerData;
|
||||
if (!tmpPlayer.get())
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_computerPlayersMutex);
|
||||
PlayerDataMap::const_iterator pos = m_computerPlayers.find(request.playerId);
|
||||
if (pos != m_computerPlayers.end())
|
||||
tmpPlayer = pos->second;
|
||||
}
|
||||
|
||||
if (tmpPlayer.get())
|
||||
{
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
#include <net/sessiondata.h>
|
||||
|
||||
SessionData::SessionData(SOCKET sockfd, unsigned id)
|
||||
: m_sockfd(sockfd), m_id(id), m_state(SessionData::Init)
|
||||
: m_sockfd(sockfd), m_id(id), m_state(SessionData::Init), m_readyFlag(false)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -58,6 +58,27 @@ SessionData::GetSocket() const
|
||||
return m_sockfd;
|
||||
}
|
||||
|
||||
void
|
||||
SessionData::SetReadyFlag()
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_dataMutex);
|
||||
m_readyFlag = true;
|
||||
}
|
||||
|
||||
void
|
||||
SessionData::ResetReadyFlag()
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_dataMutex);
|
||||
m_readyFlag = false;
|
||||
}
|
||||
|
||||
bool
|
||||
SessionData::IsReady() const
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_dataMutex);
|
||||
return m_readyFlag;
|
||||
}
|
||||
|
||||
const std::string &
|
||||
SessionData::GetClientAddr() const
|
||||
{
|
||||
|
||||
@@ -292,6 +292,24 @@ SessionManager::ForEach(boost::function<void (SessionWrapper)> func)
|
||||
}
|
||||
}
|
||||
|
||||
unsigned
|
||||
SessionManager::CountReadySessions() const
|
||||
{
|
||||
unsigned counter = 0;
|
||||
boost::mutex::scoped_lock lock(m_sessionMapMutex);
|
||||
|
||||
SessionMap::const_iterator i = m_sessionMap.begin();
|
||||
SessionMap::const_iterator end = m_sessionMap.end();
|
||||
|
||||
while (i != end)
|
||||
{
|
||||
if ((*i).second.sessionData->IsReady())
|
||||
++counter;
|
||||
++i;
|
||||
}
|
||||
return counter;
|
||||
}
|
||||
|
||||
void
|
||||
SessionManager::Clear()
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user