Have teams pay for their recruits between the pre- and recruit events.
And similarly for recalls. Fetaure request / bug #16711
This commit is contained in:
parent
c47788c4d6
commit
a3a8d7c448
7 changed files with 23 additions and 25 deletions
|
@ -15,6 +15,8 @@ Version 1.11.0+svn:
|
|||
* WML engine:
|
||||
* The recall, recruit, prerecall, and prerecruit events will now block
|
||||
undoing unless they contain [allow_undo].
|
||||
* The cost of a recall/recruit is now paid between the prerecall/prerecruit
|
||||
and recall/recruit events. (FR #16711)
|
||||
* Miscellaneous and bug fixes:
|
||||
* Fix invalid memory access crash resulting from deleting all saved games
|
||||
in the Load Game dialog
|
||||
|
|
|
@ -696,7 +696,7 @@ static bool validate_recruit_iterator(unit_map::iterator & un_it,
|
|||
}
|
||||
|
||||
bool place_recruit(const unit &u, const map_location &recruit_location, const map_location& recruited_from,
|
||||
bool is_recall, bool show, bool fire_event, bool full_movement,
|
||||
int cost, bool is_recall, bool show, bool fire_event, bool full_movement,
|
||||
bool wml_triggered)
|
||||
{
|
||||
// Alias
|
||||
|
@ -736,6 +736,7 @@ bool place_recruit(const unit &u, const map_location &recruit_location, const ma
|
|||
new_unit_itor->set_hidden(true);
|
||||
}
|
||||
preferences::encountered_units().insert(new_unit_itor->type_id());
|
||||
(*resources::teams)[new_unit.side()-1].spend_gold(cost);
|
||||
|
||||
if ( show ) {
|
||||
// Find a leader to animate.
|
||||
|
|
|
@ -137,7 +137,7 @@ const std::vector<const unit*> get_recalls_for_location(int side, const map_loca
|
|||
* @returns true if an event has mutated the game state.
|
||||
*/
|
||||
bool place_recruit(const unit &u, const map_location &recruit_location, const map_location& recruited_from,
|
||||
bool is_recall, bool show = false, bool fire_event = true, bool full_movement = false,
|
||||
int cost, bool is_recall, bool show = false, bool fire_event = true, bool full_movement = false,
|
||||
bool wml_triggered = false);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -678,9 +678,8 @@ void recall_result::do_execute()
|
|||
|
||||
unit &un = *rec;
|
||||
recorder.add_recall(un.id(), recall_location_, recall_from_);
|
||||
place_recruit(un, recall_location_, recall_from_, true, true);
|
||||
place_recruit(un, recall_location_, recall_from_, my_team.recall_cost(), true, true);
|
||||
statistics::recall_unit(un);
|
||||
my_team.spend_gold(my_team.recall_cost());
|
||||
|
||||
my_team.recall_list().erase(rec);
|
||||
if (resources::screen!=NULL) {
|
||||
|
@ -885,9 +884,8 @@ void recruit_result::do_execute()
|
|||
const std::string recruit_err = find_recruit_location(get_side(), recruit_location_, recruit_from_, u->id());
|
||||
if(recruit_err.empty()) {
|
||||
const unit new_unit(u, get_side(), true);
|
||||
place_recruit(new_unit, recruit_location_, recruit_from_, false, preferences::show_ai_moves());
|
||||
place_recruit(new_unit, recruit_location_, recruit_from_, u->cost(), false, preferences::show_ai_moves());
|
||||
statistics::recruit_unit(new_unit);
|
||||
get_my_team().spend_gold(u->cost());
|
||||
// Confirm the transaction - i.e. don't undo recruitment
|
||||
replay_guard.confirm_transaction();
|
||||
set_gamestate_changed();
|
||||
|
|
|
@ -1937,7 +1937,7 @@ WML_HANDLER_FUNCTION(recall, /*event_info*/, cfg)
|
|||
if(resources::game_map->on_board(loc)) {
|
||||
DBG_NG << "...valid location for the recall found. Recalling.\n";
|
||||
avail.erase(u); // Erase before recruiting, since recruiting can fire more events
|
||||
place_recruit(to_recruit, loc, leader->get_location(), true,
|
||||
place_recruit(to_recruit, loc, leader->get_location(), 0, true,
|
||||
cfg["show"].to_bool(true), cfg["fire_event"].to_bool(false), true, true);
|
||||
return;
|
||||
}
|
||||
|
@ -1952,7 +1952,7 @@ WML_HANDLER_FUNCTION(recall, /*event_info*/, cfg)
|
|||
DBG_NG << "No usable leader found, but found usable location. Recalling.\n";
|
||||
avail.erase(u); // Erase before recruiting, since recruiting can fire more events
|
||||
map_location null_location = map_location::null_location;
|
||||
place_recruit(to_recruit, loc, null_location, true,
|
||||
place_recruit(to_recruit, loc, null_location, 0, true,
|
||||
cfg["show"].to_bool(true), cfg["fire_event"].to_bool(false), true, true);
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -856,8 +856,7 @@ bool menu_handler::do_recruit(const std::string &name, int side_num,
|
|||
//create a unit with traits
|
||||
recorder.add_recruit(recruit_num, loc, recruited_from);
|
||||
const unit new_unit(u_type, side_num, true);
|
||||
bool mutated = place_recruit(new_unit, loc, recruited_from, false, true);
|
||||
current_team.spend_gold(u_type->cost());
|
||||
bool mutated = place_recruit(new_unit, loc, recruited_from, u_type->cost(), false, true);
|
||||
statistics::recruit_unit(new_unit);
|
||||
|
||||
//MP_COUNTDOWN grant time bonus for recruiting
|
||||
|
@ -1077,9 +1076,8 @@ bool menu_handler::do_recall(const unit& un, int side_num, const map_location& r
|
|||
|
||||
recall_list_team.erase(it);
|
||||
recorder.add_recall(un.id(), recall_location, recall_from);
|
||||
bool mutated = place_recruit(un, recall_location, recall_from, true, true);
|
||||
bool mutated = place_recruit(un, recall_location, recall_from, current_team.recall_cost(), true, true);
|
||||
statistics::recall_unit(un);
|
||||
current_team.spend_gold(current_team.recall_cost());
|
||||
|
||||
bool shroud_cleared = clear_shroud(side_num);
|
||||
resources::undo_stack->push_back(undo_action(un, recall_location, recall_from, undo_action::RECALL));
|
||||
|
@ -1256,9 +1254,8 @@ void menu_handler::redo(int side_num)
|
|||
assert(unit_it != current_team.recall_list().end());
|
||||
current_team.recall_list().erase(unit_it);
|
||||
|
||||
place_recruit(un, loc, from, true, true);
|
||||
place_recruit(un, loc, from, current_team.recall_cost(), true, true);
|
||||
statistics::recall_unit(un);
|
||||
current_team.spend_gold(current_team.recall_cost());
|
||||
gui_->invalidate(loc);
|
||||
recorder.add_checksum_check(loc);
|
||||
} else {
|
||||
|
@ -1295,8 +1292,7 @@ void menu_handler::redo(int side_num)
|
|||
if(msg.empty()) {
|
||||
const unit new_unit = action.affected_unit;
|
||||
//unit new_unit(action.affected_unit.type(),team_num_,true);
|
||||
place_recruit(new_unit, loc, from, false, true);
|
||||
current_team.spend_gold(new_unit.type()->cost());
|
||||
place_recruit(new_unit, loc, from, new_unit.type()->cost(), false, true);
|
||||
statistics::recruit_unit(new_unit);
|
||||
gui_->invalidate(loc);
|
||||
|
||||
|
|
|
@ -987,28 +987,30 @@ bool do_replay_handle(int side_num, const std::string &do_untill)
|
|||
|
||||
const std::string res = find_recruit_location(side_num, loc, from, u_type->id());
|
||||
const unit new_unit(u_type, side_num, true);
|
||||
const int beginning_gold = current_team.gold();
|
||||
|
||||
if (res.empty()) {
|
||||
place_recruit(new_unit, loc, from, false, !get_replay_source().is_skipping());
|
||||
place_recruit(new_unit, loc, from, u_type->cost(), false, !get_replay_source().is_skipping());
|
||||
} else {
|
||||
std::stringstream errbuf;
|
||||
errbuf << "cannot recruit unit: " << res << "\n";
|
||||
replay::process_error(errbuf.str());
|
||||
// Keep the gold total right.
|
||||
current_team.spend_gold(u_type->cost());
|
||||
}
|
||||
|
||||
if (u_type->cost() > current_team.gold()) {
|
||||
if ( u_type->cost() > beginning_gold ) {
|
||||
std::stringstream errbuf;
|
||||
errbuf << "unit '" << u_type->id() << "' is too expensive to recruit: "
|
||||
<< u_type->cost() << "/" << current_team.gold() << "\n";
|
||||
<< u_type->cost() << "/" << beginning_gold << "\n";
|
||||
replay::process_error(errbuf.str());
|
||||
}
|
||||
LOG_REPLAY << "recruit: team=" << side_num << " '" << u_type->id() << "' at (" << loc
|
||||
<< ") cost=" << u_type->cost() << " from gold=" << current_team.gold() << ' ';
|
||||
|
||||
<< ") cost=" << u_type->cost() << " from gold=" << beginning_gold << ' '
|
||||
<< "-> " << current_team.gold() << "\n";
|
||||
|
||||
statistics::recruit_unit(new_unit);
|
||||
|
||||
current_team.spend_gold(u_type->cost());
|
||||
LOG_REPLAY << "-> " << (current_team.gold()) << "\n";
|
||||
fix_shroud = true;
|
||||
check_checksums(*cfg);
|
||||
}
|
||||
|
@ -1024,9 +1026,8 @@ bool do_replay_handle(int side_num, const std::string &do_untill)
|
|||
|
||||
if (recall_unit != current_team.recall_list().end()) {
|
||||
statistics::recall_unit(*recall_unit);
|
||||
place_recruit(*recall_unit, loc, from, true, !get_replay_source().is_skipping());
|
||||
place_recruit(*recall_unit, loc, from, current_team.recall_cost(), true, !get_replay_source().is_skipping());
|
||||
current_team.recall_list().erase(recall_unit);
|
||||
current_team.spend_gold(current_team.recall_cost());
|
||||
fix_shroud = true;
|
||||
} else {
|
||||
replay::process_error("illegal recall: unit_id '" + unit_id + "' could not be found within the recall list.\n");
|
||||
|
|
Loading…
Add table
Reference in a new issue