split off animation fcs from unit to unit_animation_component

This is a strict refactor, all we do is move the functions and
variables used just for animations to "unit_animation_component",
and include the necessary headers appropriate.

With a bit more work we can probably remove the graphics related
headers from unit.hpp
This commit is contained in:
Chris Beck 2014-06-17 02:18:46 -04:00
parent 4ff77b84c8
commit 504e4932b5
29 changed files with 458 additions and 334 deletions

View file

@ -986,6 +986,8 @@
<Unit filename="../../src/unit_abilities.hpp" />
<Unit filename="../../src/unit_animation.cpp" />
<Unit filename="../../src/unit_animation.hpp" />
<Unit filename="../../src/unit_animation_component.cpp" />
<Unit filename="../../src/unit_animation_component.hpp" />
<Unit filename="../../src/unit_display.cpp" />
<Unit filename="../../src/unit_display.hpp" />
<Unit filename="../../src/unit_formula_manager.cpp" />

View file

@ -1021,6 +1021,8 @@
<Unit filename="..\..\src\unit_abilities.hpp" />
<Unit filename="..\..\src\unit_animation.cpp" />
<Unit filename="..\..\src\unit_animation.hpp" />
<Unit filename="..\..\src\unit_animation_component.cpp" />
<Unit filename="..\..\src\unit_animation_component.hpp" />
<Unit filename="..\..\src\unit_display.cpp" />
<Unit filename="..\..\src\unit_display.hpp" />
<Unit filename="..\..\src\unit_formula_manager.cpp" />

View file

@ -21068,6 +21068,14 @@
RelativePath="..\..\src\unit_animation.hpp"
>
</File>
<File
RelativePath="..\..\src\unit_animation_component.cpp"
>
</File>
<File
RelativePath="..\..\src\unit_animation_component.hpp"
>
</File>
<File
RelativePath="..\..\src\unit_display.cpp"
>

View file

