mirror of
https://github.com/OpenRCT2/OpenRCT2
synced 2026-01-29 01:35:06 +01:00
Merge pull request #16670 from Fruitsalad/zero-players-attempt-2
Close #5141: Removes headless servers from player count and player list (2nd attempt)
This commit is contained in:
@@ -464,6 +464,11 @@ static void WindowMultiplayerInformationPaint(rct_window* w, rct_drawpixelinfo*
|
||||
|
||||
#pragma region Players page
|
||||
|
||||
static bool IsServerPlayerInvisible()
|
||||
{
|
||||
return network_is_server_player_invisible() && !gConfigGeneral.debugging_tools;
|
||||
}
|
||||
|
||||
static void WindowMultiplayerPlayersMouseup(rct_window* w, WidgetIndex widgetIndex)
|
||||
{
|
||||
switch (widgetIndex)
|
||||
@@ -487,7 +492,7 @@ static void WindowMultiplayerPlayersResize(rct_window* w)
|
||||
{
|
||||
window_set_resize(*w, 420, 124, 500, 450);
|
||||
|
||||
w->no_list_items = network_get_num_players();
|
||||
w->no_list_items = (IsServerPlayerInvisible() ? network_get_num_visible_players() : network_get_num_players());
|
||||
w->list_item_positions[0] = 0;
|
||||
|
||||
w->widgets[WIDX_HEADER_PING].right = w->width - 5;
|
||||
@@ -534,7 +539,8 @@ static void WindowMultiplayerPlayersScrollmousedown(rct_window* w, int32_t scrol
|
||||
w->selected_list_item = index;
|
||||
w->Invalidate();
|
||||
|
||||
WindowPlayerOpen(network_get_player_id(index));
|
||||
int32_t player = (IsServerPlayerInvisible() ? index + 1 : index);
|
||||
WindowPlayerOpen(network_get_player_id(player));
|
||||
}
|
||||
|
||||
static void WindowMultiplayerPlayersScrollmouseover(rct_window* w, int32_t scrollIndex, const ScreenCoordsXY& screenCoords)
|
||||
@@ -577,7 +583,11 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
{
|
||||
ScreenCoordsXY screenCoords;
|
||||
screenCoords.y = 0;
|
||||
for (int32_t i = 0; i < network_get_num_players(); i++)
|
||||
|
||||
const int32_t firstPlayerInList = (IsServerPlayerInvisible() ? 1 : 0);
|
||||
int32_t listPosition = 0;
|
||||
|
||||
for (int32_t player = firstPlayerInList; player < network_get_num_players(); player++)
|
||||
{
|
||||
if (screenCoords.y > dpi->y + dpi->height)
|
||||
{
|
||||
@@ -592,17 +602,17 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
|
||||
// Draw player name
|
||||
colour_t colour = COLOUR_BLACK;
|
||||
if (i == w->selected_list_item)
|
||||
if (listPosition == w->selected_list_item)
|
||||
{
|
||||
gfx_filter_rect(
|
||||
dpi, { 0, screenCoords.y, 800, screenCoords.y + SCROLLABLE_ROW_HEIGHT - 1 },
|
||||
FilterPaletteID::PaletteDarken1);
|
||||
_buffer += network_get_player_name(i);
|
||||
_buffer += network_get_player_name(player);
|
||||
colour = w->colours[2];
|
||||
}
|
||||
else
|
||||
{
|
||||
if (network_get_player_flags(i) & NETWORK_PLAYER_FLAG_ISSERVER)
|
||||
if (network_get_player_flags(player) & NETWORK_PLAYER_FLAG_ISSERVER)
|
||||
{
|
||||
_buffer += "{BABYBLUE}";
|
||||
}
|
||||
@@ -610,7 +620,7 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
{
|
||||
_buffer += "{BLACK}";
|
||||
}
|
||||
_buffer += network_get_player_name(i);
|
||||
_buffer += network_get_player_name(player);
|
||||
}
|
||||
screenCoords.x = 0;
|
||||
gfx_clip_string(_buffer.data(), 230, FontSpriteBase::MEDIUM);
|
||||
@@ -618,7 +628,7 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
|
||||
// Draw group name
|
||||
_buffer.resize(0);
|
||||
int32_t group = network_get_group_index(network_get_player_group(i));
|
||||
int32_t group = network_get_group_index(network_get_player_group(player));
|
||||
if (group != -1)
|
||||
{
|
||||
_buffer += "{BLACK}";
|
||||
@@ -629,7 +639,7 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
}
|
||||
|
||||
// Draw last action
|
||||
int32_t action = network_get_player_last_action(i, 2000);
|
||||
int32_t action = network_get_player_last_action(player, 2000);
|
||||
auto ft = Formatter();
|
||||
if (action != -999)
|
||||
{
|
||||
@@ -643,7 +653,7 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
|
||||
// Draw ping
|
||||
_buffer.resize(0);
|
||||
int32_t ping = network_get_player_ping(i);
|
||||
int32_t ping = network_get_player_ping(player);
|
||||
if (ping <= 100)
|
||||
{
|
||||
_buffer += "{GREEN}";
|
||||
@@ -665,6 +675,7 @@ static void WindowMultiplayerPlayersScrollpaint(rct_window* w, rct_drawpixelinfo
|
||||
gfx_draw_string(dpi, screenCoords, _buffer.c_str(), { colour });
|
||||
}
|
||||
screenCoords.y += SCROLLABLE_ROW_HEIGHT;
|
||||
listPosition++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1003,7 +1003,7 @@ static void WindowTopToolbarPaint(rct_window* w, rct_drawpixelinfo* dpi)
|
||||
|
||||
// Draw number of players.
|
||||
auto ft = Formatter();
|
||||
ft.Add<int32_t>(network_get_num_players());
|
||||
ft.Add<int32_t>(network_get_num_visible_players());
|
||||
DrawTextBasic(
|
||||
dpi, screenPos + ScreenCoordsXY{ 23, 1 }, STR_COMMA16, ft,
|
||||
{ COLOUR_WHITE | COLOUR_FLAG_OUTLINE, TextAlignment::RIGHT });
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
// This string specifies which version of network stream current build uses.
|
||||
// It is used for making sure only compatible builds get connected, even within
|
||||
// single OpenRCT2 version.
|
||||
#define NETWORK_STREAM_VERSION "13"
|
||||
#define NETWORK_STREAM_VERSION "14"
|
||||
#define NETWORK_STREAM_ID OPENRCT2_VERSION "-" NETWORK_STREAM_VERSION
|
||||
|
||||
static Peep* _pickup_peep = nullptr;
|
||||
@@ -111,7 +111,6 @@ static u8string network_get_public_key_path(u8string_view playerName, u8string_v
|
||||
NetworkBase::NetworkBase(OpenRCT2::IContext& context)
|
||||
: OpenRCT2::System(context)
|
||||
{
|
||||
wsa_initialized = false;
|
||||
mode = NETWORK_MODE_NONE;
|
||||
status = NETWORK_STATUS_NONE;
|
||||
last_ping_sent_time = 0;
|
||||
@@ -378,6 +377,8 @@ bool NetworkBase::BeginServer(uint16_t port, const std::string& address)
|
||||
ServerProviderEmail = gConfigNetwork.provider_email;
|
||||
ServerProviderWebsite = gConfigNetwork.provider_website;
|
||||
|
||||
IsServerPlayerInvisible = gOpenRCT2Headless;
|
||||
|
||||
CheatsReset();
|
||||
LoadGroups();
|
||||
BeginChatLog();
|
||||
@@ -692,6 +693,18 @@ NetworkGroup* NetworkBase::GetGroupByID(uint8_t id) const
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
int32_t NetworkBase::GetTotalNumPlayers() const noexcept
|
||||
{
|
||||
return static_cast<int32_t>(player_list.size());
|
||||
}
|
||||
|
||||
int32_t NetworkBase::GetNumVisiblePlayers() const noexcept
|
||||
{
|
||||
if (IsServerPlayerInvisible)
|
||||
return static_cast<int32_t>(player_list.size() - 1);
|
||||
return static_cast<int32_t>(player_list.size());
|
||||
}
|
||||
|
||||
const char* NetworkBase::FormatChat(NetworkPlayer* fromplayer, const char* text)
|
||||
{
|
||||
static std::string formatted;
|
||||
@@ -1569,7 +1582,7 @@ json_t NetworkBase::GetServerInfoAsJson() const
|
||||
{
|
||||
json_t jsonObj = {
|
||||
{ "name", gConfigNetwork.server_name }, { "requiresPassword", _password.size() > 0 },
|
||||
{ "version", network_get_version() }, { "players", player_list.size() },
|
||||
{ "version", network_get_version() }, { "players", GetNumVisiblePlayers() },
|
||||
{ "maxPlayers", gConfigNetwork.maxplayers }, { "description", gConfigNetwork.server_description },
|
||||
{ "greeting", gConfigNetwork.server_greeting }, { "dedicated", gOpenRCT2Headless },
|
||||
};
|
||||
@@ -1593,6 +1606,7 @@ void NetworkBase::Server_Send_GAMEINFO(NetworkConnection& connection)
|
||||
|
||||
packet.WriteString(jsonObj.dump());
|
||||
packet << _serverState.gamestateSnapshotsEnabled;
|
||||
packet << IsServerPlayerInvisible;
|
||||
|
||||
# endif
|
||||
connection.QueuePacket(std::move(packet));
|
||||
@@ -2598,7 +2612,7 @@ void NetworkBase::Server_Handle_AUTH(NetworkConnection& connection, NetworkPacke
|
||||
}
|
||||
}
|
||||
|
||||
if (static_cast<size_t>(gConfigNetwork.maxplayers) <= player_list.size())
|
||||
if (GetNumVisiblePlayers() >= gConfigNetwork.maxplayers)
|
||||
{
|
||||
connection.AuthStatus = NetworkAuth::Full;
|
||||
log_info("Connection %s: Server is full.", hostName);
|
||||
@@ -3107,6 +3121,7 @@ void NetworkBase::Client_Handle_GAMEINFO([[maybe_unused]] NetworkConnection& con
|
||||
{
|
||||
auto jsonString = packet.ReadString();
|
||||
packet >> _serverState.gamestateSnapshotsEnabled;
|
||||
packet >> IsServerPlayerInvisible;
|
||||
|
||||
json_t jsonData = Json::FromString(jsonString);
|
||||
|
||||
@@ -3210,7 +3225,12 @@ uint8_t network_get_current_player_id()
|
||||
|
||||
int32_t network_get_num_players()
|
||||
{
|
||||
return static_cast<int32_t>(OpenRCT2::GetContext()->GetNetwork().player_list.size());
|
||||
return OpenRCT2::GetContext()->GetNetwork().GetTotalNumPlayers();
|
||||
}
|
||||
|
||||
int32_t network_get_num_visible_players()
|
||||
{
|
||||
return OpenRCT2::GetContext()->GetNetwork().GetNumVisiblePlayers();
|
||||
}
|
||||
|
||||
const char* network_get_player_name(uint32_t index)
|
||||
@@ -3742,6 +3762,11 @@ int32_t network_get_pickup_peep_old_x(uint8_t playerid)
|
||||
return -1;
|
||||
}
|
||||
|
||||
bool network_is_server_player_invisible()
|
||||
{
|
||||
return OpenRCT2::GetContext()->GetNetwork().IsServerPlayerInvisible;
|
||||
}
|
||||
|
||||
int32_t network_get_current_player_group_index()
|
||||
{
|
||||
auto& network = OpenRCT2::GetContext()->GetNetwork();
|
||||
@@ -3976,6 +4001,10 @@ int32_t network_get_num_players()
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int32_t network_get_num_visible_players()
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
const char* network_get_player_name(uint32_t index)
|
||||
{
|
||||
return "local (OpenRCT2 compiled without MP)";
|
||||
@@ -4127,6 +4156,10 @@ int32_t network_get_current_player_group_index()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
bool network_is_server_player_invisible()
|
||||
{
|
||||
return false;
|
||||
}
|
||||
void network_append_chat_log(std::string_view)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -42,6 +42,8 @@ public: // Common
|
||||
auto GetGroupIteratorByID(uint8_t id) const;
|
||||
NetworkPlayer* GetPlayerByID(uint8_t id) const;
|
||||
NetworkGroup* GetGroupByID(uint8_t id) const;
|
||||
int32_t GetTotalNumPlayers() const noexcept;
|
||||
int32_t GetNumVisiblePlayers() const noexcept;
|
||||
void SetPassword(u8string_view password);
|
||||
uint8_t GetDefaultGroup() const noexcept;
|
||||
std::string BeginLog(const std::string& directory, const std::string& midName, const std::string& filenameFormat);
|
||||
@@ -177,6 +179,7 @@ public: // Public common
|
||||
std::string ServerProviderWebsite;
|
||||
std::vector<std::unique_ptr<NetworkPlayer>> player_list;
|
||||
std::vector<std::unique_ptr<NetworkGroup>> group_list;
|
||||
bool IsServerPlayerInvisible = false;
|
||||
|
||||
private: // Common Data
|
||||
using CommandHandler = void (NetworkBase::*)(NetworkConnection& connection, NetworkPacket& packet);
|
||||
@@ -189,7 +192,6 @@ private: // Common Data
|
||||
uint8_t default_group = 0;
|
||||
bool _closeLock = false;
|
||||
bool _requireClose = false;
|
||||
bool wsa_initialized = false;
|
||||
|
||||
private: // Server Data
|
||||
std::unordered_map<NetworkCommand, CommandHandler> server_command_handlers;
|
||||
|
||||
@@ -290,7 +290,7 @@ private:
|
||||
|
||||
json_t GetHeartbeatJson()
|
||||
{
|
||||
uint32_t numPlayers = network_get_num_players();
|
||||
uint32_t numPlayers = network_get_num_visible_players();
|
||||
|
||||
json_t root = {
|
||||
{ "token", _token },
|
||||
|
||||
@@ -56,6 +56,7 @@ void network_flush();
|
||||
[[nodiscard]] uint32_t network_get_server_tick();
|
||||
[[nodiscard]] uint8_t network_get_current_player_id();
|
||||
[[nodiscard]] int32_t network_get_num_players();
|
||||
[[nodiscard]] int32_t network_get_num_visible_players();
|
||||
[[nodiscard]] const char* network_get_player_name(uint32_t index);
|
||||
[[nodiscard]] uint32_t network_get_player_flags(uint32_t index);
|
||||
[[nodiscard]] int32_t network_get_player_ping(uint32_t index);
|
||||
@@ -92,6 +93,7 @@ void network_set_pickup_peep(uint8_t playerid, Peep* peep);
|
||||
[[nodiscard]] Peep* network_get_pickup_peep(uint8_t playerid);
|
||||
void network_set_pickup_peep_old_x(uint8_t playerid, int32_t x);
|
||||
[[nodiscard]] int32_t network_get_pickup_peep_old_x(uint8_t playerid);
|
||||
[[nodiscard]] bool network_is_server_player_invisible();
|
||||
|
||||
void network_send_chat(const char* text, const std::vector<uint8_t>& playerIds = {});
|
||||
void network_send_game_action(const GameAction* action);
|
||||
|
||||
Reference in New Issue
Block a user