Save players and live join info in ClientLobby

This commit is contained in:
Benau 2019-01-16 16:45:27 +08:00
parent 4e2b843f71
commit 9078438b23
4 changed files with 88 additions and 67 deletions

View File

@ -94,6 +94,7 @@ ClientLobby::ClientLobby(const TransportAddress& a, std::shared_ptr<Server> s)
_("Bad network connection is detected."); _("Bad network connection is detected.");
m_first_connect = true; m_first_connect = true;
m_spectator = false; m_spectator = false;
m_server_live_joinable = false;
} // ClientLobby } // ClientLobby
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -664,9 +665,7 @@ void ClientLobby::handleServerInfo(Event* event)
} }
bool server_config = data.getUInt8() == 1; bool server_config = data.getUInt8() == 1;
NetworkingLobby::getInstance()->toggleServerConfigButton(server_config); NetworkingLobby::getInstance()->toggleServerConfigButton(server_config);
bool live_join_spectator = data.getUInt8() == 1; m_server_live_joinable = data.getUInt8() == 1;
NetworkingLobby::getInstance()
->toggleServerLiveJoinable(live_join_spectator);
} // handleServerInfo } // handleServerInfo
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -683,42 +682,40 @@ void ClientLobby::updatePlayerList(Event* event)
m_waiting_for_game = waiting; m_waiting_for_game = waiting;
unsigned player_count = data.getUInt8(); unsigned player_count = data.getUInt8();
std::vector<std::tuple<uint32_t, uint32_t, uint32_t, core::stringw,
int, KartTeam, PerPlayerDifficulty> > players;
core::stringw total_players; core::stringw total_players;
m_lobby_players.clear();
for (unsigned i = 0; i < player_count; i++) for (unsigned i = 0; i < player_count; i++)
{ {
std::tuple<uint32_t, uint32_t, uint32_t, core::stringw, int, LobbyPlayer lp = {};
KartTeam, PerPlayerDifficulty> pl; lp.m_host_id = data.getUInt32();
uint32_t host_id = data.getUInt32(); lp.m_online_id = data.getUInt32();
uint32_t online_id = data.getUInt32();
uint8_t local_id = data.getUInt8(); uint8_t local_id = data.getUInt8();
std::get<0>(pl) = host_id; lp.m_difficulty = PLAYER_DIFFICULTY_NORMAL;
std::get<1>(pl) = online_id; lp.m_local_player_id = local_id;
std::get<2>(pl) = local_id; data.decodeStringW(&lp.m_user_name);
data.decodeStringW(&std::get<3>(pl)); total_players += lp.m_user_name;
total_players += std::get<3>(pl);
bool is_peer_waiting_for_game = data.getUInt8() == 1; bool is_peer_waiting_for_game = data.getUInt8() == 1;
bool is_peer_server_owner = data.getUInt8() == 1; bool is_peer_server_owner = data.getUInt8() == 1;
// icon to be used, see NetworkingLobby::loadedFromFile // icon to be used, see NetworkingLobby::loadedFromFile
std::get<4>(pl) = is_peer_server_owner ? 0 : lp.m_icon_id = is_peer_server_owner ? 0 :
std::get<1>(pl) != 0 /*if online account*/ ? 1 : 2; lp.m_online_id != 0 /*if online account*/ ? 1 : 2;
if (waiting && !is_peer_waiting_for_game) if (waiting && !is_peer_waiting_for_game)
std::get<4>(pl) = 3; lp.m_icon_id = 3;
PerPlayerDifficulty d = (PerPlayerDifficulty)data.getUInt8(); lp.m_difficulty = (PerPlayerDifficulty)data.getUInt8();
std::get<6>(pl) = d; if (lp.m_difficulty == PLAYER_DIFFICULTY_HANDICAP)
if (d == PLAYER_DIFFICULTY_HANDICAP) {
std::get<3>(pl) = _("%s (handicapped)", std::get<3>(pl)); lp.m_user_name = _("%s (handicapped)", lp.m_user_name);
std::get<5>(pl) = (KartTeam)data.getUInt8(); }
lp.m_kart_team = (KartTeam)data.getUInt8();
bool ready = data.getUInt8() == 1; bool ready = data.getUInt8() == 1;
if (ready) if (ready)
std::get<4>(pl) = 4; lp.m_icon_id = 4;
if (host_id == STKHost::get()->getMyHostId()) if (lp.m_host_id == STKHost::get()->getMyHostId())
{ {
auto& local_players = NetworkConfig::get()->getNetworkPlayers(); auto& local_players = NetworkConfig::get()->getNetworkPlayers();
std::get<2>(local_players.at(local_id)) = d; std::get<2>(local_players.at(local_id)) = lp.m_difficulty;
} }
players.push_back(pl); m_lobby_players.push_back(lp);
} }
// Notification sound for new player // Notification sound for new player
@ -727,7 +724,7 @@ void ClientLobby::updatePlayerList(Event* event)
SFXManager::get()->quickSound("energy_bar_full"); SFXManager::get()->quickSound("energy_bar_full");
m_total_players = total_players; m_total_players = total_players;
NetworkingLobby::getInstance()->updatePlayers(players); NetworkingLobby::getInstance()->updatePlayers();
} // updatePlayerList } // updatePlayerList
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------

