Changeset - r25817:3f5c3838fe0a
[Not reviewed]
master
0 10 0
Patric Stout - 3 years ago 2021-07-11 19:57:05
truebrain@openttd.org
Add: allow setting your server visibility to "invite-only" (#9434)

In this mode you do register to the Game Coordinator, but your
server will not show up in the public server listing. You can give
your friends the invite code of the server with which they can
join.
10 files changed with 86 insertions and 31 deletions:
0 comments (0 inline, 0 general)
docs/multiplayer.md
Show inline comments
 
@@ -48,6 +48,10 @@ Last updated:    2011-02-16
 
    - click add server
 
    - type in the ip address or hostname
 
    - if you want to add a port use :<port>
 
 - If you want to play and you have the invite code of the game server you
 
   want connect to.
 
    - click add server
 
    - type in the invite code
 
 - Now you can select a company and press: "Join company", to help that company
 
    - Or you can press "Spectate game", to spectate the game
 
    - Or you can press "New company", and start your own company (if there are
 
@@ -110,9 +114,10 @@ Last updated:    2011-02-16
 
 - You can let your server automatically restart a map when, let's say, year 2030
 
   is reached. See 'set restart_game_date' for detail.
 

	
 
 - If you want to be on the server-list, enable Advertising. To do this, select
 
   'Internet (advertise)' in the Start Server menu, or type in console:
 
   'set server_advertise 1'.
 
 - If you want to be on the server-list, make your server public. You can do
 
   this either from the Start Server GUI, via the in-game Online Players GUI,
 
   or by typing in the console:
 
   'set server_game_type 1'.
 

	
 
 - You can protect your server with a password via the console: 'set server_pw',
 
   or via the Start Server menu.
src/console_cmds.cpp
Show inline comments
 
@@ -2420,7 +2420,6 @@ void IConsoleStdLibRegister()
 
	IConsole::AliasRegister("name",                  "setting client_name %+");
 
	IConsole::AliasRegister("server_name",           "setting server_name %+");
 
	IConsole::AliasRegister("server_port",           "setting server_port %+");
 
	IConsole::AliasRegister("server_advertise",      "setting server_advertise %+");
 
	IConsole::AliasRegister("max_clients",           "setting max_clients %+");
 
	IConsole::AliasRegister("max_companies",         "setting max_companies %+");
 
	IConsole::AliasRegister("max_spectators",        "setting max_spectators %+");
src/lang/english.txt
Show inline comments
 
@@ -1995,8 +1995,11 @@ STR_FACE_TIE                            
 
STR_FACE_EARRING                                                :Earring:
 
STR_FACE_TIE_EARRING_TOOLTIP                                    :{BLACK}Change tie or earring
 

	
 
############ Next lines match ServerGameType
 
STR_NETWORK_SERVER_VISIBILITY_LOCAL                             :Local
 
STR_NETWORK_SERVER_VISIBILITY_PUBLIC                            :Public
 
STR_NETWORK_SERVER_VISIBILITY_INVITE_ONLY                       :Invite only
 
############ End of leave-in-this-order
 

	
 
# Network server list
 
STR_NETWORK_SERVER_LIST_CAPTION                                 :{WHITE}Multiplayer
src/network/network.cpp
Show inline comments
 
@@ -934,7 +934,7 @@ bool NetworkServerStart()
 

	
 
	NetworkInitGameInfo();
 

	
 
	if (_settings_client.network.server_advertise) {
 
	if (_settings_client.network.server_game_type != SERVER_GAME_TYPE_LOCAL) {
 
		_network_coordinator_client.Register();
 
	}
 

	
 
@@ -1000,6 +1000,29 @@ void NetworkDisconnect(bool blocking, bo
 
}
 

	
 
/**
 
 * The setting server_game_type was updated; possibly we need to take some
 
 * action.
 
 */
 
void NetworkUpdateServerGameType()
 
{
 
	if (!_networking) return;
 

	
 
	switch (_settings_client.network.server_game_type) {
 
		case SERVER_GAME_TYPE_LOCAL:
 
			_network_coordinator_client.CloseConnection();
 
			break;
 

	
 
		case SERVER_GAME_TYPE_INVITE_ONLY:
 
		case SERVER_GAME_TYPE_PUBLIC:
 
			_network_coordinator_client.Register();
 
			break;
 

	
 
		default:
 
			NOT_REACHED();
 
	}
 
}
 

	
 
/**
 
 * Receives something from the network.
 
 * @return true if everything went fine, false when the connection got closed.
 
 */
src/network/network_coordinator.cpp
Show inline comments
 
@@ -94,8 +94,8 @@ bool ClientNetworkCoordinatorSocketHandl
 
			SetDParamStr(0, detail);
 
			ShowErrorMessage(STR_NETWORK_ERROR_COORDINATOR_REGISTRATION_FAILED, STR_JUST_RAW_STRING, WL_ERROR);
 

	
 
			/* To prevent that we constantly try to reconnect, switch to private game. */
 
			_settings_client.network.server_advertise = false;
 
			/* To prevent that we constantly try to reconnect, switch to local game. */
 
			_settings_client.network.server_game_type = SERVER_GAME_TYPE_LOCAL;
 

	
 
			this->CloseConnection();
 
			return false;
 
@@ -153,9 +153,18 @@ bool ClientNetworkCoordinatorSocketHandl
 
			default: connection_type = "Unknown"; break; // Should never happen, but don't fail if it does.
 
		}
 

	
 
		std::string game_type;
 
		switch (_settings_client.network.server_game_type) {
 
			case SERVER_GAME_TYPE_INVITE_ONLY: game_type = "Invite only"; break;
 
			case SERVER_GAME_TYPE_PUBLIC: game_type = "Public"; break;
 

	
 
			case SERVER_GAME_TYPE_LOCAL: // Impossible to register local servers.
 
			default: game_type = "Unknown"; break; // Should never happen, but don't fail if it does.
 
		}
 

	
 
		Debug(net, 3, "----------------------------------------");
 
		Debug(net, 3, "Your server is now registered with the Game Coordinator:");
 
		Debug(net, 3, "  Game type:       Public");
 
		Debug(net, 3, "  Game type:       {}", game_type);
 
		Debug(net, 3, "  Connection type: {}", connection_type);
 
		Debug(net, 3, "  Invite code:     {}", _network_server_invite_code);
 
		Debug(net, 3, "----------------------------------------");
 
@@ -298,7 +307,7 @@ void ClientNetworkCoordinatorSocketHandl
 

	
 
	Packet *p = new Packet(PACKET_COORDINATOR_SERVER_REGISTER);
 
	p->Send_uint8(NETWORK_COORDINATOR_VERSION);
 
	p->Send_uint8(SERVER_GAME_TYPE_PUBLIC);
 
	p->Send_uint8(_settings_client.network.server_game_type);
 
	p->Send_uint16(_settings_client.network.server_port);
 
	if (_settings_client.network.server_invite_code.empty() || _settings_client.network.server_invite_code_secret.empty()) {
 
		p->Send_string("");
 
@@ -467,7 +476,7 @@ void ClientNetworkCoordinatorSocketHandl
 
void ClientNetworkCoordinatorSocketHandler::SendReceive()
 
{
 
	/* Private games are not listed via the Game Coordinator. */
 
	if (_network_server && !_settings_client.network.server_advertise) {
 
	if (_network_server && _settings_client.network.server_game_type == SERVER_GAME_TYPE_LOCAL) {
 
		if (this->sock != INVALID_SOCKET) {
 
			this->CloseConnection();
 
		}
src/network/network_func.h
Show inline comments
 
@@ -39,6 +39,7 @@ bool NetworkValidateOurClientName();
 
bool NetworkValidateClientName(std::string &client_name);
 
bool NetworkValidateServerName(std::string &server_name);
 
void NetworkUpdateClientName(const std::string &client_name);
 
void NetworkUpdateServerGameType();
 
bool NetworkCompanyHasClients(CompanyID company);
 
std::string NetworkChangeCompanyPassword(CompanyID company_id, std::string password);
 
void NetworkReboot();
src/network/network_gui.cpp
Show inline comments
 
@@ -61,16 +61,6 @@ static ClientID _admin_client_id = INVAL
 
static CompanyID _admin_company_id = INVALID_COMPANY; ///< For what company a confirmation window is open.
 

	
 
/**
 
 * Visibility of the server. Public servers advertise, where private servers
 
 * do not.
 
 */
 
static const StringID _server_visibility_dropdown[] = {
 
	STR_NETWORK_SERVER_VISIBILITY_LOCAL,
 
	STR_NETWORK_SERVER_VISIBILITY_PUBLIC,
 
	INVALID_STRING_ID
 
};
 

	
 
/**
 
 * Update the network new window because a new server is
 
 * found on the network.
 
 */
 
@@ -79,6 +69,17 @@ void UpdateNetworkGameWindow()
 
	InvalidateWindowData(WC_NETWORK_WINDOW, WN_NETWORK_WINDOW_GAME, 0);
 
}
 

	
 
static DropDownList BuildVisibilityDropDownList()
 
{
 
	DropDownList list;
 

	
 
	list.emplace_back(new DropDownListStringItem(STR_NETWORK_SERVER_VISIBILITY_LOCAL, SERVER_GAME_TYPE_LOCAL, false));
 
	list.emplace_back(new DropDownListStringItem(STR_NETWORK_SERVER_VISIBILITY_INVITE_ONLY, SERVER_GAME_TYPE_INVITE_ONLY, false));
 
	list.emplace_back(new DropDownListStringItem(STR_NETWORK_SERVER_VISIBILITY_PUBLIC, SERVER_GAME_TYPE_PUBLIC, false));
 

	
 
	return list;
 
}
 

	
 
typedef GUIList<NetworkGameList*, StringFilter&> GUIGameServerList;
 
typedef int ServerListPosition;
 
static const ServerListPosition SLP_INVALID = -1;
 
@@ -1015,7 +1016,7 @@ struct NetworkStartServerWindow : public
 
	{
 
		switch (widget) {
 
			case WID_NSS_CONNTYPE_BTN:
 
				SetDParam(0, _server_visibility_dropdown[_settings_client.network.server_advertise]);
 
				SetDParam(0, STR_NETWORK_SERVER_VISIBILITY_LOCAL + _settings_client.network.server_game_type);
 
				break;
 

	
 
			case WID_NSS_CLIENTS_TXT:
 
@@ -1036,7 +1037,7 @@ struct NetworkStartServerWindow : public
 
	{
 
		switch (widget) {
 
			case WID_NSS_CONNTYPE_BTN:
 
				*size = maxdim(GetStringBoundingBox(_server_visibility_dropdown[0]), GetStringBoundingBox(_server_visibility_dropdown[1]));
 
				*size = maxdim(maxdim(GetStringBoundingBox(STR_NETWORK_SERVER_VISIBILITY_LOCAL), GetStringBoundingBox(STR_NETWORK_SERVER_VISIBILITY_PUBLIC)), GetStringBoundingBox(STR_NETWORK_SERVER_VISIBILITY_INVITE_ONLY));
 
				size->width += padding.width;
 
				size->height += padding.height;
 
				break;
 
@@ -1066,7 +1067,7 @@ struct NetworkStartServerWindow : public
 
				break;
 

	
 
			case WID_NSS_CONNTYPE_BTN: // Connection type
 
				ShowDropDownMenu(this, _server_visibility_dropdown, _settings_client.network.server_advertise, WID_NSS_CONNTYPE_BTN, 0, 0); // do it for widget WID_NSS_CONNTYPE_BTN
 
				ShowDropDownList(this, BuildVisibilityDropDownList(), _settings_client.network.server_game_type, WID_NSS_CONNTYPE_BTN);
 
				break;
 

	
 
			case WID_NSS_CLIENTS_BTND:    case WID_NSS_CLIENTS_BTNU:    // Click on up/down button for number of clients
 
@@ -1144,7 +1145,7 @@ struct NetworkStartServerWindow : public
 
	{
 
		switch (widget) {
 
			case WID_NSS_CONNTYPE_BTN:
 
				_settings_client.network.server_advertise = (index != 0);
 
				_settings_client.network.server_game_type = (ServerGameType)index;
 
				break;
 
			default:
 
				NOT_REACHED();
 
@@ -2041,7 +2042,7 @@ public:
 
	{
 
		switch (widget) {
 
			case WID_CL_SERVER_VISIBILITY:
 
				*size = maxdim(GetStringBoundingBox(_server_visibility_dropdown[0]), GetStringBoundingBox(_server_visibility_dropdown[1]));
 
				*size = maxdim(maxdim(GetStringBoundingBox(STR_NETWORK_SERVER_VISIBILITY_LOCAL), GetStringBoundingBox(STR_NETWORK_SERVER_VISIBILITY_PUBLIC)), GetStringBoundingBox(STR_NETWORK_SERVER_VISIBILITY_INVITE_ONLY));
 
				size->width += padding.width;
 
				size->height += padding.height;
 
				break;
 
@@ -2073,7 +2074,7 @@ public:
 
				break;
 

	
 
			case WID_CL_SERVER_VISIBILITY:
 
				SetDParam(0, _server_visibility_dropdown[_settings_client.network.server_advertise]);
 
				SetDParam(0, STR_NETWORK_SERVER_VISIBILITY_LOCAL + _settings_client.network.server_game_type);
 
				break;
 

	
 
			case WID_CL_SERVER_INVITE_CODE: {
 
@@ -2117,7 +2118,7 @@ public:
 
			case WID_CL_SERVER_VISIBILITY:
 
				if (!_network_server) break;
 

	
 
				ShowDropDownMenu(this, _server_visibility_dropdown, _settings_client.network.server_advertise, WID_CL_SERVER_VISIBILITY, 0, 0);
 
				ShowDropDownList(this, BuildVisibilityDropDownList(), _settings_client.network.server_game_type, WID_CL_SERVER_VISIBILITY);
 
				break;
 

	
 
			case WID_CL_MATRIX: {
 
@@ -2183,7 +2184,8 @@ public:
 
			case WID_CL_SERVER_VISIBILITY:
 
				if (!_network_server) break;
 

	
 
				_settings_client.network.server_advertise = (index != 0);
 
				_settings_client.network.server_game_type = (ServerGameType)index;
 
				NetworkUpdateServerGameType();
 
				break;
 

	
 
			case WID_CL_MATRIX: {
src/network/network_type.h
Show inline comments
 
@@ -42,6 +42,7 @@ enum NetworkVehicleType {
 
enum ServerGameType : uint8 {
 
	SERVER_GAME_TYPE_LOCAL = 0,
 
	SERVER_GAME_TYPE_PUBLIC,
 
	SERVER_GAME_TYPE_INVITE_ONLY,
 
};
 

	
 
/** 'Unique' identifier to be given to clients */
src/settings_type.h
Show inline comments
 
@@ -15,6 +15,7 @@
 
#include "town_type.h"
 
#include "transport_type.h"
 
#include "network/core/config.h"
 
#include "network/network_type.h"
 
#include "company_type.h"
 
#include "cargotype.h"
 
#include "linkgraph/linkgraph_type.h"
 
@@ -266,6 +267,7 @@ struct NetworkSettings {
 
	uint16      server_port;                              ///< port the server listens on
 
	uint16      server_admin_port;                        ///< port the server listens on for the admin network
 
	bool        server_admin_chat;                        ///< allow private chat for the server to be distributed to the admin network
 
	ServerGameType server_game_type;                      ///< Server type: local / public / invite-only.
 
	std::string server_invite_code;                       ///< Invite code to use when registering as server.
 
	std::string server_invite_code_secret;                ///< Secret to proof we got this invite code from the Game Coordinator.
 
	std::string server_name;                              ///< name of the server
src/table/settings/network_settings.ini
Show inline comments
 
@@ -9,14 +9,18 @@
 
[pre-amble]
 
static void UpdateClientConfigValues();
 

	
 
static std::initializer_list<const char*> _server_game_type{"local", "public", "invite-only"};
 

	
 
static const SettingVariant _network_settings_table[] = {
 
[post-amble]
 
};
 
[templates]
 
SDTC_BOOL  =  SDTC_BOOL(              $var,        $flags, $def,                              $str, $strhelp, $strval, $pre_cb, $post_cb, $from, $to,        $cat, $extra, $startup),
 
SDTC_OMANY = SDTC_OMANY(              $var, $type, $flags, $def,             $max, $full,     $str, $strhelp, $strval, $pre_cb, $post_cb, $from, $to,        $cat, $extra, $startup),
 
SDTC_VAR   =   SDTC_VAR(              $var, $type, $flags, $def,       $min, $max, $interval, $str, $strhelp, $strval, $pre_cb, $post_cb, $from, $to,        $cat, $extra, $startup),
 

	
 
[validation]
 
SDTC_OMANY = static_assert($max <= MAX_$type, "Maximum value for $var exceeds storage size");
 
SDTC_VAR = static_assert($max <= MAX_$type, "Maximum value for $var exceeds storage size");
 

	
 
[defaults]
 
@@ -159,10 +163,16 @@ flags    = SF_NOT_IN_SAVE | SF_NO_NETWOR
 
def      = true
 
cat      = SC_EXPERT
 

	
 
[SDTC_BOOL]
 
var      = network.server_advertise
 
[SDTC_OMANY]
 
var      = network.server_game_type
 
type     = SLE_UINT8
 
flags    = SF_NOT_IN_SAVE | SF_NO_NETWORK_SYNC | SF_NETWORK_ONLY
 
def      = false
 
def      = SERVER_GAME_TYPE_LOCAL
 
min      = SERVER_GAME_TYPE_LOCAL
 
max      = SERVER_GAME_TYPE_INVITE_ONLY
 
full     = _server_game_type
 
post_cb  = [](auto) { NetworkUpdateServerGameType(); }
 
cat      = SC_BASIC
 

	
 
[SDTC_BOOL]
 
var      = network.autoclean_companies
0 comments (0 inline, 0 general)