@ -890,6 +890,7 @@ set(wesnoth-main_SRC
unit.cpp
unit_abilities.cpp
unit_animation.cpp
unit_animation_component.cpp
unit_display.cpp
unit_formula_manager.cpp
unit_frame.cpp

View file

@ -523,6 +523,7 @@ wesnoth_sources = Split("""
unit.cpp
unit_abilities.cpp
unit_animation.cpp
unit_animation_component.cpp
unit_display.cpp
unit_formula_manager.cpp
unit_frame.cpp

View file

@ -44,6 +44,7 @@
#include "../tod_manager.hpp"
#include "../unit.hpp"
#include "../unit_abilities.hpp"
#include "../unit_animation_component.hpp"
#include "../unit_display.hpp"
#include "../unit_helper.hpp"
#include "../unit_map.hpp"
@ -1326,13 +1327,13 @@ namespace {
if (a_.valid()) {
unit &u = a_.get_unit();
u.set_standing();
u.anim_comp().set_standing();
u.set_experience(u.experience() + a_.xp_);
}
if (d_.valid()) {
unit &u = d_.get_unit();
u.set_standing();
u.anim_comp().set_standing();
u.set_experience(u.experience() + d_.xp_);
}

View file

@ -42,6 +42,7 @@
#include "../formula_string_utils.hpp"
#include "../team.hpp"
#include "../unit.hpp"
#include "../unit_animation_component.hpp"
#include "../whiteboard/manager.hpp"
#include <boost/foreach.hpp>
@ -494,7 +495,7 @@ namespace { // Private helpers for move_unit()
moves_left_.pop_front();
// Invalidate before moving so we invalidate neighbor hexes if needed.
move_it_->invalidate(disp);
move_it_->anim_comp().invalidate(disp);
// Attempt actually moving.
// (Fails if *step_to is occupied).
@ -505,7 +506,7 @@ namespace { // Private helpers for move_unit()
// Update the moving unit.
move_it_ = move_result.first;
move_it_->set_facing(step_from->get_relative_dir(*step_to));
move_it_->set_standing(false);
move_it_->anim_comp().set_standing(false);
disp.invalidate_unit_after_move(*move_loc_, *step_to);
disp.invalidate(*step_to);
move_loc_ = step_to;

View file

@ -30,6 +30,7 @@
#include "../resources.hpp"
#include "../team.hpp"
#include "../unit.hpp"
#include "../unit_animation_component.hpp"
#include "../unit_display.hpp"
#include "../unit_map.hpp"
#include "../whiteboard/manager.hpp"
@ -746,7 +747,7 @@ bool undo_list::move_action::undo(int side, undo_list & /*undos*/)
u = units.find(rev_route.back());
u->set_goto(map_location());
u->set_movement(saved_moves, true);
u->set_standing();
u->anim_comp().set_standing();
gui.invalidate_unit_after_move(rev_route.front(), rev_route.back());
return true;
@ -964,7 +965,7 @@ bool undo_list::move_action::redo(int side)
// Set the unit's state.
u->set_goto(goto_hex);
u->set_movement(saved_moves, true);
u->set_standing();
u->anim_comp().set_standing();
if ( resources::gameboard->map().is_village(route.back()) ) {
get_village(route.back(), u->side());

View file

@ -17,6 +17,7 @@
* Routines to set up the display, scroll and zoom the map.
*/
#include "arrow.hpp"
#include "cursor.hpp"
#include "drawable_unit.hpp"
#include "display.hpp"
@ -30,19 +31,20 @@
#include "map.hpp"
#include "map_label.hpp"
#include "minimap.hpp"
#include "overlay.hpp"
#include "play_controller.hpp" //note: this can probably be refactored out
#include "reports.hpp"
#include "resources.hpp"
#include "synced_context.hpp"
#include "team.hpp"
#include "terrain_builder.hpp"
#include "text.hpp"
#include "time_of_day.hpp"
#include "tooltips.hpp"
#include "arrow.hpp"
#include "tod_manager.hpp"
#include "resources.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "whiteboard/manager.hpp"
#include "overlay.hpp"
#include "synced_context.hpp"
#include "SDL_image.h"
@ -3056,10 +3058,10 @@ void display::invalidate_animations()
}
const std::deque<unit*> & unit_list = fake_unit_man_->get_fake_unit_list_for_invalidation();
BOOST_FOREACH(const unit* u, unit_list) {
u->refresh();
u->anim_comp().refresh();
}
BOOST_FOREACH(const unit & u, dc_->units()) {
u.refresh();
u.anim_comp().refresh();
}
bool new_inval;
do {
@ -3068,10 +3070,10 @@ void display::invalidate_animations()
#pragma omp parallel for reduction(|:new_inval) shared(unit_list) schedule(guided)
#endif //_OPENMP
BOOST_FOREACH(const unit* u, unit_list) {
new_inval |= u->invalidate(*this);
new_inval |= u->anim_comp().invalidate(*this);
}
BOOST_FOREACH(const unit & u, dc_->units()) {
new_inval |= u.invalidate(*this);
new_inval |= u.anim_comp().invalidate(*this);
}
}while(new_inval);
}

View file

@ -21,6 +21,7 @@
#include "map.hpp"
#include "team.hpp"
#include "unit_animation.hpp"
#include "unit_animation_component.hpp"
#include "unit_frame.hpp"
#include <boost/foreach.hpp>
@ -33,24 +34,26 @@ void drawable_unit::redraw_unit (display & disp) const
const team & viewing_team = teams[disp.viewing_team()];
unit_animation_component & ac = *anim_comp_;
if ( hidden_ || disp.is_blindfolded() || !is_visible_to_team(viewing_team,map, disp.show_everything()) )
{
clear_haloes();
if(anim_) {
anim_->update_last_draw_time();
ac.clear_haloes();
if(ac.anim_) {
ac.anim_->update_last_draw_time();
}
return;
}
if (!anim_) {
set_standing();
if (!anim_) return;
if (!ac.anim_) {
ac.set_standing();
if (!ac.anim_) return;
}
if (refreshing_) return;
refreshing_ = true;
if (ac.refreshing_) return;
ac.refreshing_ = true;
anim_->update_last_draw_time();
ac.anim_->update_last_draw_time();
frame_parameters params;
const t_translation::t_terrain terrain = map.get_terrain(loc_);
const terrain_type& terrain_info = map.get_terrain_info(terrain);
@ -106,7 +109,7 @@ void drawable_unit::redraw_unit (display & disp) const
params.primary_frame = t_true;
const frame_parameters adjusted_params = anim_->get_current_params(params);
const frame_parameters adjusted_params = ac.anim_->get_current_params(params);
const map_location dst = loc_.get_direction(facing_);
const int xsrc = disp.get_location_x(loc_);
@ -118,20 +121,20 @@ void drawable_unit::redraw_unit (display & disp) const
const int x = static_cast<int>(adjusted_params.offset * xdst + (1.0-adjusted_params.offset) * xsrc) + d2;
const int y = static_cast<int>(adjusted_params.offset * ydst + (1.0-adjusted_params.offset) * ysrc) + d2;
if(unit_halo_ == halo::NO_HALO && !image_halo().empty()) {
unit_halo_ = halo::add(0, 0, image_halo()+TC_image_mods(), map_location(-1, -1));
if(ac.unit_halo_ == halo::NO_HALO && !image_halo().empty()) {
ac.unit_halo_ = halo::add(0, 0, image_halo()+TC_image_mods(), map_location(-1, -1));
}
if(unit_halo_ != halo::NO_HALO && image_halo().empty()) {
halo::remove(unit_halo_);
unit_halo_ = halo::NO_HALO;
} else if(unit_halo_ != halo::NO_HALO) {
halo::set_location(unit_halo_, x, y - height_adjust);
if(ac.unit_halo_ != halo::NO_HALO && image_halo().empty()) {
halo::remove(ac.unit_halo_);
ac.unit_halo_ = halo::NO_HALO;
} else if(ac.unit_halo_ != halo::NO_HALO) {
halo::set_location(ac.unit_halo_, x, y - height_adjust);
}
// We draw bars only if wanted, visible on the map view
bool draw_bars = draw_bars_ ;
bool draw_bars = ac.draw_bars_ ;
if (draw_bars) {
const int d = disp.hex_size();
SDL_Rect unit_rect = sdl::create_rect(xsrc, ysrc +adjusted_params.y, d, d);
@ -291,7 +294,7 @@ void drawable_unit::redraw_unit (display & disp) const
params.y -= height_adjust_unit - height_adjust;
params.halo_y -= height_adjust_unit - height_adjust;
anim_->redraw(params);
refreshing_ = false;
ac.anim_->redraw(params);
ac.refreshing_ = false;
}

View file

@ -101,7 +101,7 @@ void editor_action_item_replace::perform_without_undo(map_context& /*mc*/) const
//
// item& u = *items.find(new_loc_);
// //TODO do we still need set_standing?
// u.set_standing();
// u.anim_comp().set_standing();
//
// mc.add_changed_location(loc_);
// mc.add_changed_location(new_loc_);

View file

@ -24,6 +24,9 @@
#include "editor/map/map_context.hpp"
#include "../../unit.hpp"
#include "../../unit_animation_component.hpp"
#include <boost/scoped_ptr.hpp>
namespace editor {
@ -99,7 +102,7 @@ void editor_action_unit_replace::perform_without_undo(map_context& mc) const
unit& u = *units.find(new_loc_);
//TODO do we still need set_standing?
u.set_standing();
u.anim_comp().set_standing();
mc.add_changed_location(loc_);
mc.add_changed_location(new_loc_);
@ -135,7 +138,7 @@ void editor_action_unit_facing::perform_without_undo(map_context& mc) const
if (unit_it != units.end()) {
unit_it->set_facing(new_direction_);
unit_it->set_standing();
unit_it->anim_comp().set_standing();
}
}

View file

@ -42,9 +42,11 @@
#include "../clipboard.hpp"
#include "../game_preferences.hpp"
#include "../gettext.hpp"
#include "../leader_scroll_dialog.hpp"
#include "../preferences_display.hpp"
#include "../sound.hpp"
#include "../leader_scroll_dialog.hpp"
#include "../unit.hpp"
#include "../unit_animation_component.hpp"
#include "halo.hpp"
@ -655,7 +657,7 @@ bool editor_controller::execute_command(const hotkey::hotkey_command& cmd, int i
resources::units->find(gui_->mouseover_hex());
assert(un != resources::units->end());
un->set_facing(map_location::DIRECTION(index));
un->set_standing();
un->anim_comp().set_standing();
return true;
}
}
@ -766,7 +768,7 @@ bool editor_controller::execute_command(const hotkey::hotkey_command& cmd, int i
const unit_map::unit_iterator un = context_manager_->get_map_context().get_units().find(loc);
bool canrecruit = un->can_recruit();
un->set_can_recurit(!canrecruit);
un->set_standing();
un->anim_comp().set_standing();
}
return true;
case HOTKEY_DELETE_UNIT:

View file

@ -18,6 +18,7 @@
#include "fake_unit.hpp"
#include "log.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
static lg::log_domain log_engine("engine");
#define ERR_NG LOG_STREAM(err, log_engine)
@ -43,7 +44,7 @@ int fake_unit_manager::remove_temporary_unit(unit *u)
fake_units_.erase(it, fake_units_.end());
my_display_.invalidate(u->get_location());
// Redraw with no location to get rid of haloes
u->clear_haloes();
u->anim_comp().clear_haloes();
}
if (removed > 1) {
ERR_NG << "Error: duplicate temp unit found in fake_unit_manager::remove_temporary_unit" << std::endl;

View file

@ -58,6 +58,8 @@
#include "../soundsource.hpp"
#include "../synced_context.hpp"
#include "../terrain_filter.hpp"
#include "../unit.hpp"
#include "../unit_animation_component.hpp"
#include "../unit_display.hpp"
#include "../unit_helper.hpp"
#include "../wml_exception.hpp"
@ -857,7 +859,7 @@ WML_HANDLER_FUNCTION(heal_unit, event_info, cfg)
u->set_state(unit::STATE_SLOWED, false);
u->set_state(unit::STATE_PETRIFIED, false);
u->set_state(unit::STATE_UNHEALABLE, false);
u->set_standing();
u->anim_comp().set_standing();
}
if (heal_amount_to_set)
@ -948,7 +950,7 @@ WML_HANDLER_FUNCTION(kill, event_info, cfg)
resources::screen->invalidate(loc);
unit_map::iterator iun = resources::units->find(loc);
if ( iun != resources::units->end() && iun.valid() )
iun->invalidate(*resources::screen);
iun->anim_comp().invalidate(*resources::screen);
}
resources::screen->redraw_minimap();
@ -1422,7 +1424,7 @@ WML_HANDLER_FUNCTION(move_units_fake, /*event_info*/, cfg)
path_step[1] = paths[un][step];
unit_display::move_unit(path_step, *units[un]);
units[un]->set_location(path_step[1]);
units[un]->set_standing();
units[un]->anim_comp().set_standing();
}
}
@ -2359,7 +2361,7 @@ WML_HANDLER_FUNCTION(teleport, event_info, cfg)
unit::clear_status_caches();
u = resources::units->find(vacant_dst);
u->set_standing();
u->anim_comp().set_standing();
if ( clear_shroud ) {
// Now that the unit is visibly in position, clear the shroud.

View file

@ -40,6 +40,8 @@
#include "replay_helper.hpp"
#include "resources.hpp"
#include "synced_context.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "wml_separators.hpp"
#include "whiteboard/manager.hpp"
@ -725,7 +727,7 @@ void mouse_handler::select_hex(const map_location& hex, const bool browse, const
if (!(browse || resources::whiteboard->unit_has_actions(&*u)))
{
sound::play_UI_sound("select-unit.wav");
u->set_selecting();
u->anim_comp().set_selecting();
if(fire_event) {
// ensure unit map is back to normal while event is fired
wb::real_map srum;

View file

@ -65,6 +65,7 @@
#include "sound.hpp"
#include "synced_context.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "ai/lua/core.hpp"
#include "version.hpp"
#include "gui/widgets/clickable.hpp"
@ -2193,7 +2194,7 @@ static int intf_put_unit(lua_State *L)
if (lu) {
lu->put_map(loc);
lu->get()->set_standing();
lu->get()->anim_comp().set_standing();
} else {
u->set_location(loc);
resources::units->insert(u);
@ -2268,7 +2269,7 @@ static int intf_extract_unit(lua_State *L)
if (lu->on_map()) {
u = resources::units->extract(u->get_location());
assert(u);
u->clear_haloes();
u->anim_comp().clear_haloes();
} else if (int side = lu->on_recall_list()) {
team &t = (*resources::teams)[side - 1];
UnitPtr v = UnitPtr(new unit(*u));

View file

@ -32,6 +32,7 @@
#include "resources.hpp"
#include "unit_id.hpp"
#include "unit_abilities.hpp"
#include "unit_animation_component.hpp"
#include "unit_formula_manager.hpp"
#include "scripting/lua.hpp"
#include "side_filter.hpp"
@ -184,7 +185,6 @@ unit::unit(const unit& o):
events_(o.events_),
filter_recall_(o.filter_recall_),
emit_zoc_(o.emit_zoc_),
state_(o.state_),
overlays_(o.overlays_),
@ -202,17 +202,12 @@ unit::unit(const unit& o):
modification_descriptions_(o.modification_descriptions_),
anim_comp_(new unit_animation_component(*this, *o.anim_comp_)),
animations_(o.animations_),
anim_(NULL),
next_idling_(0),
frame_begin_time_(o.frame_begin_time_),
unit_halo_(halo::NO_HALO),
getsHit_(o.getsHit_),
refreshing_(o.refreshing_),
hidden_(o.hidden_),
draw_bars_(o.draw_bars_),
hp_bar_scaling_(o.hp_bar_scaling_),
xp_bar_scaling_(o.xp_bar_scaling_),
@ -265,7 +260,6 @@ unit::unit(const config &cfg, bool use_traits, const vconfig* vcfg) :
events_(),
filter_recall_(),
emit_zoc_(0),
state_(STATE_STANDING),
overlays_(),
role_(cfg["role"]),
attacks_(),
@ -278,15 +272,10 @@ unit::unit(const config &cfg, bool use_traits, const vconfig* vcfg) :
is_fearless_(false),
is_healthy_(false),
modification_descriptions_(),
anim_comp_(new unit_animation_component(*this)),
animations_(),
anim_(NULL),
next_idling_(0),
frame_begin_time_(0),
unit_halo_(halo::NO_HALO),
getsHit_(0),
refreshing_(false),
hidden_(false),
draw_bars_(false),
hp_bar_scaling_(cfg["hp_bar_scaling"].blank() ? type_->hp_bar_scaling() : cfg["hp_bar_scaling"]),
xp_bar_scaling_(cfg["xp_bar_scaling"].blank() ? type_->xp_bar_scaling() : cfg["xp_bar_scaling"]),
modifications_(),
@ -370,7 +359,7 @@ unit::unit(const config &cfg, bool use_traits, const vconfig* vcfg) :
unit_value_ = *v;
}
if (const config::attribute_value *v = cfg.get("halo")) {
clear_haloes();
anim_comp_->clear_haloes();
cfg_["halo"] = *v;
}
if (const config::attribute_value *v = cfg.get("profile")) {
@ -570,7 +559,6 @@ unit::unit(const unit_type &u_type, int side, bool real_unit,
events_(),
filter_recall_(),
emit_zoc_(0),
state_(STATE_STANDING),
overlays_(),
role_(),
attacks_(),
@ -583,15 +571,10 @@ unit::unit(const unit_type &u_type, int side, bool real_unit,
is_fearless_(false),
is_healthy_(false),
modification_descriptions_(),
anim_comp_(new unit_animation_component(*this)),
animations_(),
anim_(NULL),
next_idling_(0),
frame_begin_time_(0),
unit_halo_(halo::NO_HALO),
getsHit_(0),
refreshing_(false),
hidden_(false),
draw_bars_(false),
modifications_(),
invisibility_cache_()
{
@ -614,7 +597,7 @@ unit::unit(const unit_type &u_type, int side, bool real_unit,
unit::~unit()
{
try {
clear_haloes();
anim_comp_->clear_haloes();
// Remove us from the status cache
std::vector<const unit *>::iterator itor =
@ -623,6 +606,8 @@ unit::~unit()
if(itor != units_with_cache.end()) {
units_with_cache.erase(itor);
}
} catch (std::exception & e) {
ERR_UT << "Caught exception when destroying unit: " << e.what() << std::endl;
} catch (...) {}
}
@ -864,8 +849,7 @@ void unit::advance_to(const config &old_cfg, const unit_type &u_type,
game_events::add_events(cfg_.child_range("event"), new_type.id());
cfg_.clear_children("event");
refreshing_ = false;
anim_.reset();
anim_comp_->reset_after_advance();
}
std::string unit::big_profile() const
@ -1069,7 +1053,7 @@ void unit::expire_modifications(const std::string & duration)
}
if ( rebuild_from != NULL ) {
clear_haloes();
anim_comp_->clear_haloes();
advance_to(*rebuild_from);
}
}
@ -1759,80 +1743,6 @@ const surface unit::still_image(bool scaled) const
return unit_image;
}
void unit::set_standing(bool with_bars) const
{
display *disp = display::get_singleton();
if (preferences::show_standing_animations()&& !incapacitated()) {
start_animation(INT_MAX, choose_animation(*disp, loc_, "standing"),
with_bars, "", 0, STATE_STANDING);
} else {
start_animation(INT_MAX, choose_animation(*disp, loc_, "_disabled_"),
with_bars, "", 0, STATE_STANDING);
}
}
void unit::set_ghosted(bool with_bars) const
{
display *disp = display::get_singleton();
start_animation(INT_MAX, choose_animation(*disp, loc_, "ghosted"),
with_bars);
}
void unit::set_disabled_ghosted(bool with_bars) const
{
display *disp = display::get_singleton();
start_animation(INT_MAX, choose_animation(*disp, loc_, "disabled_ghosted"),
with_bars);
}
void unit::set_idling() const
{
display *disp = display::get_singleton();
start_animation(INT_MAX, choose_animation(*disp, loc_, "idling"),
true, "", 0, STATE_FORGET);
}
void unit::set_selecting() const
{
const display *disp = display::get_singleton();
if (preferences::show_standing_animations() && !get_state(STATE_PETRIFIED)) {
start_animation(INT_MAX, choose_animation(*disp, loc_, "selected"),
true, "", 0, STATE_FORGET);
} else {
start_animation(INT_MAX, choose_animation(*disp, loc_, "_disabled_selected_"),
true, "", 0, STATE_FORGET);
}
}
void unit::start_animation (int start_time, const unit_animation *animation,
bool with_bars, const std::string &text, Uint32 text_color, STATE state) const
{
const display * disp = display::get_singleton();
if (!animation) {
if (state == STATE_STANDING)
state_ = state;
if (!anim_ && state_ != STATE_STANDING)
set_standing(with_bars);
return ;
}
state_ = state;
// everything except standing select and idle
bool accelerate = (state != STATE_FORGET && state != STATE_STANDING);
draw_bars_ = with_bars;
anim_.reset(new unit_animation(*animation));
const int real_start_time = start_time == INT_MAX ? anim_->get_begin_time() : start_time;
anim_->start_animation(real_start_time, loc_, loc_.get_direction(facing_),
text, text_color, accelerate);
frame_begin_time_ = anim_->get_begin_time() -1;
if (disp->idle_anim()) {
next_idling_ = get_current_animation_tick()
+ static_cast<int>((20000 + rand() % 20000) * disp->idle_anim_rate());
} else {
next_idling_ = INT_MAX;
}
}
void unit::set_facing(map_location::DIRECTION dir) const {
if(dir != map_location::NDIRECTIONS) {
facing_ = dir;
@ -1840,42 +1750,6 @@ void unit::set_facing(map_location::DIRECTION dir) const {
// Else look at yourself (not available so continue to face the same direction)
}
void unit::clear_haloes () const
{
if(unit_halo_ != halo::NO_HALO) {
halo::remove(unit_halo_);
unit_halo_ = halo::NO_HALO;
}
if(anim_ ) anim_->clear_haloes();
}
bool unit::invalidate (const display & disp) const
{
bool result = false;
// Very early calls, anim not initialized yet
if(get_animation()) {
frame_parameters params;
const gamemap & map = disp.get_map();
const t_translation::t_terrain terrain = map.get_terrain(get_location());
const terrain_type& terrain_info = map.get_terrain_info(terrain);
int height_adjust = static_cast<int>(terrain_info.unit_height_adjust() * disp.get_zoom_factor());
if (is_flying() && height_adjust < 0) {
height_adjust = 0;
}
params.y -= height_adjust;
params.halo_y -= height_adjust;
params.image_mod = image_mods();
params.halo_mod = TC_image_mods();
params.image= absolute_image();
result |= get_animation()->invalidate(params);
}
return result;
}
int unit::upkeep() const
{
// Leaders do not incur upkeep.
@ -2333,7 +2207,7 @@ void unit::add_modification(const std::string& mod_type, const config& mod, bool
cfg_["ellipse"] = effect["ellipse"];
} else if (apply_to == "halo") {
clear_haloes();
anim_comp_->clear_haloes();
cfg_["halo"] = effect["halo"];
} else if (apply_to == "overlay") {
@ -2478,31 +2352,6 @@ std::string unit::absolute_image() const {
return cfg_["image_icon"].empty() ? cfg_["image"] : cfg_["image_icon"];
}
const unit_animation* unit::choose_animation(const display& disp, const map_location& loc,const std::string& event,
const map_location& second_loc,const int value,const unit_animation::hit_type hit,
const attack_type* attack, const attack_type* second_attack, int swing_num) const
{
// Select one of the matching animations at random
std::vector<const unit_animation*> options;
int max_val = unit_animation::MATCH_FAIL;
for(std::vector<unit_animation>::const_iterator i = animations_.begin(); i != animations_.end(); ++i) {
int matching = i->matches(disp,loc,second_loc,this,event,value,hit,attack,second_attack,swing_num);
if(matching > unit_animation::MATCH_FAIL && matching == max_val) {
options.push_back(&*i);
} else if(matching > max_val) {
max_val = matching;
options.clear();
options.push_back(&*i);
}
}
if(max_val == unit_animation::MATCH_FAIL) {
return NULL;
}
return options[rand()%options.size()];
}
void unit::apply_modifications()
{
log_scope("apply mods");
@ -2720,33 +2569,6 @@ int side_upkeep(int side)
return res;
}
void unit::refresh() const
{
if (state_ == STATE_FORGET && anim_ && anim_->animation_finished_potential())
{
set_standing();
return;
}
display &disp = *display::get_singleton();
if (state_ != STATE_STANDING || get_current_animation_tick() < next_idling_ ||
!disp.tile_nearly_on_screen(loc_) || incapacitated())
{
return;
}
if (get_current_animation_tick() > next_idling_ + 1000)
{
// prevent all units animating at the same time
if (disp.idle_anim()) {
next_idling_ = get_current_animation_tick()
+ static_cast<int>((20000 + rand() % 20000) * disp.idle_anim_rate());
} else {
next_idling_ = INT_MAX;
}
} else {
set_idling();
}
}
team_data calculate_team_data(const team& tm, int side)
{
team_data res;
@ -2802,7 +2624,7 @@ void unit::set_hidden(bool state) const {
hidden_ = state;
if(!state) return;
// We need to get rid of haloes immediately to avoid display glitches
clear_haloes();
anim_comp_->clear_haloes();
}
// Filters unimportant stats from the unit config and returns a checksum of

View file

@ -28,6 +28,7 @@
class display;
class gamemap;
class team;
class unit_animation_component;
class unit_formula_manager;
class vconfig;
@ -204,7 +205,6 @@ public:
void end_turn();
void new_scenario();
/** Called on every draw */
void refresh() const;
bool take_hit(int damage) { hit_points_ -= damage; return hit_points_ <= 0; }
void heal(int amount);
@ -248,21 +248,10 @@ public:
/** A SDL surface, ready for display for place where we need a still-image of the unit. */
const surface still_image(bool scaled = false) const;
/** Clear unit_halo_ */
void clear_haloes() const;
void set_standing(bool with_bars = true) const;
void set_ghosted(bool with_bars = true) const;
void set_disabled_ghosted(bool with_bars = true) const;
void set_idling() const;
void set_selecting() const;
unit_animation* get_animation() const { return anim_.get();}
unit_animation_component & anim_comp() const { return *anim_comp_; }
void set_facing(map_location::DIRECTION dir) const;
map_location::DIRECTION facing() const { return facing_; }
bool invalidate(const display & disp) const;
const std::vector<t_string>& trait_names() const { return trait_names_; }
const std::vector<t_string>& trait_descriptions() const { return trait_descriptions_; }
std::vector<std::string> get_traits_list() const;
@ -319,15 +308,6 @@ public:
const map_location& get_interrupted_move() const { return interrupted_move_; }
void set_interrupted_move(const map_location& interrupted_move) { interrupted_move_ = interrupted_move; }
/** States for animation. */
enum STATE {
STATE_STANDING, /** anim must fit in a hex */
STATE_FORGET, /** animation will be automatically replaced by a standing anim when finished */
STATE_ANIM}; /** normal anims */
void start_animation (int start_time, const unit_animation *animation,
bool with_bars, const std::string &text = "",
Uint32 text_color = 0, STATE state = STATE_ANIM) const;
/** The name of the file to game_display (used in menus). */
std::string absolute_image() const;
std::string image_halo() const { return cfg_["halo"]; }
@ -342,13 +322,6 @@ public:
/// Never returns NULL, but may point to the null race.
const unit_race* race() const { return race_; }
const unit_animation* choose_animation(const display& disp,
const map_location& loc, const std::string& event,
const map_location& second_loc = map_location::null_location(),
const int damage=0,
const unit_animation::hit_type hit_type = unit_animation::INVALID,
const attack_type* attack=NULL,const attack_type* second_attack = NULL,
int swing_num =0) const;
/**
* Returns true if the unit is currently under effect by an ability with this given TAG NAME.
@ -477,7 +450,6 @@ private:
protected:
bool emit_zoc_;
mutable STATE state_; //animation state
private:
std::vector<std::string> overlays_;
@ -497,19 +469,14 @@ private:
utils::string_map modification_descriptions_;
// Animations:
friend class unit_animation_component;
protected:
boost::scoped_ptr<unit_animation_component> anim_comp_;
std::vector<unit_animation> animations_;
mutable boost::scoped_ptr<unit_animation> anim_;
mutable int next_idling_; // used for animation
mutable int frame_begin_time_; // used for animation
mutable int unit_halo_; // flag used for drawing / animation
bool getsHit_;
mutable bool refreshing_; // avoid infinite recursion. flag used for drawing / animation
mutable bool hidden_;
mutable bool draw_bars_; // flag used for drawing / animation
double hp_bar_scaling_, xp_bar_scaling_;
private:

View file

@ -19,10 +19,11 @@
#include "game_display.hpp"
#include "halo.hpp"
#include "map.hpp"
#include "unit.hpp"
#include "variable.hpp"
#include "resources.hpp"
#include "play_controller.hpp"
#include "resources.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "variable.hpp"
#include <boost/foreach.hpp>
@ -1283,7 +1284,7 @@ void unit_animator::add_animation(const unit* animated_unit
tmp.text_color = text_color;
tmp.src = src;
tmp.with_bars= with_bars;
tmp.animation = animated_unit->choose_animation(*disp,src,event,dst,value,hit_type,attack,second_attack,value2);
tmp.animation = animated_unit->anim_comp().choose_animation(*disp,src,event,dst,value,hit_type,attack,second_attack,value2);
if(!tmp.animation) return;
start_time_ = std::max<int>(start_time_,tmp.animation->get_begin_time());
@ -1326,9 +1327,9 @@ void unit_animator::replace_anim_if_invalid(const unit* animated_unit
{
if(!animated_unit) return;
display*disp = display::get_singleton();
if(animated_unit->get_animation() &&
!animated_unit->get_animation()->animation_finished_potential() &&
animated_unit->get_animation()->matches(*disp,src,dst,animated_unit,event,value,hit_type,attack,second_attack,value2) >unit_animation::MATCH_FAIL) {
if(animated_unit->anim_comp().get_animation() &&
!animated_unit->anim_comp().get_animation()->animation_finished_potential() &&
animated_unit->anim_comp().get_animation()->matches(*disp,src,dst,animated_unit,event,value,hit_type,attack,second_attack,value2) >unit_animation::MATCH_FAIL) {
anim_elem tmp;
tmp.my_unit = animated_unit;
tmp.text = text;
@ -1347,21 +1348,21 @@ void unit_animator::start_animations()
int begin_time = INT_MAX;
std::vector<anim_elem>::iterator anim;
for(anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
if(anim->my_unit->get_animation()) {
if(anim->my_unit->anim_comp().get_animation()) {
if(anim->animation) {
begin_time = std::min<int>(begin_time,anim->animation->get_begin_time());
} else {
begin_time = std::min<int>(begin_time,anim->my_unit->get_animation()->get_begin_time());
begin_time = std::min<int>(begin_time,anim->my_unit->anim_comp().get_animation()->get_begin_time());
}
}
}
for(anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
if(anim->animation) {
anim->my_unit->start_animation(begin_time, anim->animation,
anim->my_unit->anim_comp().start_animation(begin_time, anim->animation,
anim->with_bars, anim->text, anim->text_color);
anim->animation = NULL;
} else {
anim->my_unit->get_animation()->update_parameters(anim->src,anim->src.get_direction(anim->my_unit->facing()));
anim->my_unit->anim_comp().get_animation()->update_parameters(anim->src,anim->src.get_direction(anim->my_unit->facing()));
}
}
@ -1371,7 +1372,7 @@ bool unit_animator::would_end() const
{
bool finished = true;
for(std::vector<anim_elem>::const_iterator anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
finished &= anim->my_unit->get_animation()->animation_finished_potential();
finished &= anim->my_unit->anim_comp().get_animation()->animation_finished_potential();
}
return finished;
}
@ -1381,7 +1382,7 @@ void unit_animator::wait_until(int animation_time) const
display*disp = display::get_singleton();
double speed = disp->turbo_speed();
resources::controller->play_slice(false);
int end_tick = animated_units_[0].my_unit->get_animation()->time_to_tick(animation_time);
int end_tick = animated_units_[0].my_unit->anim_comp().get_animation()->time_to_tick(animation_time);
while (SDL_GetTicks() < static_cast<unsigned int>(end_tick)
- std::min<int>(static_cast<unsigned int>(20/speed),20)) {
@ -1389,7 +1390,7 @@ void unit_animator::wait_until(int animation_time) const
std::min<int>(10,
static_cast<int>((animation_time - get_animation_time()) * speed))));
resources::controller->play_slice(false);
end_tick = animated_units_[0].my_unit->get_animation()->time_to_tick(animation_time);
end_tick = animated_units_[0].my_unit->anim_comp().get_animation()->time_to_tick(animation_time);
}
disp->delay(std::max<int>(0,end_tick - SDL_GetTicks() +5));
new_animation_frame();
@ -1442,25 +1443,25 @@ void unit_animator::wait_for_end() const
disp->delay(10);
finished = true;
for(std::vector<anim_elem>::const_iterator anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
finished &= anim->my_unit->get_animation()->animation_finished_potential();
finished &= anim->my_unit->anim_comp().get_animation()->animation_finished_potential();
}
}
}
int unit_animator::get_animation_time() const{
return animated_units_[0].my_unit->get_animation()->get_animation_time() ;
return animated_units_[0].my_unit->anim_comp().get_animation()->get_animation_time() ;
}
int unit_animator::get_animation_time_potential() const{
return animated_units_[0].my_unit->get_animation()->get_animation_time_potential() ;
return animated_units_[0].my_unit->anim_comp().get_animation()->get_animation_time_potential() ;
}
int unit_animator::get_end_time() const
{
int end_time = INT_MIN;
for(std::vector<anim_elem>::const_iterator anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
if(anim->my_unit->get_animation()) {
end_time = std::max<int>(end_time,anim->my_unit->get_animation()->get_end_time());
if(anim->my_unit->anim_comp().get_animation()) {
end_time = std::max<int>(end_time,anim->my_unit->anim_comp().get_animation()->get_end_time());
}
}
return end_time;
@ -1469,8 +1470,8 @@ int unit_animator::get_end_time() const
void unit_animator::pause_animation()
{
for(std::vector<anim_elem>::iterator anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
if(anim->my_unit->get_animation()) {
anim->my_unit->get_animation()->pause_animation();
if(anim->my_unit->anim_comp().get_animation()) {
anim->my_unit->anim_comp().get_animation()->pause_animation();
}
}
}
@ -1478,8 +1479,8 @@ void unit_animator::pause_animation()
void unit_animator::restart_animation()
{
for(std::vector<anim_elem>::iterator anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
if(anim->my_unit->get_animation()) {
anim->my_unit->get_animation()->restart_animation();
if(anim->my_unit->anim_comp().get_animation()) {
anim->my_unit->anim_comp().get_animation()->restart_animation();
}
}
}
@ -1487,6 +1488,6 @@ void unit_animator::restart_animation()
void unit_animator::set_all_standing()
{
for(std::vector<anim_elem>::iterator anim = animated_units_.begin(); anim != animated_units_.end();++anim) {
anim->my_unit->set_standing();
anim->my_unit->anim_comp().set_standing();
}
}

View file

@ -0,0 +1,188 @@
/*
Copyright (C) 2014 by Chris Beck <render787@gmail.com>
Part of the Battle for Wesnoth Project http://www.wesnoth.org/
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY.
See the COPYING file for more details.
*/
#include "unit_animation_component.hpp"
#include "display.hpp"
#include "map.hpp"
#include "preferences.hpp"
#include "unit_animation.hpp"
#include "unit.hpp"
const unit_animation* unit_animation_component::choose_animation(const display& disp, const map_location& loc,const std::string& event,
const map_location& second_loc,const int value,const unit_animation::hit_type hit,
const attack_type* attack, const attack_type* second_attack, int swing_num)
{
// Select one of the matching animations at random
std::vector<const unit_animation*> options;
int max_val = unit_animation::MATCH_FAIL;
for(std::vector<unit_animation>::const_iterator i = u_.animations_.begin(); i != u_.animations_.end(); ++i) {
int matching = i->matches(disp,loc,second_loc,&u_,event,value,hit,attack,second_attack,swing_num);
if(matching > unit_animation::MATCH_FAIL && matching == max_val) {
options.push_back(&*i);
} else if(matching > max_val) {
max_val = matching;
options.clear();
options.push_back(&*i);
}
}
if(max_val == unit_animation::MATCH_FAIL) {
return NULL;
}
return options[rand()%options.size()];
}
void unit_animation_component::set_standing(bool with_bars)
{
display *disp = display::get_singleton();
if (preferences::show_standing_animations()&& !u_.incapacitated()) {
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "standing"),
with_bars, "", 0, STATE_STANDING);
} else {
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "_disabled_"),
with_bars, "", 0, STATE_STANDING);
}
}
void unit_animation_component::set_ghosted(bool with_bars)
{
display *disp = display::get_singleton();
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "ghosted"),
with_bars);
}
void unit_animation_component::set_disabled_ghosted(bool with_bars)
{
display *disp = display::get_singleton();
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "disabled_ghosted"),
with_bars);
}
void unit_animation_component::set_idling()
{
display *disp = display::get_singleton();
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "idling"),
true, "", 0, STATE_FORGET);
}
void unit_animation_component::set_selecting()
{
const display *disp = display::get_singleton();
if (preferences::show_standing_animations() && !u_.incapacitated()) {
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "selected"),
true, "", 0, STATE_FORGET);
} else {
start_animation(INT_MAX, choose_animation(*disp, u_.loc_, "_disabled_selected_"),
true, "", 0, STATE_FORGET);
}
}
void unit_animation_component::start_animation (int start_time, const unit_animation *animation,
bool with_bars, const std::string &text, Uint32 text_color, STATE state)
{
const display * disp = display::get_singleton();
if (!animation) {
if (state == STATE_STANDING)
state_ = state;
if (!anim_ && state_ != STATE_STANDING)
set_standing(with_bars);
return ;
}
state_ = state;
// everything except standing select and idle
bool accelerate = (state != STATE_FORGET && state != STATE_STANDING);
draw_bars_ = with_bars;
anim_.reset(new unit_animation(*animation));
const int real_start_time = start_time == INT_MAX ? anim_->get_begin_time() : start_time;
anim_->start_animation(real_start_time, u_.loc_, u_.loc_.get_direction(u_.facing_),
text, text_color, accelerate);
frame_begin_time_ = anim_->get_begin_time() -1;
if (disp->idle_anim()) {
next_idling_ = get_current_animation_tick()
+ static_cast<int>((20000 + rand() % 20000) * disp->idle_anim_rate());
} else {
next_idling_ = INT_MAX;
}
}
void unit_animation_component::refresh()
{
if (state_ == STATE_FORGET && anim_ && anim_->animation_finished_potential())
{
set_standing();
return;
}
display &disp = *display::get_singleton();
if (state_ != STATE_STANDING || get_current_animation_tick() < next_idling_ ||
!disp.tile_nearly_on_screen(u_.loc_) || u_.incapacitated())
{
return;
}
if (get_current_animation_tick() > next_idling_ + 1000)
{
// prevent all units animating at the same time
if (disp.idle_anim()) {
next_idling_ = get_current_animation_tick()
+ static_cast<int>((20000 + rand() % 20000) * disp.idle_anim_rate());
} else {
next_idling_ = INT_MAX;
}
} else {
set_idling();
}
}
void unit_animation_component::clear_haloes ()
{
if(unit_halo_ != halo::NO_HALO) {
halo::remove(unit_halo_);
unit_halo_ = halo::NO_HALO;
}
if(anim_ ) anim_->clear_haloes();
}
bool unit_animation_component::invalidate (const display & disp)
{
bool result = false;
// Very early calls, anim not initialized yet
if(get_animation()) {
frame_parameters params;
const gamemap & map = disp.get_map();
const t_translation::t_terrain terrain = map.get_terrain(u_.loc_);
const terrain_type& terrain_info = map.get_terrain_info(terrain);
int height_adjust = static_cast<int>(terrain_info.unit_height_adjust() * disp.get_zoom_factor());
if (u_.is_flying() && height_adjust < 0) {
height_adjust = 0;
}
params.y -= height_adjust;
params.halo_y -= height_adjust;
params.image_mod = u_.image_mods();
params.halo_mod = u_.TC_image_mods();
params.image= u_.absolute_image();
result |= get_animation()->invalidate(params);
}
return result;
}
void unit_animation_component::reset_after_advance()
{
refreshing_ = false;
anim_.reset();
}

View file

@ -0,0 +1,104 @@
/*
Copyright (C) 2014 by Chris Beck <render787@gmail.com>
Part of the Battle for Wesnoth Project http://www.wesnoth.org/
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY.
See the COPYING file for more details.
*/
// This class encapsulates the animation functionality of unit.
#ifndef UNIT_ANIM_COMP_HPP
#define UNIT_ANIM_COMP_HPP
#include "halo.hpp"
#include "unit_animation.hpp" //Note: only needed for enum
#include <boost/scoped_ptr.hpp>
class unit;
class unit_animation_component
{
public:
/** States for animation. */
enum STATE {
STATE_STANDING, /** anim must fit in a hex */
STATE_FORGET, /** animation will be automatically replaced by a standing anim when finished */
STATE_ANIM}; /** normal anims */
unit_animation_component(unit & my_unit) :
u_(my_unit),
anim_(NULL),
state_(STATE_STANDING),
next_idling_(0),
frame_begin_time_(0),
draw_bars_(false),
refreshing_(false),
unit_halo_(halo::NO_HALO) {}
unit_animation_component(unit & my_unit, const unit_animation_component & o) :
u_(my_unit),
anim_(NULL),
state_(o.state_),
next_idling_(0),
frame_begin_time_(o.frame_begin_time_),
draw_bars_(o.draw_bars_),
refreshing_(o.refreshing_),
unit_halo_(halo::NO_HALO) {}
const unit_animation* choose_animation(const display& disp,
const map_location& loc, const std::string& event,
const map_location& second_loc = map_location::null_location(),
const int damage=0,
const unit_animation::hit_type hit_type = unit_animation::INVALID,
const attack_type* attack=NULL,const attack_type* second_attack = NULL,
int swing_num =0);
void set_standing(bool with_bars = true);
void set_ghosted(bool with_bars = true);
void set_disabled_ghosted(bool with_bars = true);
void set_idling();
void set_selecting();
void start_animation (int start_time, const unit_animation *animation,
bool with_bars, const std::string &text = "",
Uint32 text_color = 0, STATE state = STATE_ANIM);
bool invalidate(const display & disp);
void refresh();
void clear_haloes();
void reset_after_advance();
unit_animation* get_animation() const { return anim_.get(); }
friend class unit;
friend class drawable_unit;
private:
const unit & u_;
boost::scoped_ptr<unit_animation> anim_;
STATE state_; //animation state
int next_idling_; // used for animation
int frame_begin_time_; // used for animation
bool draw_bars_;
bool refreshing_; // avoid infinite recursion. flag used for drawing / animation
int unit_halo_; // flag used for drawing / animation
};
#endif

View file

@ -26,6 +26,8 @@
#include "mouse_events.hpp"
#include "resources.hpp"
#include "terrain_filter.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "unit_map.hpp"
#include <boost/foreach.hpp>
@ -92,7 +94,7 @@ static void teleport_unit_between(const map_location& a, const map_location& b,
animator.wait_for_end();
}
temp_unit.set_standing();
temp_unit.anim_comp().set_standing();
disp.update_display();
events::pump();
}
@ -267,7 +269,7 @@ void unit_mover::start(unit& u)
// Initialize our temporary unit for the move.
temp_unit_ptr_->set_location(path_[0]);
temp_unit_ptr_->set_facing(path_[0].get_relative_dir(path_[1]));
temp_unit_ptr_->set_standing(false);
temp_unit_ptr_->anim_comp().set_standing(false);
disp_->invalidate(path_[0]);
// If the unit can be seen here by the viewing side:
@ -299,7 +301,7 @@ void unit_mover::start(unit& u)
// Switch the display back to the real unit.
u.set_facing(temp_unit_ptr_->facing());
u.set_standing(false); // Need to reset u's animation so the new facing takes effect.
u.anim_comp().set_standing(false); // Need to reset u's animation so the new facing takes effect.
u.set_hidden(was_hidden_);
temp_unit_ptr_->set_hidden(true);
}
@ -353,13 +355,13 @@ void unit_mover::proceed_to(unit& u, size_t path_index, bool update, bool wait)
temp_unit_ptr_->set_location(path_[current_]);
disp_->invalidate(path_[current_]);
// scroll in as much of the remaining path as possible
if ( temp_unit_ptr_->get_animation() )
temp_unit_ptr_->get_animation()->pause_animation();
if ( temp_unit_ptr_->anim_comp().get_animation() )
temp_unit_ptr_->anim_comp().get_animation()->pause_animation();
disp_->scroll_to_tiles(path_.begin() + current_,
path_.end(), game_display::ONSCREEN,
true, false, 0.0, force_scroll_);
if ( temp_unit_ptr_->get_animation() )
temp_unit_ptr_->get_animation()->restart_animation();
if ( temp_unit_ptr_->anim_comp().get_animation() )
temp_unit_ptr_->anim_comp().get_animation()->restart_animation();
}
if ( tiles_adjacent(path_[current_], path_[current_+1]) )
@ -375,7 +377,7 @@ void unit_mover::proceed_to(unit& u, size_t path_index, bool update, bool wait)
// Update the unit's facing.
u.set_facing(temp_unit_ptr_->facing());
u.set_standing(false); // Need to reset u's animation so the new facing takes effect.
u.anim_comp().set_standing(false); // Need to reset u's animation so the new facing takes effect.
// Remember the unit to unhide when the animation finishes.
shown_unit_ = &u;
if ( wait )
@ -458,7 +460,7 @@ void unit_mover::finish(unit &u, map_location::DIRECTION dir)
// Facing gets set even when not animating.
u.set_facing(dir == map_location::NDIRECTIONS ? final_dir : dir);
u.set_standing(true); // Need to reset u's animation so the new facing takes effect.
u.anim_comp().set_standing(true); // Need to reset u's animation so the new facing takes effect.
// Redraw path ends (even if not animating).
disp_->invalidate(path_.front());
@ -532,10 +534,10 @@ void unit_sheath_weapon(const map_location& primary_loc, unit* primary_unit,
animator.wait_for_end();
}
if(primary_unit) {
primary_unit->set_standing();
primary_unit->anim_comp().set_standing();
}
if(secondary_unit) {
secondary_unit->set_standing();
secondary_unit->anim_comp().set_standing();
}
reset_helpers(primary_unit,secondary_unit);
@ -618,7 +620,7 @@ void unit_attack(display * disp, game_board & board,
hit_type, &attack, secondary_attack, swing);
// note that we take an anim from the real unit, we'll use it later
const unit_animation *defender_anim = def->choose_animation(*disp,
const unit_animation *defender_anim = def->anim_comp().choose_animation(*disp,
def->get_location(), "defend", att->get_location(), damage,
hit_type, &attack, secondary_attack, swing);
animator.add_animation(&defender, defender_anim, def->get_location(),
@ -660,7 +662,7 @@ void unit_attack(display * disp, game_board & board,
}
animator.wait_for_end();
// pass the animation back to the real unit
def->start_animation(animator.get_end_time(), defender_anim, true);
def->anim_comp().start_animation(animator.get_end_time(), defender_anim, true);
reset_helpers(&*att, &*def);
def->set_hitpoints(def_hitpoints);
}
@ -675,7 +677,7 @@ void reset_helpers(const unit *attacker,const unit *defender)
BOOST_FOREACH (const unit_ability & ability, leaders) {
unit_map::const_iterator leader = units.find(ability.second);
assert(leader != units.end());
leader->set_standing();
leader->anim_comp().set_standing();
}
}
@ -684,7 +686,7 @@ void reset_helpers(const unit *attacker,const unit *defender)
BOOST_FOREACH (const unit_ability & ability, helpers) {
unit_map::const_iterator helper = units.find(ability.second);
assert(helper != units.end());
helper->set_standing();
helper->anim_comp().set_standing();
}
}
}

View file

@ -42,6 +42,7 @@
#include "play_controller.hpp"
#include "resources.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "unit_map.hpp"
#include <boost/foreach.hpp>
@ -198,7 +199,7 @@ void highlighter::last_action_redraw(move_ptr move)
bool this_is_second_to_last_action = (second_to_last_action != sa.end() && move == *second_to_last_action);
if(this_is_last_action || (this_is_second_to_last_action && !last_action_has_fake_unit)) {
move->get_fake_unit()->set_standing(true);
move->get_fake_unit()->anim_comp().set_standing(true);
}
}
}
@ -276,7 +277,7 @@ void highlighter::highlight_main_visitor::visit(move_ptr move)
}
if(move->get_fake_unit()) {
///@todo find some highlight animation
move->get_fake_unit()->set_ghosted(true);
move->get_fake_unit()->anim_comp().set_ghosted(true);
//Make sure the fake unit is the only one displayed in its hex
resources::screen->add_exclusive_draw(move->get_fake_unit()->get_location(), *move->get_fake_unit());
highlighter_.exclusive_display_hexes_.insert(move->get_fake_unit()->get_location());
@ -308,7 +309,7 @@ void highlighter::highlight_secondary_visitor::visit(move_ptr move)
move->set_arrow_brightness(move::ARROW_BRIGHTNESS_HIGHLIGHTED);
}
if(move->get_fake_unit()) {
move->get_fake_unit()->set_ghosted(true);
move->get_fake_unit()->anim_comp().set_ghosted(true);
//Make sure the fake unit is the only one displayed in its hex
resources::screen->add_exclusive_draw(move->get_fake_unit()->get_location(), *move->get_fake_unit());
highlighter_.exclusive_display_hexes_.insert(move->get_fake_unit()->get_location());
@ -328,7 +329,7 @@ void highlighter::unhighlight_visitor::visit(move_ptr move)
move->set_arrow_brightness(move::ARROW_BRIGHTNESS_STANDARD);
}
if(move->get_fake_unit()) {
move->get_fake_unit()->set_disabled_ghosted(false);
move->get_fake_unit()->anim_comp().set_disabled_ghosted(false);
highlighter_.last_action_redraw(move);
}

View file

@ -45,6 +45,8 @@
#include "play_controller.hpp"
#include "resources.hpp"
#include "team.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "unit_display.hpp"
#include <boost/lexical_cast.hpp>
@ -334,7 +336,7 @@ void manager::post_delete_action(action_ptr action)
if(action_it != side_actions->end()) {
move_ptr move = boost::dynamic_pointer_cast<class move>(*action_it);
if(move && move->get_fake_unit()) {
move->get_fake_unit()->set_standing(true);
move->get_fake_unit()->anim_comp().set_standing(true);
}
}
}
@ -714,13 +716,13 @@ void manager::create_temp_move()
// Create temp ghost unit
fake_unit.reset(new class fake_unit(*temp_moved_unit));
fake_unit->place_on_fake_unit_manager( resources::fake_units);
fake_unit->set_ghosted(true);
fake_unit->anim_comp().set_ghosted(true);
}
unit_display::move_unit(path, *fake_unit, false); //get facing right
fake_unit->invalidate(*game_display::get_singleton());
fake_unit->anim_comp().invalidate(*game_display::get_singleton());
fake_unit->set_location(*curr_itor);
fake_unit->set_ghosted(true);
fake_unit->anim_comp().set_ghosted(true);
}
else //zero-hex path -- don't bother drawing a fake unit
fake_unit.reset();
@ -730,7 +732,7 @@ void manager::create_temp_move()
}
//in case path shortens on next step and one ghosted unit has to be removed
int ind = fake_units_.size() - 1;
fake_units_[ind]->invalidate(*game_display::get_singleton());
fake_units_[ind]->anim_comp().invalidate(*game_display::get_singleton());
//toss out old arrows and fake units
move_arrows_.resize(turn+1);
fake_units_.resize(turn+1);
@ -741,7 +743,7 @@ void manager::erase_temp_move()
move_arrows_.clear();
BOOST_FOREACH(fake_unit_ptr const& tmp, fake_units_) {
if(tmp) {
tmp->invalidate(*game_display::get_singleton());
tmp->anim_comp().invalidate(*game_display::get_singleton());
}
}
fake_units_.clear();
@ -812,7 +814,7 @@ void manager::save_temp_attack(const map_location& attacker_loc, const map_locat
assert(route_->steps.back() == attacker_loc);
source_hex = route_->steps.front();
fake_unit->set_disabled_ghosted(true);
fake_unit->anim_comp().set_disabled_ghosted(true);
}
else
{

View file

@ -35,6 +35,7 @@
#include "resources.hpp"
#include "team.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "unit_display.hpp"
#include "unit_map.hpp"
@ -135,7 +136,7 @@ move::move(config const& cfg, bool hidden)
if(hidden)
fake_unit_->set_hidden(true);
fake_unit_->place_on_fake_unit_manager(resources::fake_units);
fake_unit_->set_ghosted(true);
fake_unit_->anim_comp().set_ghosted(true);
unit_display::move_unit(route_->steps, *fake_unit_, false); //get facing right
fake_unit_->set_location(route_->steps.back());
@ -151,7 +152,7 @@ void move::init()
//than previous actions' fake units
if (fake_unit_)
{
fake_unit_->set_ghosted(true);
fake_unit_->anim_comp().set_ghosted(true);
}
side_actions_ptr side_actions = resources::teams->at(team_index()).get_side_actions();
side_actions::iterator action = side_actions->find_last_action_of(*(get_unit()));
@ -160,7 +161,7 @@ void move::init()
if (move_ptr move = boost::dynamic_pointer_cast<class move>(*action))
{
if (move->fake_unit_)
move->fake_unit_->set_disabled_ghosted(true);
move->fake_unit_->anim_comp().set_disabled_ghosted(true);
}
}

View file

@ -33,6 +33,7 @@
#include "synced_context.hpp"
#include "team.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include <boost/foreach.hpp>
@ -98,7 +99,7 @@ void recall::init()
fake_unit_->set_location(recall_hex_);
fake_unit_->set_movement(0, true);
fake_unit_->set_attacks(0);
fake_unit_->set_ghosted(false);
fake_unit_->anim_comp().set_ghosted(false);
fake_unit_->place_on_fake_unit_manager( resources::fake_units);
}

View file

@ -29,6 +29,7 @@
#include "play_controller.hpp"
#include "resources.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include "unit_map.hpp"
#include "unit_types.hpp"
@ -87,7 +88,7 @@ void recruit::init()
fake_unit_->set_location(recruit_hex_);
fake_unit_->set_movement(0, true);
fake_unit_->set_attacks(0);
fake_unit_->set_ghosted(false);
fake_unit_->anim_comp().set_ghosted(false);
fake_unit_->place_on_fake_unit_manager(resources::fake_units);
cost_ = fake_unit_->type().cost();

View file

@ -32,6 +32,7 @@
#include "resources.hpp"
#include "team.hpp"
#include "unit.hpp"
#include "unit_animation_component.hpp"
#include <boost/foreach.hpp>
@ -140,13 +141,13 @@ temporary_unit_hider::~temporary_unit_hider()
void ghost_owner_unit(unit* unit)
{
unit->set_disabled_ghosted(false);
unit->anim_comp().set_disabled_ghosted(false);
resources::screen->invalidate(unit->get_location());
}
void unghost_owner_unit(unit* unit)
{
unit->set_standing(true);
unit->anim_comp().set_standing(true);
resources::screen->invalidate(unit->get_location());
}