View File

@ -29,10 +29,24 @@
#include <set> #include <set>
enum PeerDisconnectInfo : unsigned int; enum PeerDisconnectInfo : unsigned int;
enum KartTeam : int8_t;
enum PerPlayerDifficulty : uint8_t;
class BareNetworkString; class BareNetworkString;
class Server; class Server;
struct LobbyPlayer
{
irr::core::stringw m_user_name;
int m_local_player_id;
uint32_t m_host_id;
KartTeam m_kart_team;
PerPlayerDifficulty m_difficulty;
uint32_t m_online_id;
/* Icon used in networking lobby, see NetworkingLobby::loadedFromFile. */
int m_icon_id;
};
class ClientLobby : public LobbyProtocol class ClientLobby : public LobbyProtocol
{ {
private: private:
@ -81,6 +95,8 @@ private:
bool m_spectator; bool m_spectator;
bool m_server_live_joinable;
uint64_t m_auto_back_to_lobby_time; uint64_t m_auto_back_to_lobby_time;
uint64_t m_start_live_game_time; uint64_t m_start_live_game_time;
@ -97,6 +113,8 @@ private:
std::map<PeerDisconnectInfo, irr::core::stringw> m_disconnected_msg; std::map<PeerDisconnectInfo, irr::core::stringw> m_disconnected_msg;
std::vector<LobbyPlayer> m_lobby_players;
irr::core::stringw m_total_players; irr::core::stringw m_total_players;
void liveJoinAcknowledged(Event* event); void liveJoinAcknowledged(Event* event);
@ -131,6 +149,9 @@ public:
bool isSpectator() const { return m_spectator; } bool isSpectator() const { return m_spectator; }
void startLiveJoinKartSelection(); void startLiveJoinKartSelection();
void sendChat(irr::core::stringw text); void sendChat(irr::core::stringw text);
const std::vector<LobbyPlayer>& getLobbyPlayers() const
{ return m_lobby_players; }
bool isServerLiveJoinable() const { return m_server_live_joinable; }
}; };
#endif // CLIENT_LOBBY_HPP #endif // CLIENT_LOBBY_HPP

View File

