27 #define LOG_MP LOG_STREAM(info, log_mp_connect_engine) 28 #define ERR_MP LOG_STREAM(err, log_mp_connect_engine) 35 : era_factions_(era_factions)
36 , side_num_(side[
"side"].to_int())
37 , faction_from_recruit_(side[
"faction_from_recruit"].to_bool())
38 , original_type_(get_default_faction(side)[
"type"].str())
39 , original_gender_(get_default_faction(side)[
"gender"].str())
41 , original_faction_(get_default_faction(side)[
"faction"].str())
42 , original_recruit_(
utils::
split(get_default_faction(side)[
"recruit"].str()))
43 , choose_faction_by_leader_(side[
"leader"].str())
44 , saved_game_(saved_game)
45 , has_no_recruits_(original_recruit_.empty() && side[
"previous_recruits"].empty())
46 , faction_lock_(side[
"faction_lock"].to_bool(lock_settings))
47 , leader_lock_(side[
"leader_lock"].to_bool(lock_settings))
48 , available_factions_()
49 , available_leaders_()
50 , available_genders_()
51 , choosable_factions_()
52 , choosable_leaders_()
53 , choosable_genders_()
54 , current_faction_(nullptr)
55 , current_leader_(
"null")
56 , current_gender_(
"null")
57 , default_leader_type_(side[
"type"])
58 , default_leader_gender_(side[
"gender"])
59 , default_leader_cfg_(nullptr)
61 const std::string& leader_id = side[
"id"];
62 if(!leader_id.empty()) {
74 if(side_unit[
"canrecruit"].to_bool()) {
92 faction_lock_ = faction_lock_ && (use_map_settings || lock_settings);
96 if(
current_leader_ == side_unit[
"type"] && side_unit[
"canrecruit"].to_bool()) {
121 if((*faction)[
"id"] ==
id) {
128 ERR_MP <<
"Faction '" <<
id <<
"' is not available for side " <<
side_num_ <<
" Ignoring";
159 std::vector<std::string> faction_choices, faction_excepts;
162 if(faction_choices.size() == 1 && faction_choices.front().empty()) {
163 faction_choices.clear();
167 if(faction_excepts.size() == 1 && faction_excepts.front().empty()) {
168 faction_excepts.clear();
172 std::vector<int> nonrandom_sides;
173 std::vector<int> fallback_nonrandom_sides;
177 if(faction[
"random_faction"].to_bool()) {
181 const std::string& faction_id = faction[
"id"];
183 if(!faction_choices.empty() && std::find(faction_choices.begin(), faction_choices.end(),
184 faction_id) == faction_choices.end()) {
188 if(!faction_excepts.empty() && std::find(faction_excepts.begin(), faction_excepts.end(),
189 faction_id) != faction_excepts.end()) {
194 fallback_nonrandom_sides.push_back(
i);
196 if(!avoid.empty() && std::find(avoid.begin(), avoid.end(),
197 faction_id) != avoid.end()) {
202 nonrandom_sides.push_back(
i);
205 if(nonrandom_sides.empty()) {
207 nonrandom_sides = fallback_nonrandom_sides;
210 if(nonrandom_sides.empty()) {
223 if(nonrandom_leaders.empty()) {
225 if(leader !=
"random") {
226 nonrandom_leaders.push_back(leader);
231 if(nonrandom_leaders.empty()) {
233 "Unable to find a leader type for faction $faction", {{
"faction", (*current_faction_)[
"name"].str()}}));
246 std::vector<std::string> nonrandom_genders;
248 if(gender !=
"random") {
249 nonrandom_genders.push_back(gender);
263 const config* custom_faction =
nullptr;
267 if((*faction)[
"id"] ==
"Custom" && !show_custom_faction) {
272 custom_faction = faction;
310 if((*
f)[
"id"] !=
"Random") {
319 std::set<std::string> seen;
321 [&seen](
const std::string&
s) {
return !seen.insert(
s).second; }
385 if(faction_index >= 0) {
418 if(default_gender.empty()) {
433 [&default_faction](
const config* faction) {
434 return (*faction)[
"id"] == default_faction;
446 std::vector<std::string> find;
447 std::string search_field;
456 search_field =
"recruit";
460 search_field =
"leader";
462 find.push_back(
"Custom");
466 int res = -1,
index = 0, best_score = 0;
468 int faction_score = 0;
469 for(
const std::string& search : find) {
470 for(
const std::string& r :
utils::split((*faction)[search_field])) {
478 if(faction_score > best_score) {
479 best_score = faction_score;
498 std::vector<std::string> leaders_to_append =
utils::split((*faction)[
"leader"]);
501 leaders_to_append.end());
530 ERR_MP <<
"Leader '" << leader <<
"' is not available for side " <<
side_num_ <<
" Ignoring";
540 ERR_MP <<
"Gender '" << gender <<
"' is not available for side " <<
side_num_ <<
" Ignoring";
548 if(
const config& df = cfg.
child(
"default_faction")) {
const config * default_leader_cfg_
int faction_index(const config &faction) const
std::string default_leader_type_
std::string savegame_gender_
int current_faction_index() const
config & child(config_key_type key, int n=0)
Returns the nth child with the given key, or a reference to an invalid config if there is none...
static const std::string s_male
Standard string id (not translatable) for MALE.
const unit_type * find(const std::string &key, unit_type::BUILD_STATUS status=unit_type::FULL) const
Finds a unit_type by its id() and makes sure it is built to the specified level.
static const config & get_default_faction(const config &cfg)
This class represents a single unit of a specific type.
config & find_child(config_key_type key, const std::string &name, const std::string &value)
Returns the first child of tag key with a name attribute containing value.
static l_noret error(LoadState *S, const char *why)
void resolve_random(randomness::mt_rng &rng, const std::vector< std::string > &avoid)
child_itors child_range(config_key_type key)
uint32_t get_next_random()
Get a new random number.
static lg::log_domain log_mp_connect_engine("mp/connect/engine")
int gender_index(const std::string &gender) const
returns -1 if no gender with that name was found
unit_type_data unit_types
void set_current_leader(const unsigned index)
void update_available_factions()
void set_current_gender(const unsigned index)
static std::string _(const char *str)
Definitions for the interface to Wesnoth Markup Language (WML).
const std::string original_faction_
A single unit type that the player may recruit.
std::string default_leader_gender_
static const std::string s_female
Standard string id (not translatable) for FEMALE.
void append_leaders_from_faction(const config *faction)
const std::string choose_faction_by_leader_
flg_manager(const std::vector< const config *> &era_factions, const config &side, bool lock_settings, bool use_map_settings, bool saved_game)
int leader_index(const std::string &leader) const
returns -1 if no leader with that name was found
std::vector< const config * > available_factions_
std::vector< const config * > choosable_factions_
const bool has_no_recruits_
std::string current_leader_
void set_current_faction(const unsigned index)
std::string current_gender_
int find_suitable_faction() const
std::vector< std::string > choosable_genders_
static map_location::DIRECTION s
std::size_t index(const std::string &str, const std::size_t index)
Codepoint index corresponding to the nth character in a UTF-8 string.
static int sort(lua_State *L)
const std::vector< const config * > & era_factions_
std::vector< std::string > split(const config_attribute_value &val)
void update_available_genders()
void update_choosable_genders()
Standard logging facilities (interface).
const std::vector< std::string > original_recruit_
void update_choosable_leaders()
std::vector< std::string > available_genders_
void update_available_leaders()
void select_default_faction()
A config object defines a single node in a WML file, with access to child nodes.
const bool faction_from_recruit_
std::vector< std::string > available_leaders_
void update_choosable_factions()
std::vector< std::string > choosable_leaders_
const config * current_faction_