示例#1
0
boost::statechart::result WaitingForTurnData::react(const GameStart& msg) {
    if (TRACE_EXECUTION) Logger().debugStream() << "(HumanClientFSM) WaitingForTurnData.GameStart";
    bool loaded_game_data;
    bool ui_data_available;
    SaveGameUIData ui_data;
    bool save_state_string_available;
    std::string save_state_string; // ignored - used by AI but not by human client
    OrderSet orders;

    ExtractMessageData(msg.m_message,               Client().m_single_player_game,      Client().EmpireIDRef(),
                       Client().CurrentTurnRef(),   Empires(),                          GetUniverse(),
                       GetSpeciesManager(),         Client().m_player_info,             orders,
                       loaded_game_data,            ui_data_available,                  ui_data,
                       save_state_string_available, save_state_string);

    Client().StartGame();
    std::swap(Client().Orders(), orders); // bring back orders planned in the current turn, they will be applied later, after some basic turn initialization
    if (loaded_game_data && ui_data_available)
        Client().m_ui->RestoreFromSaveData(ui_data);

    // if I am the host on the first turn, do an autosave. on later turns, will
    // have just loaded save, so don't need to autosave. might also have just
    // loaded a turn 1 autosave, but not sure how to check for that here...
    if (Client().CurrentTurn() == 1 && Client().Networking().PlayerIsHost(Client().PlayerID()))
        Client().Autosave();

    return transit<PlayingTurn>();
}
示例#2
0
void MessageWndEdit::FindGameWords() {
     // add player and empire names
    for (std::map<int, Empire*>::value_type& entry : Empires()) {
        m_game_words.insert(entry.second->Name());
        m_game_words.insert(entry.second->PlayerName());
    }
    // add system names
    for (std::shared_ptr<System> system : GetUniverse().Objects().FindObjects<System>()) {
        if (system->Name() != "")
            m_game_words.insert(system->Name());
    }
     // add ship names
    for (std::shared_ptr<Ship> ship : GetUniverse().Objects().FindObjects<Ship>()) {
        if (ship->Name() != "")
            m_game_words.insert(ship->Name());
    }
     // add ship design names

    for (const auto& design : GetPredefinedShipDesignManager().GetOrderedShipDesigns()) {
        if (!design->Name().empty())
            m_game_words.insert(UserString(design->Name()));
    }
     // add specials names
    for (const std::string& special_name : SpecialNames()) {
        if (special_name != "")
            m_game_words.insert(UserString(special_name));
    }
     // add species names
    for (const std::map<std::string, Species*>::value_type& entry : GetSpeciesManager()) {
        if (entry.second->Name() != "")
            m_game_words.insert(UserString(entry.second->Name()));
    }
     // add techs names
    for (const std::string& tech_name : GetTechManager().TechNames()) {
        if (tech_name != "")
            m_game_words.insert(UserString(tech_name));
    }
    // add building type names
    for (const auto& entry : GetBuildingTypeManager()) {
        if (entry.second->Name() != "")
            m_game_words.insert(UserString(entry.second->Name()));
    }
    // add ship hulls
    for (const auto& design : GetPredefinedShipDesignManager().GetOrderedShipDesigns()) {
        if (!design->Hull().empty())
            m_game_words.insert(UserString(design->Hull()));
    }
    // add ship parts
    for (const auto& design : GetPredefinedShipDesignManager().GetOrderedShipDesigns()) {
        for (const std::string& part_name : design->Parts()) {
            if (part_name != "")
                m_game_words.insert(UserString(part_name));
        }
    }
 }
