#ifndef _MultiplayerCommon_h_ #define _MultiplayerCommon_h_ #include "../universe/EnumsFwd.h" #include "../network/Networking.h" #include "Export.h" #include "OptionsDB.h" #include "Pending.h" #include "Serialize.h" #include #include #include #include #include #include #include FO_COMMON_API extern const std::string MP_SAVE_FILE_EXTENSION; FO_COMMON_API extern const std::string SP_SAVE_FILE_EXTENSION; FO_COMMON_API extern const int ALL_EMPIRES; FO_COMMON_API extern const int INVALID_GAME_TURN; /** The data that represent the galaxy setup for a new game. */ struct FO_COMMON_API GalaxySetupData { /** \name Structors */ //@{ GalaxySetupData(); GalaxySetupData(const GalaxySetupData&) = default; GalaxySetupData(GalaxySetupData&& base); //@} /** \name Accessors */ //@{ const std::string& GetSeed() const; int GetSize() const; Shape GetShape() const; GalaxySetupOption GetAge() const; GalaxySetupOption GetStarlaneFreq() const; GalaxySetupOption GetPlanetDensity() const; GalaxySetupOption GetSpecialsFreq() const; GalaxySetupOption GetMonsterFreq() const; GalaxySetupOption GetNativeFreq() const; Aggression GetAggression() const; const std::map& GetGameRules() const; const std::string& GetGameUID() const; //@} /** \name Mutators */ //@{ void SetSeed(const std::string& seed); void SetGameUID(const std::string& game_uid); //@} GalaxySetupData& operator=(const GalaxySetupData&) = default; std::string m_seed; int m_size; Shape m_shape; GalaxySetupOption m_age; GalaxySetupOption m_starlane_freq; GalaxySetupOption m_planet_density; GalaxySetupOption m_specials_freq; GalaxySetupOption m_monster_freq; GalaxySetupOption m_native_freq; Aggression m_ai_aggr; std::map m_game_rules; std::string m_game_uid; /** HACK! This must be set to the encoding empire's id when serializing a * GalaxySetupData, so that only the relevant parts of the galaxy data are * serialized. The use of this local field is done just so I don't * have to rewrite any custom boost::serialization classes that implement * empire-dependent visibility. */ int m_encoding_empire; ///< used during serialization to globally set what empire knowledge to use private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; BOOST_CLASS_VERSION(GalaxySetupData, 3); /** Contains the UI data that must be saved in save game files in order to * restore games to the users' last views. */ struct FO_COMMON_API SaveGameUIData { int map_top = 0; int map_left = 0; double map_zoom_steps_in = 0.0; std::set fleets_exploring; // See DesignWnd.cpp for the usage of the following variables. int obsolete_ui_event_count = 0; std::vector>>> ordered_ship_design_ids_and_obsolete; std::vector>> ordered_ship_hull_and_obsolete; std::unordered_map obsolete_ship_parts; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; BOOST_CLASS_VERSION(SaveGameUIData, 4); /** The data for one empire necessary for game-setup during multiplayer loading. */ struct FO_COMMON_API SaveGameEmpireData { /** \name Structors */ //@{ SaveGameEmpireData() : m_empire_id(ALL_EMPIRES), m_empire_name(), m_player_name(), m_color(), m_authenticated(false), m_eliminated(false), m_won(false) {} SaveGameEmpireData(int empire_id, const std::string& empire_name, const std::string& player_name, const GG::Clr& colour, bool authenticated, bool eliminated, bool won) : m_empire_id(empire_id), m_empire_name(empire_name), m_player_name(player_name), m_color(colour), m_authenticated(authenticated), m_eliminated(eliminated), m_won(won) {} //@} int m_empire_id; std::string m_empire_name; std::string m_player_name; GG::Clr m_color; bool m_authenticated; bool m_eliminated; bool m_won; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; BOOST_CLASS_VERSION(SaveGameEmpireData, 2); /** Contains basic data about a player in a game. */ struct FO_COMMON_API PlayerSaveHeaderData { PlayerSaveHeaderData() : m_name(), m_empire_id(ALL_EMPIRES), m_client_type(Networking::INVALID_CLIENT_TYPE) {} PlayerSaveHeaderData(const std::string& name, int empire_id, Networking::ClientType client_type) : m_name(name), m_empire_id(empire_id), m_client_type(client_type) {} std::string m_name; int m_empire_id; Networking::ClientType m_client_type; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; /** Contains data that must be saved for a single player. */ struct FO_COMMON_API PlayerSaveGameData : public PlayerSaveHeaderData { PlayerSaveGameData() : PlayerSaveHeaderData(), m_orders(), m_ui_data(), m_save_state_string() {} PlayerSaveGameData(const std::string& name, int empire_id, const std::shared_ptr& orders, const std::shared_ptr& ui_data, const std::string& save_state_string, Networking::ClientType client_type) : PlayerSaveHeaderData(name, empire_id, client_type), m_orders(orders), m_ui_data(ui_data), m_save_state_string(save_state_string) {} std::shared_ptr m_orders; std::shared_ptr m_ui_data; std::string m_save_state_string; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; BOOST_CLASS_VERSION(PlayerSaveGameData, 2); /** Data that must be retained by the server when saving and loading a * game that isn't player data or the universe */ struct FO_COMMON_API ServerSaveGameData { ServerSaveGameData() : m_current_turn(INVALID_GAME_TURN) {} ServerSaveGameData(int current_turn) : m_current_turn(current_turn) {} int m_current_turn; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; /** The data structure used to represent a single player's setup options for a * multiplayer game (in the multiplayer lobby screen). */ struct PlayerSetupData { /** \name Structors */ //@{ PlayerSetupData() : m_player_name(), m_player_id(Networking::INVALID_PLAYER_ID), m_empire_name(), m_empire_color(GG::Clr(0, 0, 0, 0)), m_starting_species_name(), m_save_game_empire_id(ALL_EMPIRES), m_client_type(Networking::INVALID_CLIENT_TYPE), m_player_ready(false), m_authenticated(false), m_starting_team(Networking::NO_TEAM_ID) {} //@} std::string m_player_name; ///< the player's name int m_player_id; ///< player id std::string m_empire_name; ///< the name of the player's empire when starting a new game GG::Clr m_empire_color; ///< the color used to represent this player's empire when starting a new game std::string m_starting_species_name;///< name of the species with which the player starts when starting a new game int m_save_game_empire_id; ///< when loading a game, the ID of the empire that this player will control Networking::ClientType m_client_type; ///< is this player an AI, human player or...? bool m_player_ready; ///< if player ready to play. bool m_authenticated; ///< if player was authenticated int m_starting_team; ///< team id or -1 if no team. private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; bool FO_COMMON_API operator==(const PlayerSetupData& lhs, const PlayerSetupData& rhs); bool operator!=(const PlayerSetupData& lhs, const PlayerSetupData& rhs); BOOST_CLASS_VERSION(PlayerSetupData, 2); /** The data needed to establish a new single player game. If \a m_new_game * is true, a new game is to be started, using the remaining members besides * \a m_filename. Otherwise, the saved game \a m_filename will be loaded * instead. */ struct SinglePlayerSetupData : public GalaxySetupData { /** \name Structors */ //@{ SinglePlayerSetupData(): m_new_game(true), m_filename(), m_players() {} //@} bool m_new_game; std::string m_filename; std::vector m_players; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; /** The data structure that represents the state of the multiplayer lobby. */ struct FO_COMMON_API MultiplayerLobbyData : public GalaxySetupData { /** \name Structors */ //@{ MultiplayerLobbyData() : m_any_can_edit(false), m_new_game(true), m_start_locked(false), m_players(), m_save_game(), m_save_game_empire_data(), m_save_game_current_turn(0), m_in_game(false) {} MultiplayerLobbyData(const GalaxySetupData& base) : GalaxySetupData(base), m_any_can_edit(false), m_new_game(true), m_start_locked(false), m_players(), m_save_game(), m_save_game_empire_data(), m_save_game_current_turn(0), m_in_game(false) {} MultiplayerLobbyData(GalaxySetupData&& base) : GalaxySetupData(std::move(base)), m_any_can_edit(false), m_new_game(true), m_start_locked(false), m_players(), m_save_game(), m_save_game_empire_data(), m_save_game_current_turn(0), m_in_game(false) {} //@} std::string Dump() const; bool m_any_can_edit; bool m_new_game; bool m_start_locked; // TODO: Change from a list<(player_id, PlayerSetupData)> where // PlayerSetupData contain player_id to a vector of PlayerSetupData std::list> m_players; // std::string m_save_game; //< File name of a save file std::map m_save_game_empire_data;// indexed by empire_id int m_save_game_current_turn; std::string m_start_lock_cause; bool m_in_game; ///< In-game lobby private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; BOOST_CLASS_VERSION(MultiplayerLobbyData, 2); /** The data structure stores information about latest chat massages. */ struct FO_COMMON_API ChatHistoryEntity { /** \name Structors */ //@{ ChatHistoryEntity() {} //@} boost::posix_time::ptime m_timestamp; std::string m_player_name; std::string m_text; GG::Clr m_text_color; private: friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; BOOST_CLASS_VERSION(ChatHistoryEntity, 1); /** Information about one player that other players are informed of. Assembled by server and sent to players. */ struct PlayerInfo { PlayerInfo() : name(""), empire_id(ALL_EMPIRES), client_type(Networking::INVALID_CLIENT_TYPE), host(false) {} PlayerInfo(const std::string& player_name_, int empire_id_, Networking::ClientType client_type_, bool host_) : name(player_name_), empire_id(empire_id_), client_type(client_type_), host(host_) {} std::string name; ///< name of this player (not the same as the empire name) int empire_id; ///< id of the player's empire Networking::ClientType client_type; ///< is this a human player, AI player, or observer? bool host; ///< true iff this is the host player friend class boost::serialization::access; template void serialize(Archive& ar, const unsigned int version); }; // Note: *::serialize() implemented in SerializeMultiplayerCommon.cpp. #endif // _MultiplayerCommon_h_