@ -166,9 +166,8 @@ void NetworkingLobby::init()
m_player_names.clear(); m_player_names.clear();
m_allow_change_team = false; m_allow_change_team = false;
m_has_auto_start_in_server = false; m_has_auto_start_in_server = false;
m_server_live_joinable = false;
m_client_live_joinable = false; m_client_live_joinable = false;
m_ping_update_timer = 0.0f; m_ping_update_timer = 0;
m_start_timeout = std::numeric_limits<float>::max(); m_start_timeout = std::numeric_limits<float>::max();
m_cur_starting_timer = std::numeric_limits<int64_t>::max(); m_cur_starting_timer = std::numeric_limits<int64_t>::max();
m_min_start_game_players = 0; m_min_start_game_players = 0;
@ -227,6 +226,11 @@ void NetworkingLobby::init()
getWidget("send")->setVisible(true); getWidget("send")->setVisible(true);
getWidget("send")->setActive(false); getWidget("send")->setActive(false);
} }
if (auto cl = LobbyProtocol::get<ClientLobby>())
{
if (cl->isLobbyReady())
updatePlayers();
}
} }
} // init } // init
@ -281,10 +285,9 @@ void NetworkingLobby::onUpdate(float delta)
m_config_button->setImage(m_config_texture); m_config_button->setImage(m_config_texture);
m_client_live_joinable = false; m_client_live_joinable = false;
m_ping_update_timer += delta; if (m_player_list && StkTime::getRealTimeMs() > m_ping_update_timer)
if (m_player_list && m_ping_update_timer > 2.0f)
{ {
m_ping_update_timer = 0.0f; m_ping_update_timer = StkTime::getRealTimeMs() + 2000;
updatePlayerPings(); updatePlayerPings();
} }
@ -355,7 +358,7 @@ void NetworkingLobby::onUpdate(float delta)
// and network timer is synchronized // and network timer is synchronized
if (t && if (t &&
STKHost::get()->getNetworkTimerSynchronizer()->isSynchronised() && STKHost::get()->getNetworkTimerSynchronizer()->isSynchronised() &&
m_server_live_joinable) cl->isServerLiveJoinable())
{ {
m_client_live_joinable = true; m_client_live_joinable = true;
} }
@ -490,7 +493,7 @@ void NetworkingLobby::updatePlayerPings()
auto peer_pings = STKHost::get()->getPeerPings(); auto peer_pings = STKHost::get()->getPeerPings();
for (auto& p : m_player_names) for (auto& p : m_player_names)
{ {
core::stringw name_with_ping = std::get<0>(p.second); core::stringw name_with_ping = p.second.m_user_name;
auto host_online_ids = StringUtils::splitToUInt(p.first, '_'); auto host_online_ids = StringUtils::splitToUInt(p.first, '_');
if (host_online_ids.size() != 3) if (host_online_ids.size() != 3)
continue; continue;
@ -506,12 +509,15 @@ void NetworkingLobby::updatePlayerPings()
else else
continue; continue;
int id = m_player_list->getItemID(p.first); int id = m_player_list->getItemID(p.first);
m_player_list->renameItem(id, name_with_ping, std::get<1>(p.second)); if (id != -1)
if (std::get<2>(p.second) == KART_TEAM_RED) {
m_player_list->renameItem(id, name_with_ping, p.second.m_icon_id);
if (p.second.m_kart_team == KART_TEAM_RED)
m_player_list->markItemRed(id); m_player_list->markItemRed(id);
else if (std::get<2>(p.second) == KART_TEAM_BLUE) else if (p.second.m_kart_team == KART_TEAM_BLUE)
m_player_list->markItemBlue(id); m_player_list->markItemBlue(id);
} }
}
} // updatePlayerPings } // updatePlayerPings
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
@ -541,11 +547,11 @@ void NetworkingLobby::eventCallback(Widget* widget, const std::string& name,
} }
new NetworkUserDialog(host_online_local_ids[0], new NetworkUserDialog(host_online_local_ids[0],
host_online_local_ids[1], host_online_local_ids[2], host_online_local_ids[1], host_online_local_ids[2],
std::get<0>(m_player_names.at( m_player_names.at(
m_player_list->getSelectionInternalName())), m_player_list->getSelectionInternalName()).m_user_name,
m_allow_change_team, m_allow_change_team,
std::get<3>(m_player_names.at( m_player_names.at(
m_player_list->getSelectionInternalName()))); m_player_list->getSelectionInternalName()).m_difficulty);
} // click on a user } // click on a user
else if (name == m_send_button->m_properties[PROP_ID]) else if (name == m_send_button->m_properties[PROP_ID])
{ {
@ -624,9 +630,7 @@ bool NetworkingLobby::onEscapePressed()
} // onEscapePressed } // onEscapePressed
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
void NetworkingLobby::updatePlayers(const std::vector<std::tuple<uint32_t, void NetworkingLobby::updatePlayers()
uint32_t, uint32_t, core::stringw,
int, KartTeam, PerPlayerDifficulty> >& p)
{ {
// In GUI-less server this function will be called without proper // In GUI-less server this function will be called without proper
// initialisation // initialisation
@ -635,32 +639,36 @@ void NetworkingLobby::updatePlayers(const std::vector<std::tuple<uint32_t,
m_player_list->clear(); m_player_list->clear();
m_player_names.clear(); m_player_names.clear();
if (p.empty()) auto cl = LobbyProtocol::get<ClientLobby>();
if (!cl)
return;
const auto& players = cl->getLobbyPlayers();
if (players.empty())
return; return;
irr::gui::STKModifiedSpriteBank* icon_bank = m_icon_bank; irr::gui::STKModifiedSpriteBank* icon_bank = m_icon_bank;
for (unsigned i = 0; i < p.size(); i++) for (unsigned i = 0; i < players.size(); i++)
{ {
auto& q = p[i]; const LobbyPlayer& player = players[i];
if (icon_bank) if (icon_bank)
{ {
m_player_list->setIcons(icon_bank); m_player_list->setIcons(icon_bank);
icon_bank = NULL; icon_bank = NULL;
} }
KartTeam cur_team = std::get<5>(q); KartTeam cur_team = player.m_kart_team;
m_allow_change_team = cur_team != KART_TEAM_NONE; m_allow_change_team = cur_team != KART_TEAM_NONE;
const std::string internal_name = const std::string internal_name =
StringUtils::toString(std::get<0>(q)) + "_" + StringUtils::toString(player.m_host_id) + "_" +
StringUtils::toString(std::get<1>(q)) + "_" + StringUtils::toString(player.m_online_id) + "_" +
StringUtils::toString(std::get<2>(q)); StringUtils::toString(player.m_local_player_id);
m_player_list->addItem(internal_name, std::get<3>(q), std::get<4>(q)); m_player_list->addItem(internal_name, player.m_user_name,
player.m_icon_id);
if (cur_team == KART_TEAM_RED) if (cur_team == KART_TEAM_RED)
m_player_list->markItemRed(i); m_player_list->markItemRed(i);
else if (cur_team == KART_TEAM_BLUE) else if (cur_team == KART_TEAM_BLUE)
m_player_list->markItemBlue(i); m_player_list->markItemBlue(i);
m_player_names[internal_name] = m_player_names[internal_name] = player;
std::make_tuple(std::get<3>(q), std::get<4>(q), cur_team,
std::get<6>(q));
} }
updatePlayerPings(); updatePlayerPings();
} // updatePlayers } // updatePlayers

View File

@ -28,6 +28,7 @@
class InputDevice; class InputDevice;
class Server; class Server;
enum KartTeam : int8_t; enum KartTeam : int8_t;
struct LobbyPlayer;
namespace GUIEngine namespace GUIEngine
{ {
@ -65,9 +66,8 @@ private:
NetworkingLobby(); NetworkingLobby();
float m_ping_update_timer; uint64_t m_ping_update_timer;
std::map<std::string, std::tuple<core::stringw, /*icon*/int, KartTeam, std::map<std::string, LobbyPlayer> m_player_names;
PerPlayerDifficulty> > m_player_names;
std::shared_ptr<Server> m_joined_server; std::shared_ptr<Server> m_joined_server;
std::vector<core::stringw> m_server_info; std::vector<core::stringw> m_server_info;
int m_server_info_height; int m_server_info_height;
@ -80,8 +80,7 @@ private:
unsigned m_min_start_game_players; unsigned m_min_start_game_players;
bool m_allow_change_team, m_has_auto_start_in_server, bool m_allow_change_team, m_has_auto_start_in_server,
m_server_configurable, m_server_live_joinable, m_server_configurable, m_client_live_joinable;
m_client_live_joinable;
video::ITexture* m_config_texture; video::ITexture* m_config_texture;
video::ITexture* m_spectate_texture; video::ITexture* m_spectate_texture;
@ -135,10 +134,7 @@ public:
m_joined_server = server; m_joined_server = server;
m_server_info.clear(); m_server_info.clear();
} }
void updatePlayers(const std::vector<std::tuple<uint32_t/*host id*/, void updatePlayers();
uint32_t/*online id*/, uint32_t/*local player id*/,
core::stringw/*player name*/, int/*icon id*/,
KartTeam, PerPlayerDifficulty> >& p);
void openSplitscreenDialog(InputDevice* device); void openSplitscreenDialog(InputDevice* device);
void addSplitscreenPlayer(irr::core::stringw name); void addSplitscreenPlayer(irr::core::stringw name);
void cleanAddedPlayers(); void cleanAddedPlayers();
@ -146,7 +142,6 @@ public:
float start_timeout, unsigned server_max_player); float start_timeout, unsigned server_max_player);
void setStartingTimerTo(float t); void setStartingTimerTo(float t);
void toggleServerConfigButton(bool val) { m_server_configurable = val; } void toggleServerConfigButton(bool val) { m_server_configurable = val; }
void toggleServerLiveJoinable(bool val) { m_server_live_joinable = val; }
}; // class NetworkingLobby }; // class NetworkingLobby
#endif #endif