Major redesign: Using game ids and player ids in gui (associated with tree view items).
Player list of all network games is now dynamically updated in lobby (no polling, server sends events).
This commit is contained in:
@@ -485,6 +485,21 @@ ClientStateWaitJoin::InternalProcess(ClientThread &client, boost::shared_ptr<Net
|
||||
// A new game was created on the server.
|
||||
NetPacketGameListNew::Data gameListNewData;
|
||||
packet->ToNetPacketGameListNew()->GetData(gameListNewData);
|
||||
|
||||
// Request player info for players if needed.
|
||||
PlayerIdList::const_iterator i = gameListNewData.gameInfo.players.begin();
|
||||
PlayerIdList::const_iterator end = gameListNewData.gameInfo.players.end();
|
||||
while (i != end)
|
||||
{
|
||||
PlayerInfo info;
|
||||
if (!client.GetCachedPlayerInfo(*i, info))
|
||||
{
|
||||
// Request player info.
|
||||
client.RequestPlayerInfo(*i);
|
||||
}
|
||||
++i;
|
||||
}
|
||||
|
||||
client.AddGameInfo(gameListNewData.gameId, gameListNewData.gameInfo);
|
||||
}
|
||||
else if (packet->ToNetPacketGameListUpdate())
|
||||
@@ -495,6 +510,24 @@ ClientStateWaitJoin::InternalProcess(ClientThread &client, boost::shared_ptr<Net
|
||||
if (gameListUpdateData.gameMode == GAME_MODE_CLOSED)
|
||||
client.RemoveGameInfo(gameListUpdateData.gameId);
|
||||
}
|
||||
else if (packet->ToNetPacketGameListPlayerJoined())
|
||||
{
|
||||
NetPacketGameListPlayerJoined::Data playerJoinedData;
|
||||
packet->ToNetPacketGameListPlayerJoined()->GetData(playerJoinedData);
|
||||
client.ModifyGameInfoAddPlayer(playerJoinedData.gameId, playerJoinedData.playerId);
|
||||
// Request player info if needed.
|
||||
PlayerInfo info;
|
||||
if (!client.GetCachedPlayerInfo(playerJoinedData.playerId, info))
|
||||
{
|
||||
client.RequestPlayerInfo(playerJoinedData.playerId);
|
||||
}
|
||||
}
|
||||
else if (packet->ToNetPacketGameListPlayerLeft())
|
||||
{
|
||||
NetPacketGameListPlayerLeft::Data playerLeftData;
|
||||
packet->ToNetPacketGameListPlayerLeft()->GetData(playerLeftData);
|
||||
client.ModifyGameInfoRemovePlayer(playerLeftData.gameId, playerLeftData.playerId);
|
||||
}
|
||||
else if (packet->ToNetPacketJoinGameAck())
|
||||
{
|
||||
// Successfully joined a game.
|
||||
@@ -573,25 +606,24 @@ ClientStateWaitGame::InternalProcess(ClientThread &client, boost::shared_ptr<Net
|
||||
packet->ToNetPacketPlayerJoined()->GetData(netPlayerData);
|
||||
|
||||
boost::shared_ptr<PlayerData> playerData;
|
||||
try
|
||||
PlayerInfo info;
|
||||
if (client.GetCachedPlayerInfo(netPlayerData.playerId, info))
|
||||
{
|
||||
PlayerInfo info = client.GetCachedPlayerInfo(netPlayerData.playerId);
|
||||
playerData.reset(
|
||||
new PlayerData(netPlayerData.playerId, 0, info.ptype, netPlayerData.prights));
|
||||
playerData->SetName(info.playerName);
|
||||
} catch (const NetException &)
|
||||
}
|
||||
else
|
||||
{
|
||||
ostringstream name;
|
||||
name << "#" << netPlayerData.playerId;
|
||||
|
||||
// Request player info.
|
||||
PlayerInfo info;
|
||||
info.playerName = name.str();
|
||||
client.RequestPlayerInfo(netPlayerData.playerId, info);
|
||||
client.RequestPlayerInfo(netPlayerData.playerId);
|
||||
// Use temporary data until the PlayerInfo request is completed.
|
||||
playerData.reset(
|
||||
new PlayerData(netPlayerData.playerId, 0, info.ptype, netPlayerData.prights));
|
||||
playerData->SetName(info.playerName);
|
||||
new PlayerData(netPlayerData.playerId, 0, PLAYER_TYPE_HUMAN, netPlayerData.prights));
|
||||
playerData->SetName(name.str());
|
||||
}
|
||||
client.AddPlayerData(playerData);
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <game.h>
|
||||
|
||||
#include <boost/lambda/lambda.hpp>
|
||||
#include <sstream>
|
||||
#include <cassert>
|
||||
|
||||
using namespace std;
|
||||
@@ -217,25 +218,33 @@ ClientThread::SendCreateGame(const GameData &gameData, const std::string &name,
|
||||
}
|
||||
|
||||
GameInfo
|
||||
ClientThread::GetGameInfo(const string &game) const
|
||||
ClientThread::GetGameInfo(unsigned gameId) const
|
||||
{
|
||||
GameInfo tmpInfo;
|
||||
try
|
||||
{
|
||||
unsigned id = GetGameIdByName(game);
|
||||
|
||||
boost::mutex::scoped_lock lock(m_gameInfoMapMutex);
|
||||
GameInfoMap::const_iterator pos = m_gameInfoMap.find(id);
|
||||
if (pos != m_gameInfoMap.end())
|
||||
{
|
||||
tmpInfo = pos->second;
|
||||
}
|
||||
} catch (const NetException &)
|
||||
boost::mutex::scoped_lock lock(m_gameInfoMapMutex);
|
||||
GameInfoMap::const_iterator pos = m_gameInfoMap.find(gameId);
|
||||
if (pos != m_gameInfoMap.end())
|
||||
{
|
||||
tmpInfo = pos->second;
|
||||
}
|
||||
return tmpInfo;
|
||||
}
|
||||
|
||||
PlayerInfo
|
||||
ClientThread::GetPlayerInfo(unsigned playerId) const
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_playerInfoMapMutex);
|
||||
PlayerInfo info;
|
||||
if (!GetCachedPlayerInfo(playerId, info))
|
||||
{
|
||||
ostringstream name;
|
||||
name << "#" << playerId;
|
||||
|
||||
info.playerName = name.str();
|
||||
}
|
||||
return info;
|
||||
}
|
||||
|
||||
ClientCallback &
|
||||
ClientThread::GetCallback()
|
||||
{
|
||||
@@ -320,43 +329,44 @@ ClientThread::SendPacketLoop()
|
||||
}
|
||||
}
|
||||
|
||||
PlayerInfo
|
||||
ClientThread::GetCachedPlayerInfo(unsigned id) const
|
||||
bool
|
||||
ClientThread::GetCachedPlayerInfo(unsigned id, PlayerInfo &info) const
|
||||
{
|
||||
bool retVal = false;
|
||||
|
||||
boost::mutex::scoped_lock lock(m_playerInfoMapMutex);
|
||||
PlayerInfoMap::const_iterator pos = m_playerInfoMap.find(id);
|
||||
if (pos == m_playerInfoMap.end())
|
||||
throw NetException(ERR_NET_UNKNOWN_PLAYER_ID, 0);
|
||||
return pos->second;
|
||||
if (pos != m_playerInfoMap.end())
|
||||
{
|
||||
info = pos->second;
|
||||
retVal = true;
|
||||
}
|
||||
return retVal;
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::RequestPlayerInfo(unsigned id, const PlayerInfo &tempInfo)
|
||||
ClientThread::RequestPlayerInfo(unsigned id)
|
||||
{
|
||||
boost::shared_ptr<NetPacket> req(new NetPacketRetrievePlayerInfo);
|
||||
NetPacketRetrievePlayerInfo::Data reqData;
|
||||
reqData.playerId = id;
|
||||
static_cast<NetPacketRetrievePlayerInfo *>(req.get())->SetData(reqData);
|
||||
GetSender().Send(GetContext().GetSocket(), req);
|
||||
if (find(m_playerInfoRequestList.begin(), m_playerInfoRequestList.end(), id) == m_playerInfoRequestList.end())
|
||||
{
|
||||
boost::shared_ptr<NetPacket> req(new NetPacketRetrievePlayerInfo);
|
||||
NetPacketRetrievePlayerInfo::Data reqData;
|
||||
reqData.playerId = id;
|
||||
static_cast<NetPacketRetrievePlayerInfo *>(req.get())->SetData(reqData);
|
||||
GetSender().Send(GetContext().GetSocket(), req);
|
||||
|
||||
m_playerInfoMap[id] = tempInfo;
|
||||
m_playerInfoRequestList.push_back(id);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::SetPlayerInfo(unsigned id, const PlayerInfo &info)
|
||||
{
|
||||
PlayerInfoMap::iterator pos = m_playerInfoMap.find(id);
|
||||
|
||||
// Update info cache.
|
||||
if (pos != m_playerInfoMap.end())
|
||||
{
|
||||
GetCallback().SignalNetClientPlayerChanged(pos->second.playerName, info.playerName);
|
||||
|
||||
pos->second = info;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_playerInfoMap.insert(PlayerInfoMap::value_type(id, info));
|
||||
boost::mutex::scoped_lock lock(m_playerInfoMapMutex);
|
||||
m_playerInfoMap[id] = info;
|
||||
}
|
||||
GetCallback().SignalNetClientPlayerChanged(id, info.playerName);
|
||||
|
||||
// Update player data for current game.
|
||||
boost::shared_ptr<PlayerData> playerData = GetPlayerDataByUniqueId(id);
|
||||
@@ -464,16 +474,16 @@ ClientThread::AddPlayerData(boost::shared_ptr<PlayerData> playerData)
|
||||
{
|
||||
m_playerDataList.push_back(playerData);
|
||||
if (playerData->GetUniqueId() == GetGuiPlayerId())
|
||||
GetCallback().SignalNetClientSelfJoined(playerData->GetName(), playerData->GetRights());
|
||||
GetCallback().SignalNetClientSelfJoined(playerData->GetUniqueId(), playerData->GetName(), playerData->GetRights());
|
||||
else
|
||||
GetCallback().SignalNetClientPlayerJoined(playerData->GetName(), playerData->GetRights());
|
||||
GetCallback().SignalNetClientPlayerJoined(playerData->GetUniqueId(), playerData->GetName(), playerData->GetRights());
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::RemovePlayerData(unsigned playerId)
|
||||
{
|
||||
string playerName;
|
||||
boost::shared_ptr<PlayerData> tmpData;
|
||||
|
||||
PlayerDataList::iterator i = m_playerDataList.begin();
|
||||
PlayerDataList::iterator end = m_playerDataList.end();
|
||||
@@ -481,20 +491,17 @@ ClientThread::RemovePlayerData(unsigned playerId)
|
||||
{
|
||||
if ((*i)->GetUniqueId() == playerId)
|
||||
{
|
||||
playerName = (*i)->GetName();
|
||||
tmpData = *i;
|
||||
m_playerDataList.erase(i);
|
||||
break;
|
||||
}
|
||||
++i;
|
||||
}
|
||||
|
||||
if (!playerName.empty())
|
||||
if (tmpData.get())
|
||||
{
|
||||
// Remove name and id string.
|
||||
GetCallback().SignalNetClientPlayerLeft(playerName);
|
||||
ostringstream name;
|
||||
name << "#" << playerId;
|
||||
GetCallback().SignalNetClientPlayerLeft(name.str());
|
||||
// Remove player from gui.
|
||||
GetCallback().SignalNetClientPlayerLeft(tmpData->GetUniqueId(), tmpData->GetName());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -623,22 +630,22 @@ ClientThread::GetGameIdByName(const std::string &name) const
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::AddGameInfo(unsigned id, const GameInfo &info)
|
||||
ClientThread::AddGameInfo(unsigned gameId, const GameInfo &info)
|
||||
{
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_gameInfoMapMutex);
|
||||
m_gameInfoMap.insert(GameInfoMap::value_type(id, info));
|
||||
m_gameInfoMap.insert(GameInfoMap::value_type(gameId, info));
|
||||
}
|
||||
GetCallback().SignalNetClientGameListNew(info.name);
|
||||
GetCallback().SignalNetClientGameListNew(gameId, info.name);
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::RemoveGameInfo(unsigned id)
|
||||
ClientThread::RemoveGameInfo(unsigned gameId)
|
||||
{
|
||||
string name;
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_gameInfoMapMutex);
|
||||
GameInfoMap::iterator pos = m_gameInfoMap.find(id);
|
||||
GameInfoMap::iterator pos = m_gameInfoMap.find(gameId);
|
||||
if (pos != m_gameInfoMap.end())
|
||||
{
|
||||
name = pos->second.name;
|
||||
@@ -646,7 +653,41 @@ ClientThread::RemoveGameInfo(unsigned id)
|
||||
}
|
||||
}
|
||||
if (!name.empty())
|
||||
GetCallback().SignalNetClientGameListRemove(name);
|
||||
GetCallback().SignalNetClientGameListRemove(gameId, name);
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::ModifyGameInfoAddPlayer(unsigned gameId, unsigned playerId)
|
||||
{
|
||||
bool playerAdded = false;
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_gameInfoMapMutex);
|
||||
GameInfoMap::iterator pos = m_gameInfoMap.find(gameId);
|
||||
if (pos != m_gameInfoMap.end())
|
||||
{
|
||||
pos->second.players.push_back(playerId);
|
||||
playerAdded = true;
|
||||
}
|
||||
}
|
||||
if (playerAdded)
|
||||
GetCallback().SignalNetClientGameListPlayerJoined(gameId, playerId);
|
||||
}
|
||||
|
||||
void
|
||||
ClientThread::ModifyGameInfoRemovePlayer(unsigned gameId, unsigned playerId)
|
||||
{
|
||||
bool playerRemoved = false;
|
||||
{
|
||||
boost::mutex::scoped_lock lock(m_gameInfoMapMutex);
|
||||
GameInfoMap::iterator pos = m_gameInfoMap.find(gameId);
|
||||
if (pos != m_gameInfoMap.end())
|
||||
{
|
||||
pos->second.players.remove(playerId);
|
||||
playerRemoved = true;
|
||||
}
|
||||
}
|
||||
if (playerRemoved)
|
||||
GetCallback().SignalNetClientGameListPlayerLeft(gameId, playerId);
|
||||
}
|
||||
|
||||
bool
|
||||
|
||||
@@ -1091,7 +1091,7 @@ NetPacketGameListNew::GetData(NetPacketGameListNew::Data &outData) const
|
||||
// Store all available players.
|
||||
for (int i = 0; i < curNumPlayers; i++)
|
||||
{
|
||||
outData.gameInfo.players.push_back(*tmpPlayer);
|
||||
outData.gameInfo.players.push_back(ntohl(*tmpPlayer));
|
||||
++tmpPlayer;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
|
||||
#include <net/servergamestate.h>
|
||||
#include <net/servergamethread.h>
|
||||
#include <net/serverlobbythread.h>
|
||||
#include <net/receiverhelper.h>
|
||||
#include <net/senderthread.h>
|
||||
#include <net/netpacket.h>
|
||||
@@ -279,6 +280,9 @@ ServerGameStateInit::HandleNewSession(ServerGameThread &server, SessionWrapper s
|
||||
session.sessionData->SetState(SessionData::Game);
|
||||
// Accept session.
|
||||
server.GetSessionManager().AddSession(session);
|
||||
|
||||
// Notify lobby.
|
||||
server.GetLobbyThread().NotifyPlayerJoinedGame(server.GetId(), session.playerData->GetUniqueId());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -227,11 +227,10 @@ ServerGameThread::CloseSessionDelayed(SessionWrapper session)
|
||||
thisPlayerLeftData.playerId = tmpPlayerData->GetUniqueId();
|
||||
static_cast<NetPacketPlayerLeft *>(thisPlayerLeft.get())->SetData(thisPlayerLeftData);
|
||||
GetSessionManager().SendToAllSessions(GetSender(), thisPlayerLeft, SessionData::Game);
|
||||
|
||||
GetCallback().SignalNetServerPlayerLeft(tmpPlayerData->GetName());
|
||||
}
|
||||
|
||||
GetLobbyThread().CloseSessionDelayed(session);
|
||||
GetLobbyThread().NotifyPlayerLeftGame(GetId(), session.playerData->GetUniqueId());
|
||||
}
|
||||
|
||||
void
|
||||
|
||||
@@ -93,6 +93,30 @@ ServerLobbyThread::CloseSessionDelayed(SessionWrapper session)
|
||||
m_closeSessionList.push_back(closeSessionData);
|
||||
}
|
||||
|
||||
void
|
||||
ServerLobbyThread::NotifyPlayerJoinedGame(unsigned gameId, unsigned playerId)
|
||||
{
|
||||
// Send notification to players in lobby.
|
||||
boost::shared_ptr<NetPacket> packet(new NetPacketGameListPlayerJoined);
|
||||
NetPacketGameListPlayerJoined::Data packetData;
|
||||
packetData.gameId = gameId;
|
||||
packetData.playerId = playerId;
|
||||
static_cast<NetPacketGameListPlayerJoined *>(packet.get())->SetData(packetData);
|
||||
m_sessionManager.SendToAllSessions(GetSender(), packet, SessionData::Established);
|
||||
}
|
||||
|
||||
void
|
||||
ServerLobbyThread::NotifyPlayerLeftGame(unsigned gameId, unsigned playerId)
|
||||
{
|
||||
// Send notification to players in lobby.
|
||||
boost::shared_ptr<NetPacket> packet(new NetPacketGameListPlayerLeft);
|
||||
NetPacketGameListPlayerLeft::Data packetData;
|
||||
packetData.gameId = gameId;
|
||||
packetData.playerId = playerId;
|
||||
static_cast<NetPacketGameListPlayerLeft *>(packet.get())->SetData(packetData);
|
||||
m_sessionManager.SendToAllSessions(GetSender(), packet, SessionData::Established);
|
||||
}
|
||||
|
||||
void
|
||||
ServerLobbyThread::RemoveGame(unsigned id)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user