示例#3
0
bool SetEmpireHomeworld(Empire* empire, int planet_id, std::string species_name) {
    // get home planet and system, check if they exist
    TemporaryPtr<Planet> home_planet = GetPlanet(planet_id);
    TemporaryPtr<System> home_system;
    if (home_planet)
        home_system = GetSystem(home_planet->SystemID());
    if (!home_planet || !home_system) {
        ErrorLogger() << "SetEmpireHomeworld: couldn't get homeworld or system for empire" << empire->EmpireID();
        return false;
    }

    DebugLogger() << "SetEmpireHomeworld: setting system " << home_system->ID()
                  << " (planet " <<  home_planet->ID() << ") to be home system for empire " << empire->EmpireID();

    // get species, check if it exists
    Species* species = GetSpeciesManager().GetSpecies(species_name);
    if (!species) {
        ErrorLogger() << "SetEmpireHomeworld: couldn't get species \""
                      << species_name << "\" to set with homeworld id " << home_planet->ID();
        return false;
    }

    // set homeword's planet type to the preferred type for this species
    const std::map<PlanetType, PlanetEnvironment>& spte = species->PlanetEnvironments();
    if (!spte.empty()) {
        // invert map from planet type to environments to map from
        // environments to type, sorted by environment
        std::map<PlanetEnvironment, PlanetType> sept;
        for (std::map<PlanetType, PlanetEnvironment>::const_iterator it = spte.begin(); it != spte.end(); ++it)
            sept[it->second] = it->first;
        // assuming enum values are ordered in increasing goodness...
        PlanetType preferred_planet_type = sept.rbegin()->second;

        // both the current as well as the original type need to be set to the preferred type
        home_planet->SetType(preferred_planet_type);
        home_planet->SetOriginalType(preferred_planet_type);
        // set planet size according to planet type
        if (preferred_planet_type == PT_ASTEROIDS)
            home_planet->SetSize(SZ_ASTEROIDS);
        else if (preferred_planet_type == PT_GASGIANT)
            home_planet->SetSize(SZ_GASGIANT);
        else
            home_planet->SetSize(SZ_MEDIUM);
    }

    home_planet->Colonize(empire->EmpireID(), species_name, Meter::LARGE_VALUE);
    species->AddHomeworld(home_planet->ID());
    empire->SetCapitalID(home_planet->ID());
    empire->AddExploredSystem(home_planet->SystemID());

    return true;
}
示例#4
0
boost::statechart::result WaitingForTurnData::react(const TurnUpdate& msg) {
    if (TRACE_EXECUTION) Logger().debugStream() << "(HumanClientFSM) WaitingForTurnData.TurnUpdate";

    ExtractMessageData(msg.m_message,   Client().EmpireID(),    Client().CurrentTurnRef(),
                       Empires(),       GetUniverse(),          GetSpeciesManager(),
                       Client().m_player_info);

    // if I am the host, do autosave
    if (Client().Networking().PlayerIsHost(Client().PlayerID()))
        Client().Autosave();

    return transit<PlayingTurn>();
}
示例#5
0
boost::statechart::result WaitingForTurnData::react(const TurnUpdate& msg) {
    if (TRACE_EXECUTION) Logger().debugStream() << "(HumanClientFSM) WaitingForTurnData.TurnUpdate";

    ExtractMessageData(msg.m_message,   Client().EmpireID(),    Client().CurrentTurnRef(),
                       Empires(),       GetUniverse(),          GetSpeciesManager(),
                       Client().m_player_info);

    // if I am the host, do autosave
    for (std::map<int, PlayerInfo>::const_iterator it = Client().m_player_info.begin(); it != Client().m_player_info.end(); ++it)
        if (it->second.host && it->first == Client().PlayerID())
            Client().Autosave();

    return transit<PlayingTurn>();
}
示例#6
0
void IApp::StartBackgroundParsing() {
    const auto& rdir = GetResourceDir();

    GetBuildingTypeManager().SetBuildingTypes(Pending::StartParsing(parse::buildings, rdir / "scripting/buildings"));
    GetEncyclopedia().SetArticles(Pending::StartParsing(parse::encyclopedia_articles, rdir / "scripting/encyclopedia"));
    GetFieldTypeManager().SetFieldTypes(Pending::StartParsing(parse::fields, rdir / "scripting/fields"));
    GetSpecialsManager().SetSpecialsTypes(Pending::StartParsing(parse::specials, rdir / "scripting/specials"));
    GetSpeciesManager().SetSpeciesTypes(Pending::StartParsing(parse::species, rdir / "scripting/species"));
    GetPartTypeManager().SetPartTypes(Pending::StartParsing(parse::ship_parts, rdir / "scripting/ship_parts"));
    GetHullTypeManager().SetHullTypes(Pending::StartParsing(parse::ship_hulls, rdir / "scripting/ship_hulls"));
    GetPredefinedShipDesignManager().SetShipDesignTypes(
        Pending::StartParsing(parse::ship_designs, rdir / "scripting/ship_designs"));
    GetPredefinedShipDesignManager().SetMonsterDesignTypes(
        Pending::StartParsing(parse::ship_designs, rdir / "scripting/monster_designs"));
    GetGameRules().Add(Pending::StartParsing(parse::game_rules, rdir / "scripting/game_rules.focs.txt"));
    GetTechManager().SetTechs(Pending::StartParsing(parse::techs<TechManager::TechParseTuple>, rdir / "scripting/techs"));

    InitEmpireColors(rdir / "empire_colors.xml");
}
示例#7
0
boost::statechart::result WaitingForGameStart::react(const GameStart& msg) {
    TraceLogger(FSM) << "(HumanClientFSM) WaitingForGameStart.GameStart";

    bool loaded_game_data;
    bool ui_data_available;
    SaveGameUIData ui_data;
    bool save_state_string_available;
    std::string save_state_string; // ignored - used by AI but not by human client
    OrderSet orders;
    bool single_player_game = false;
    int empire_id = ALL_EMPIRES;
    int current_turn = INVALID_GAME_TURN;
    Client().PlayerStatus().clear();
    Client().Orders().Reset();

    ExtractGameStartMessageData(msg.m_message,       single_player_game,             empire_id,
                                current_turn,        Empires(),                      GetUniverse(),
                                GetSpeciesManager(), GetCombatLogManager(),          GetSupplyManager(),
                                Client().Players(),  Client().Orders(),              loaded_game_data,
                                ui_data_available,   ui_data,                        save_state_string_available,
                                save_state_string,   Client().GetGalaxySetupData());

    DebugLogger(FSM) << "Extracted GameStart message for turn: " << current_turn << " with empire: " << empire_id;

    Client().SetSinglePlayerGame(single_player_game);
    Client().SetEmpireID(empire_id);
    Client().SetCurrentTurn(current_turn);

    GetGameRules().SetFromStrings(Client().GetGalaxySetupData().GetGameRules());

    bool is_new_game = !(loaded_game_data && ui_data_available);
    Client().StartGame(is_new_game);

    if (!is_new_game)
        Client().GetClientUI().RestoreFromSaveData(ui_data);

    // if I am the host on the first turn, do an autosave.
    if (is_new_game && Client().Networking().PlayerIsHost(Client().PlayerID()))
        Client().Autosave();

    return transit<PlayingTurn>();
}
示例#8
0
boost::statechart::result WaitingForGameStart::react(const GameStart& msg) {
    if (TRACE_EXECUTION) DebugLogger() << "(HumanClientFSM) WaitingForGameStart.GameStart";

    bool loaded_game_data;
    bool ui_data_available;
    SaveGameUIData ui_data;
    bool save_state_string_available;
    std::string save_state_string; // ignored - used by AI but not by human client
    OrderSet orders;
    bool single_player_game = false;
    int empire_id = ALL_EMPIRES;
    int current_turn = INVALID_GAME_TURN;
    Client().PlayerStatus().clear();

    ExtractMessageData(msg.m_message,       single_player_game,             empire_id,
                       current_turn,        Empires(),                      GetUniverse(),
                       GetSpeciesManager(), GetCombatLogManager(),          Client().Players(),
                       orders,              loaded_game_data,               ui_data_available,
                       ui_data,             save_state_string_available,    save_state_string,
                       Client().GetGalaxySetupData());

    DebugLogger() << "Extracted GameStart message for turn: " << current_turn << " with empire: " << empire_id;

    Client().SetSinglePlayerGame(single_player_game);
    Client().SetEmpireID(empire_id);
    Client().SetCurrentTurn(current_turn);

    Client().StartGame();
    std::swap(Client().Orders(), orders); // bring back orders planned in the current turn, they will be applied later, after some basic turn initialization
    if (loaded_game_data && ui_data_available)
        Client().GetClientUI()->RestoreFromSaveData(ui_data);

    // if I am the host on the first turn, do an autosave. on later turns, will
    // have just loaded save, so don't need to autosave. might also have just
    // loaded a turn 1 autosave, but not sure how to check for that here...
    if (Client().CurrentTurn() == 1 && Client().Networking().PlayerIsHost(Client().PlayerID()))
        Client().Autosave();

    return transit<PlayingTurn>();
}
示例#9
0
boost::statechart::result WaitingForTurnData::react(const TurnUpdate& msg) {
    if (TRACE_EXECUTION) DebugLogger() << "(HumanClientFSM) PlayingGame.TurnUpdate";

    int current_turn = INVALID_GAME_TURN;

    try {
        ExtractMessageData(msg.m_message,           Client().EmpireID(),    current_turn,
                           Empires(),               GetUniverse(),          GetSpeciesManager(),
                           GetCombatLogManager(),   Client().Players());
    } catch (...) {
        Client().GetClientUI()->GetMessageWnd()->HandleLogMessage(UserString("ERROR_PROCESSING_SERVER_MESSAGE") + "\n");
        return discard_event();
    }

    DebugLogger() << "Extracted TurnUpdate message for turn: " << current_turn;

    Client().SetCurrentTurn(current_turn);

    // if I am the host, do autosave
    if (Client().Networking().PlayerIsHost(Client().PlayerID()))
        Client().Autosave();

    return transit<PlayingTurn>();
}
示例#10
0
void HumanClientApp::NewSinglePlayerGame(bool quickstart) {
    if (!GetOptionsDB().Get<bool>("force-external-server")) {
        try {
            StartServer();
        } catch (const std::runtime_error& err) {
            ErrorLogger() << "HumanClientApp::NewSinglePlayerGame : Couldn't start server.  Got error message: " << err.what();
            ClientUI::MessageBox(UserString("SERVER_WONT_START"), true);
            return;
        }
    }

    bool ended_with_ok = false;
    if (!quickstart) {
        GalaxySetupWnd galaxy_wnd;
        galaxy_wnd.Run();
        ended_with_ok = galaxy_wnd.EndedWithOk();
    }

    bool failed = false;
    unsigned int start_time = Ticks();
    while (!m_networking.ConnectToLocalHostServer(boost::posix_time::seconds(2))) {
        if (SERVER_CONNECT_TIMEOUT < Ticks() - start_time) {
            ClientUI::MessageBox(UserString("ERR_CONNECT_TIMED_OUT"), true);
            failed = true;
            break;
        }
    }
    m_connected = !failed;
    if (!failed && (quickstart || ended_with_ok)) {
        DebugLogger() << "HumanClientApp::NewSinglePlayerGame : Connected to server";

        SinglePlayerSetupData setup_data;
        setup_data.m_new_game = true;
        setup_data.m_filename.clear();  // not used for new game

        // get values stored in options from previous time game was run or
        // from just having run GalaxySetupWnd

        // GalaxySetupData
        setup_data.m_seed =             GetOptionsDB().Get<std::string>("GameSetup.seed");
        setup_data.m_size =             GetOptionsDB().Get<int>("GameSetup.stars");
        setup_data.m_shape =            GetOptionsDB().Get<Shape>("GameSetup.galaxy-shape");
        setup_data.m_age =              GetOptionsDB().Get<GalaxySetupOption>("GameSetup.galaxy-age");
        setup_data.m_starlane_freq =    GetOptionsDB().Get<GalaxySetupOption>("GameSetup.starlane-frequency");
        setup_data.m_planet_density =   GetOptionsDB().Get<GalaxySetupOption>("GameSetup.planet-density");
        setup_data.m_specials_freq =    GetOptionsDB().Get<GalaxySetupOption>("GameSetup.specials-frequency");
        setup_data.m_monster_freq =     GetOptionsDB().Get<GalaxySetupOption>("GameSetup.monster-frequency");
        setup_data.m_native_freq =      GetOptionsDB().Get<GalaxySetupOption>("GameSetup.native-frequency");
        setup_data.m_ai_aggr =          GetOptionsDB().Get<Aggression>("GameSetup.ai-aggression");

        // SinglePlayerSetupData contains a map of PlayerSetupData, for
        // the human and AI players.  Need to compile this information
        // from the specified human options and number of requested AIs

        // Human player setup data first

        PlayerSetupData human_player_setup_data;
        human_player_setup_data.m_player_name = GetOptionsDB().Get<std::string>("GameSetup.player-name");
        human_player_setup_data.m_empire_name = GetOptionsDB().Get<std::string>("GameSetup.empire-name");

        // DB stores index into array of available colours, so need to get that array to look up value of index.
        // if stored value is invalid, use a default colour
        const std::vector<GG::Clr>& empire_colours = EmpireColors();
        int colour_index = GetOptionsDB().Get<int>("GameSetup.empire-color");
        if (colour_index >= 0 && colour_index < static_cast<int>(empire_colours.size()))
            human_player_setup_data.m_empire_color = empire_colours[colour_index];
        else
            human_player_setup_data.m_empire_color = GG::CLR_GREEN;

        human_player_setup_data.m_starting_species_name = GetOptionsDB().Get<std::string>("GameSetup.starting-species");
        if (human_player_setup_data.m_starting_species_name == "1")
            human_player_setup_data.m_starting_species_name = "SP_HUMAN";   // kludge / bug workaround for bug with options storage and retreival.  Empty-string options are stored, but read in as "true" boolean, and converted to string equal to "1"

        if (!GetSpecies(human_player_setup_data.m_starting_species_name)) {
            const SpeciesManager& sm = GetSpeciesManager();
            if (sm.NumPlayableSpecies() < 1)
                human_player_setup_data.m_starting_species_name.clear();
            else
                human_player_setup_data.m_starting_species_name = sm.playable_begin()->first;
            }

        human_player_setup_data.m_save_game_empire_id = ALL_EMPIRES; // not used for new games
        human_player_setup_data.m_client_type = Networking::CLIENT_TYPE_HUMAN_PLAYER;

        // add to setup data players
        setup_data.m_players.push_back(human_player_setup_data);

        // AI player setup data.  One entry for each requested AI

        int num_AIs = GetOptionsDB().Get<int>("GameSetup.ai-players");
        for (int ai_i = 1; ai_i <= num_AIs; ++ai_i) {
            PlayerSetupData ai_setup_data;

            ai_setup_data.m_player_name = "AI_" + boost::lexical_cast<std::string>(ai_i);
            ai_setup_data.m_empire_name.clear();                // leave blank, to be set by server in Universe::GenerateEmpires
            ai_setup_data.m_empire_color = GG::CLR_ZERO;        // to be set by server
            ai_setup_data.m_starting_species_name.clear();      // leave blank, to be set by server
            ai_setup_data.m_save_game_empire_id = ALL_EMPIRES;  // not used for new games
            ai_setup_data.m_client_type = Networking::CLIENT_TYPE_AI_PLAYER;

            setup_data.m_players.push_back(ai_setup_data);
        }

        m_networking.SendMessage(HostSPGameMessage(setup_data));
        m_fsm->process_event(HostSPGameRequested());
    } else {
        DebugLogger() << "HumanClientApp::NewSinglePlayerGame killing server due to canceled game or server connection failure";
        if (m_networking.Connected()) {
            DebugLogger() << "HumanClientApp::NewSinglePlayerGame Sending server shutdown message.";
            m_networking.SendMessage(ShutdownServerMessage(m_networking.PlayerID()));
            boost::this_thread::sleep(boost::posix_time::seconds(1));
            m_networking.DisconnectFromServer();
            if (!m_networking.Connected())
                DebugLogger() << "HumanClientApp::NewSinglePlayerGame Disconnected from server.";
            else
                ErrorLogger() << "HumanClientApp::NewSinglePlayerGame Unexpectedly still connected to server...?";
        }
        KillServer();
    }
}
示例#11
0
    int Variable<int>::Eval(const ScriptingContext& context) const
    {
        const adobe::name_t& property_name = m_property_name.back();

        IF_CURRENT_VALUE(int)

        if (m_ref_type == ValueRef::NON_OBJECT_REFERENCE) {
            if (property_name == CurrentTurn_name)
                return CurrentTurn();

            // add more non-object reference int functions here
            Logger().errorStream() << "Variable<int>::Eval unrecognized non-object property: " << ReconstructName(m_property_name, m_ref_type);
            return 0;
        }

        const UniverseObject* object = FollowReference(m_property_name.begin(), m_property_name.end(),
                                                       m_ref_type, context);
        if (!object) {
            Logger().errorStream() << "Variable<int>::Eval unable to follow reference: " << ReconstructName(m_property_name, m_ref_type);
            return 0;
        }

        if (property_name == Owner_name) {
            return object->Owner();
        } else if (property_name == ID_name) {
            return object->ID();
        } else if (property_name == CreationTurn_name) {
            return object->CreationTurn();
        } else if (property_name == Age_name) {
            return object->AgeInTurns();
        } else if (property_name == ProducedByEmpireID_name) {
            if (const Ship* ship = universe_object_cast<const Ship*>(object))
                return ship->ProducedByEmpireID();
            else if (const Building* building = universe_object_cast<const Building*>(object))
                return building->ProducedByEmpireID();
            else
                return ALL_EMPIRES;
        } else if (property_name == DesignID_name) {
            if (const Ship* ship = universe_object_cast<const Ship*>(object))
                return ship->DesignID();
            else
                return ShipDesign::INVALID_DESIGN_ID;
        } else if (property_name == Species_name) {
            if (const Planet* planet = universe_object_cast<const Planet*>(object))
                return GetSpeciesManager().GetSpeciesID(planet->SpeciesName());
            else if (const Ship* ship = universe_object_cast<const Ship*>(object))
                return GetSpeciesManager().GetSpeciesID(ship->SpeciesName());
            else
                return -1;
        } else if (property_name == FleetID_name) {
            if (const Ship* ship = universe_object_cast<const Ship*>(object))
                return ship->FleetID();
            else if (const Fleet* fleet = universe_object_cast<const Fleet*>(object))
                return fleet->ID();
            else
                return INVALID_OBJECT_ID;
        } else if (property_name == PlanetID_name) {
            if (const Building* building = universe_object_cast<const Building*>(object))
                return building->PlanetID();
            else if (const Planet* planet = universe_object_cast<const Planet*>(object))
                return planet->ID();
            else
                return INVALID_OBJECT_ID;
        } else if (property_name == SystemID_name) {
            return object->SystemID();
        } else if (property_name == FinalDestinationID_name) {
            if (const Fleet* fleet = universe_object_cast<const Fleet*>(object))
                return fleet->FinalDestinationID();
            else
                return INVALID_OBJECT_ID;
        } else if (property_name == NextSystemID_name) {
            if (const Fleet* fleet = universe_object_cast<const Fleet*>(object))
                return fleet->NextSystemID();
            else
                return INVALID_OBJECT_ID;
        } else if (property_name == PreviousSystemID_name) {
            if (const Fleet* fleet = universe_object_cast<const Fleet*>(object))
                return fleet->PreviousSystemID();
            else
                return INVALID_OBJECT_ID;
        } else if (property_name == NumShips_name) {
            if (const Fleet* fleet = universe_object_cast<const Fleet*>(object))
                return fleet->NumShips();
            else
                return 0;
        } else if (property_name == LastTurnBattleHere_name) {
            if (const System* system = universe_object_cast<const System*>(object))
                return system->LastTurnBattleHere();
            else
                return INVALID_GAME_TURN;
        } else if (property_name == Orbit_name) {
            if (const System* system = GetSystem(object->SystemID()))
                return system->OrbitOfObjectID(object->ID());
            return -1;
        }

        Logger().errorStream() << "Variable<int>::Eval unrecognized object property: " << ReconstructName(m_property_name, m_ref_type);
        return 0;
    }
