Exemplo n.º 1
0
/**
 * Undoes this action.
 * @return true on success; false on an error.
 */
bool recall_action::undo(int side)
{
    game_display & gui = *resources::screen;
    unit_map &   units = *resources::units;
    team &current_team = resources::gameboard->teams()[side-1];

    const map_location & recall_loc = route.front();
    unit_map::iterator un_it = units.find(recall_loc);
    if ( un_it == units.end() ) {
        return false;
    }

    unit_ptr un = un_it.get_shared_ptr();
    if (!un) {
        return false;
    }

    statistics::un_recall_unit(*un);
    int cost = statistics::un_recall_unit_cost(*un);
    if (cost < 0) {
        current_team.spend_gold(-current_team.recall_cost());
    }
    else {
        current_team.spend_gold(-cost);
    }

    current_team.recall_list().add(un);
    // invalidate before erasing allow us
    // to also do the overlapped hexes
    gui.invalidate(recall_loc);
    units.erase(recall_loc);
    this->return_village();
    execute_undo_umc_wml();
    return true;
}
Exemplo n.º 2
0
/**
 * Undoes this action.
 * @return true on success; false on an error.
 */
bool recruit_action::undo(int side)
{
	game_display & gui = *resources::screen;
	unit_map &   units = *resources::units;
	team &current_team = resources::gameboard->teams()[side-1];

	const map_location & recruit_loc = route.front();
	unit_map::iterator un_it = units.find(recruit_loc);
	if ( un_it == units.end() ) {
		return false;
	}

	const unit &un = *un_it;
	statistics::un_recruit_unit(un);
	current_team.spend_gold(-un.type().cost());

	//MP_COUNTDOWN take away recruit bonus
	current_team.set_action_bonus_count(current_team.action_bonus_count() - 1);

	// invalidate before erasing allow us
	// to also do the overlapped hexes
	gui.invalidate(recruit_loc);
	units.erase(recruit_loc);
	this->return_village();
	execute_undo_umc_wml();
	return true;
}
Exemplo n.º 3
0
/**
 * Undoes this action.
 * @return true on success; false on an error.
 */
bool dismiss_action::undo(int side)
{
	team &current_team = resources::gameboard->teams()[side-1];

	current_team.recall_list().add(dismissed_unit);
	execute_undo_umc_wml();
	return true;
}
Exemplo n.º 4
0
/**
 * Undoes this action.
 * @return true on success; false on an error.
 */
bool move_action::undo(int side)
{
	game_display & gui = *resources::screen;
	unit_map &   units = *resources::units;
	team &current_team = (*resources::teams)[side-1];

	// Copy some of our stored data.
	const int saved_moves = starting_moves;
	std::vector<map_location> rev_route = route;
	std::reverse(rev_route.begin(), rev_route.end());

	// Check units.
	unit_map::iterator u = units.find(rev_route.front());
	const unit_map::iterator u_end = units.find(rev_route.back());
	if ( u == units.end()  ||  u_end != units.end() ) {
		//this can actually happen if the scenario designer has abused the [allow_undo] command
		ERR_NG << "Illegal 'undo' found. Possible abuse of [allow_undo]?" << std::endl;
		return false;
	}

	if ( resources::gameboard->map().is_village(rev_route.front()) ) {
		get_village(rev_route.front(), original_village_owner + 1, NULL, false);
		//MP_COUNTDOWN take away capture bonus
		if ( countdown_time_bonus )
		{
			current_team.set_action_bonus_count(current_team.action_bonus_count() - 1);
		}
	}

	// Record the unit's current state so it can be redone.
	starting_moves = u->movement_left();
	goto_hex = u->get_goto();

	// Move the unit.
	unit_display::move_unit(rev_route, u.get_shared_ptr(), true, starting_dir);
	units.move(u->get_location(), rev_route.back());
	unit::clear_status_caches();

	// Restore the unit's old state.
	u = units.find(rev_route.back());
	u->set_goto(map_location());
	u->set_movement(saved_moves, true);
	u->anim_comp().set_standing();

	gui.invalidate_unit_after_move(rev_route.front(), rev_route.back());
	execute_undo_umc_wml();
	return true;
}
Exemplo n.º 5
0
/**
 * Undoes this action.
 * @return true on success; false on an error.
 */
bool recall_action::undo(int side)
{
	game_display & gui = *game_display::get_singleton();
	unit_map &   units = resources::gameboard->units();
	team &current_team = resources::gameboard->get_team(side);

	const map_location & recall_loc = route.front();
	unit_map::iterator un_it = units.find(recall_loc);
	if ( un_it == units.end() ) {
		return false;
	}

	unit_ptr un = un_it.get_shared_ptr();
	if (!un) {
		return false;
	}

	statistics::un_recall_unit(*un);
	int cost = statistics::un_recall_unit_cost(*un);
	if (cost < 0) {
		current_team.spend_gold(-current_team.recall_cost());
	}
	else {
		current_team.spend_gold(-cost);
	}

	current_team.recall_list().add(un);
	// Invalidate everything, not just recall_loc, in case the sprite
	// extends into adjacent hexes (Horseman) or even farther away (Fire
	// Dragon)
	gui.invalidate_all();
	units.erase(recall_loc);
	resources::whiteboard->on_kill_unit();
	un->anim_comp().clear_haloes();
	this->return_village();
	execute_undo_umc_wml();
	return true;
}