示例#12
0
const Species* GetSpecies(const std::string& name)
{ return GetSpeciesManager().GetSpecies(name); }
示例#13
0
void MessageWndEdit::FindGameWords() {
     // add player and empire names
    for (EmpireManager::const_iterator it = Empires().begin(); it != Empires().end(); ++it) {
        m_gameWords.insert(it->second->Name());
        m_gameWords.insert(it->second->PlayerName());
    }
    // add system names
    std::vector<TemporaryPtr<System> > systems = GetUniverse().Objects().FindObjects<System>();
    for (unsigned int i = 0; i < systems.size(); ++i) {
        if (systems[i]->Name() != "")
            m_gameWords.insert(systems[i]->Name());
    }
     // add ship names
    std::vector<TemporaryPtr<Ship> > ships = GetUniverse().Objects().FindObjects<Ship>();
    for (unsigned int i = 0; i < ships.size(); ++i) {
        if (ships[i]->Name() != "")
            m_gameWords.insert(ships[i]->Name());
    }
     // add ship design names
    for (PredefinedShipDesignManager::iterator it = GetPredefinedShipDesignManager().begin();
         it != GetPredefinedShipDesignManager().end(); ++it)
    {
        if (it->second->Name() != "")
            m_gameWords.insert(UserString(it->second->Name()));
    }
     // add specials names
    std::vector<std::string> specials =  SpecialNames();
    for (unsigned int i = 0; i < specials.size(); ++i) {
        if (specials[i] != "")
            m_gameWords.insert(UserString(specials[i]));
    }
     // add species names
    for (SpeciesManager::iterator it = GetSpeciesManager().begin();
         it != GetSpeciesManager().end(); ++it)
    {
        if (it->second->Name() != "")
            m_gameWords.insert(UserString(it->second->Name()));
    }
     // add techs names
    std::vector<std::string> techs = GetTechManager().TechNames();
    for (unsigned int i = 0; i < techs.size(); ++i) {
        if (techs[i] != "")
            m_gameWords.insert(UserString(techs[i]));
    }
    // add building type names
    for (BuildingTypeManager::iterator it = GetBuildingTypeManager().begin();
         it != GetBuildingTypeManager().end(); ++it)
    {
        if (it->second->Name() != "")
            m_gameWords.insert(UserString(it->second->Name()));
    }
    // add ship hulls
    for (PredefinedShipDesignManager::iterator it = GetPredefinedShipDesignManager().begin();
         it != GetPredefinedShipDesignManager().end(); ++it)
    {
        if (it->second->Hull() != "")
            m_gameWords.insert(UserString(it->second->Hull()));
    }
    // add ship parts
    for (PredefinedShipDesignManager::iterator it = GetPredefinedShipDesignManager().begin();
         it != GetPredefinedShipDesignManager().end(); ++it)
    {
        const std::vector<std::string>& parts = it->second->Parts();
        for (std::vector<std::string>::const_iterator it1 = parts.begin(); it1 != parts.end(); ++it1) {
            if (*it1 != "")
                m_gameWords.insert(UserString(*it1));
        }
    }
 }
示例#14
0
void AIClientApp::HandleMessage(const Message& msg) {
    //DebugLogger() << "AIClientApp::HandleMessage " << msg.Type();
    switch (msg.Type()) {
    case Message::ERROR_MSG: {
        ErrorLogger() << "AIClientApp::HandleMessage : Received ERROR message from server: " << msg.Text();
        break;
    }

    case Message::HOST_ID: {
        const std::string& text = msg.Text();
        int host_id = Networking::INVALID_PLAYER_ID;
        if (text.empty()) {
            ErrorLogger() << "AIClientApp::HandleMessage for HOST_ID : Got empty message text?!";
        } else {
            try {
                host_id = boost::lexical_cast<int>(text);
            } catch(const boost::bad_lexical_cast& ex) {
                ErrorLogger() << "AIClientApp::HandleMessage for HOST_ID : Couldn't parse message text \"" << text << "\": " << ex.what();
            }
        }
        m_networking->SetHostPlayerID(host_id);
        break;
    }

    case Message::JOIN_GAME: {
        if (PlayerID() == Networking::INVALID_PLAYER_ID) {
            DebugLogger() << "AIClientApp::HandleMessage : Received JOIN_GAME acknowledgement";
            try {
                int player_id;
                boost::uuids::uuid cookie; // ignore
                ExtractJoinAckMessageData(msg, player_id, cookie);
                m_networking->SetPlayerID(player_id);
            } catch(const boost::bad_lexical_cast& ex) {
                ErrorLogger() << "AIClientApp::HandleMessage for JOIN_GAME : Couldn't parse message text \"" << msg.Text() << "\": " << ex.what();
            }
        } else {
            ErrorLogger() << "AIClientApp::HandleMessage : Received erroneous JOIN_GAME acknowledgement when already in a game";
        }
        break;
    }

    case Message::GAME_START: {
        DebugLogger() << "AIClientApp::HandleMessage : Received GAME_START message; starting AI turn...";
        bool single_player_game;        // ignored
        bool loaded_game_data;
        bool ui_data_available;         // ignored
        SaveGameUIData ui_data;         // ignored
        bool state_string_available;    // ignored, as save_state_string is sent even if not set by ExtractMessageData
        std::string save_state_string;
        m_empire_status.clear();

        ExtractGameStartMessageData(msg,                     single_player_game,     m_empire_id,
                                    m_current_turn,          m_empires,              m_universe,
                                    GetSpeciesManager(),     GetCombatLogManager(),  GetSupplyManager(),
                                    m_player_info,           m_orders,               loaded_game_data,
                                    ui_data_available,       ui_data,                state_string_available,
                                    save_state_string,       m_galaxy_setup_data);

        DebugLogger() << "Extracted GameStart message for turn: " << m_current_turn << " with empire: " << m_empire_id;

        GetUniverse().InitializeSystemGraph(m_empire_id);

        DebugLogger() << "Message::GAME_START loaded_game_data: " << loaded_game_data;
        if (loaded_game_data) {
            TraceLogger() << "Message::GAME_START save_state_string: " << save_state_string;
            m_AI->ResumeLoadedGame(save_state_string);
            Orders().ApplyOrders();
        } else {
            DebugLogger() << "Message::GAME_START Starting New Game!";
            // % Distribution of aggression levels
            // Aggression   :  0   1   2   3   4   5   (0=Beginner, 5=Maniacal)
            //                __  __  __  __  __  __
            //Max 0         :100   0   0   0   0   0
            //Max 1         : 25  75   0   0   0   0
            //Max 2         :  0  25  75   0   0   0
            //Max 3         :  0   0  25  75   0   0
            //Max 4         :  0   0   0  25  75   0
            //Max 5         :  0   0   0   0  25  75

            // Optional aggression table, possibly for 0.4.4+?
            // Aggression   :  0   1   2   3   4   5   (0=Beginner, 5=Maniacal)
            //                __  __  __  __  __  __
            //Max 0         :100   0   0   0   0   0
            //Max 1         : 25  75   0   0   0   0
            //Max 2         :  8  17  75   0   0   0
            //Max 3         :  0   8  17  75   0   0
            //Max 4         :  0   0   8  17  75   0
            //Max 5         :  0   0   0   8  17  75

            const std::string g_seed = GetGalaxySetupData().m_seed;
            const std::string emp_name = GetEmpire(m_empire_id)->Name();
            unsigned int my_seed = 0;

            try {
                // generate consistent my_seed values from galaxy seed & empire name.
                boost::hash<std::string> string_hash;
                std::size_t h = string_hash(g_seed);
                my_seed = 3 * static_cast<unsigned int>(h) * static_cast<unsigned int>(string_hash(emp_name));
                DebugLogger() << "Message::GAME_START getting " << emp_name << " AI aggression, RNG Seed: " << my_seed;
            } catch (...) {
                DebugLogger() << "Message::GAME_START getting " << emp_name << " AI aggression, could not initialise RNG.";
            }

            int rand_num = 0;
            int this_aggr = m_max_aggression;

            if (this_aggr > 0  && my_seed > 0) {
                Seed(my_seed);
                rand_num = RandSmallInt(0, 99);
                // if it's in the top 25% then decrease aggression.
                if (rand_num > 74) this_aggr--;
                // Leaving the following as commented out code for now. Possibly for 0.4.4+?
                // in the top 8% ? decrease aggression again, unless it's already as low as it gets.
                // if (rand_num > 91 && this_aggr > 0) this_aggr--;
            }

            DebugLogger() << "Message::GAME_START setting AI aggression as " << this_aggr << " (from rnd " << rand_num << "; max aggression " << m_max_aggression << ")";

            m_AI->SetAggression(this_aggr);
            m_AI->StartNewGame();
        }
        m_AI->GenerateOrders();
        break;
    }

    case Message::SAVE_GAME_COMPLETE:
        break;

    case Message::TURN_UPDATE: {
        //DebugLogger() << "AIClientApp::HandleMessage : extracting turn update message data";
        ExtractTurnUpdateMessageData(msg,                     m_empire_id,        m_current_turn,
                                     m_empires,               m_universe,         GetSpeciesManager(),
                                     GetCombatLogManager(),   GetSupplyManager(), m_player_info);
        //DebugLogger() << "AIClientApp::HandleMessage : generating orders";
        GetUniverse().InitializeSystemGraph(m_empire_id);
        m_AI->GenerateOrders();
        //DebugLogger() << "AIClientApp::HandleMessage : done handling turn update message";
        break;
    }

    case Message::TURN_PARTIAL_UPDATE:
        ExtractTurnPartialUpdateMessageData(msg, m_empire_id, m_universe);
        break;

    case Message::TURN_PROGRESS: {
        Message::TurnProgressPhase phase_id;
        ExtractTurnProgressMessageData(msg, phase_id);
        ClientApp::HandleTurnPhaseUpdate(phase_id);
        break;
    }

    case Message::PLAYER_STATUS:
        break;

    case Message::END_GAME: {
        DebugLogger() << "Message::END_GAME : Exiting";
        DebugLogger() << "Acknowledge server shutdown message.";
        Networking().SendMessage(AIEndGameAcknowledgeMessage());
        ExitApp(0);
        break;
    }

    case Message::PLAYER_CHAT: {
        std::string data;
        int player_id;
        boost::posix_time::ptime timestamp;
        ExtractServerPlayerChatMessageData(msg, player_id, timestamp, data);
        m_AI->HandleChatMessage(player_id, data);
        break;
    }

    case Message::DIPLOMACY: {
        DiplomaticMessage diplo_message;
        ExtractDiplomacyMessageData(msg, diplo_message);
        m_AI->HandleDiplomaticMessage(diplo_message);
        break;
    }

    case Message::DIPLOMATIC_STATUS: {
        DiplomaticStatusUpdateInfo diplo_update;
        ExtractDiplomaticStatusMessageData(msg, diplo_update);
        m_AI->HandleDiplomaticStatusUpdate(diplo_update);
        break;
    }

    case Message::LOGGER_CONFIG: {
         std::set<std::tuple<std::string, std::string, LogLevel>> options;
         ExtractLoggerConfigMessageData(msg, options);

         SetLoggerThresholds(options);
         break;
    }

    case Message::CHECKSUM: {
        TraceLogger() << "(AIClientApp) CheckSum.";
        VerifyCheckSum(msg);
        break;
    }

    default: {
        ErrorLogger() << "AIClientApp::HandleMessage : Received unknown Message type code " << msg.Type();
        break;
    }
    }
    //DebugLogger() << "AIClientApp::HandleMessage done";
}