widelands-dev team mailing list archive
-
widelands-dev team
-
Mailing list archive
-
Message #04665
[Merge] lp:~widelands-dev/widelands/pc_on_buttons into lp:widelands
GunChleoc has proposed merging lp:~widelands-dev/widelands/pc_on_buttons into lp:widelands.
Requested reviews:
Widelands Developers (widelands-dev)
For more details, see:
https://code.launchpad.net/~widelands-dev/widelands/pc_on_buttons/+merge/278191
This adds player color to building buttons. You can see it in action when building a new building or in the building statistics window.
The images with player color are cached in the AnimationManager.
--
Your team Widelands Developers is requested to review the proposed merge of lp:~widelands-dev/widelands/pc_on_buttons into lp:widelands.
=== modified file 'src/graphic/animation.cc'
--- src/graphic/animation.cc 2015-11-06 12:19:22 +0000
+++ src/graphic/animation.cc 2015-11-20 18:25:18 +0000
@@ -39,6 +39,7 @@
#include "graphic/image.h"
#include "graphic/image_cache.h"
#include "graphic/surface.h"
+#include "graphic/texture.h"
#include "io/filesystem/layered_filesystem.h"
#include "logic/bob.h"
#include "logic/instances.h"
@@ -123,7 +124,8 @@
uint16_t nr_frames() const override;
uint32_t frametime() const override;
const Point& hotspot() const override;
- const std::string& representative_image_from_disk_filename() const override;
+ Image* representative_image(const RGBColor* clr) const override;
+ const std::string& representative_image_filename() const override;
virtual void blit(uint32_t time, const Point&, const Rect& srcrc, const RGBColor* clr, Surface*)
const override;
void trigger_soundfx(uint32_t framenumber, uint32_t stereo_position) const override;
@@ -297,7 +299,33 @@
return hotspot_;
}
-const std::string& NonPackedAnimation::representative_image_from_disk_filename() const {
+Image* NonPackedAnimation::representative_image(const RGBColor* clr) const {
+ assert(!image_files_.empty());
+
+ const Image* image = g_gr->images().get(image_files_[0]);
+ int w = image->width();
+ int h = image->height();
+
+ Texture* rv = new Texture(w, h);
+ if (!hasplrclrs_ || clr == nullptr) {
+ ::blit(Rect(Point(0, 0), w, h),
+ *image,
+ Rect(Point(0, 0), w, h),
+ 1.,
+ BlendMode::UseAlpha,
+ rv);
+ } else {
+ blit_blended(Rect(Point(0, 0), w, h),
+ *image,
+ *g_gr->images().get(pc_mask_image_files_[0]),
+ Rect(Point(0, 0), w, h),
+ *clr,
+ rv);
+ }
+ return rv;
+}
+
+const std::string& NonPackedAnimation::representative_image_filename() const {
return image_files_[0];
}
@@ -383,20 +411,24 @@
*/
uint32_t AnimationManager::load(const LuaTable& table) {
- m_animations.push_back(new NonPackedAnimation(table));
- return m_animations.size();
+ animations_.push_back(std::unique_ptr<Animation>(new NonPackedAnimation(table)));
+ return animations_.size();
}
const Animation& AnimationManager::get_animation(uint32_t id) const
{
- if (!id || id > m_animations.size())
+ if (!id || id > animations_.size())
throw wexception("Requested unknown animation with id: %i", id);
- return *m_animations[id - 1];
+ return *animations_[id - 1].get();
}
-AnimationManager::~AnimationManager()
-{
- for (vector<Animation*>::iterator it = m_animations.begin(); it != m_animations.end(); ++it)
- delete *it;
+const Image* AnimationManager::get_representative_image(uint32_t id, const RGBColor* clr) {
+ if (representative_images_.count(id) != 1) {
+ representative_images_.insert(
+ std::make_pair(
+ id,
+ std::unique_ptr<Image>(g_gr->animations().get_animation(id).representative_image(clr))));
+ }
+ return representative_images_.at(id).get();
}
=== modified file 'src/graphic/animation.h'
--- src/graphic/animation.h 2015-11-06 12:19:22 +0000
+++ src/graphic/animation.h 2015-11-20 18:25:18 +0000
@@ -22,6 +22,7 @@
#include <cstring>
#include <map>
+#include <memory>
#include <string>
#include <vector>
@@ -67,13 +68,17 @@
/// so the caller has to adjust for the hotspot himself.
virtual const Point& hotspot() const = 0;
- /// Returns the disk filename for the first image in the animation
- virtual const std::string& representative_image_from_disk_filename() const = 0;
+ /// An image of the first frame, blended with the given player color.
+ /// The 'clr' is the player color used for blending - the parameter can be
+ /// 'nullptr', in which case the neutral image will be returned.
+ virtual Image* representative_image(const RGBColor* clr) const = 0;
+ /// The filename of the image used for the first frame, without player color.
+ virtual const std::string& representative_image_filename() const = 0;
/// Blit the animation frame that should be displayed at the given time index
/// so that the given point is at the top left of the frame. Srcrc defines
/// the part of the animation that should be blitted. The 'clr' is the player
- /// color used for blitting - the parameter can be nullptr in which case the
+ /// color used for blitting - the parameter can be 'nullptr', in which case the
/// neutral image will be blitted. The Surface is the target for the blit
/// operation and must be non-null.
virtual void blit(uint32_t time, const Point&, const Rect& srcrc, const RGBColor* clr, Surface*) const = 0;
@@ -90,7 +95,6 @@
*/
class AnimationManager {
public:
- ~AnimationManager();
/**
* Loads an animation, graphics sound and everything from a Lua table.
*
@@ -104,10 +108,14 @@
/// unknown.
const Animation& get_animation(uint32_t id) const;
+ /// Returns the representative image, using the given player color.
+ /// If this image has been generated before, it is pulled from the cache using
+ /// the clr argument that was used previously.
+ const Image* get_representative_image(uint32_t id, const RGBColor* clr = nullptr);
+
private:
- // TODO(SirVer): this vector should be changed to unique__ptr (spelled wrong to avoid message by CodeCheck)
- // instead of raw pointers to get rid of the destructor
- std::vector<Animation*> m_animations;
+ std::vector<std::unique_ptr<Animation>> animations_;
+ std::map<uint32_t, std::unique_ptr<Image>> representative_images_;
};
#endif // end of include guard: WL_GRAPHIC_ANIMATION_H
=== modified file 'src/logic/instances.cc'
--- src/logic/instances.cc 2015-11-02 19:29:03 +0000
+++ src/logic/instances.cc 2015-11-20 18:25:18 +0000
@@ -249,7 +249,7 @@
throw GameDataError("Map object %s has animations but no idle animation", init_name.c_str());
}
representative_image_filename_ = g_gr->animations().get_animation(get_animation("idle"))
- .representative_image_from_disk_filename();
+ .representative_image_filename();
}
if (table.has_key("icon")) {
icon_filename_ = table.get_string("icon");
@@ -310,9 +310,9 @@
return "";
}
-const Image* MapObjectDescr::representative_image() const {
- if (!representative_image_filename_.empty()) {
- return g_gr->images().get(representative_image_filename_);
+const Image* MapObjectDescr::representative_image(const RGBColor* player_color) const {
+ if (is_animation_known("idle")) {
+ return g_gr->animations().get_representative_image(get_animation("idle"), player_color);
}
return nullptr;
}
=== modified file 'src/logic/instances.h'
--- src/logic/instances.h 2015-10-21 16:43:30 +0000
+++ src/logic/instances.h 2015-11-20 18:25:18 +0000
@@ -32,6 +32,7 @@
#include "base/log.h"
#include "base/macros.h"
+#include "graphic/color.h"
#include "graphic/image.h"
#include "logic/cmd_queue.h"
#include "logic/widelands.h"
@@ -139,7 +140,7 @@
/// Returns the image for the first frame of the idle animation if the MapObject has animations,
/// nullptr otherwise
- const Image* representative_image() const;
+ const Image* representative_image(const RGBColor* player_color = nullptr) const;
/// Returns the image fileneme for first frame of the idle animation if the MapObject has animations,
/// is empty otherwise
const std::string& representative_image_filename() const;
=== modified file 'src/logic/partially_finished_building.cc'
--- src/logic/partially_finished_building.cc 2015-11-11 09:52:55 +0000
+++ src/logic/partially_finished_building.cc 2015-11-20 18:25:18 +0000
@@ -149,7 +149,7 @@
*/
const Image* PartiallyFinishedBuilding::representative_image() const
{
- return m_building->representative_image();
+ return m_building->representative_image(&owner().get_playercolor());
}
=== modified file 'src/wui/building_statistics_menu.cc'
--- src/wui/building_statistics_menu.cc 2015-11-17 14:36:25 +0000
+++ src/wui/building_statistics_menu.cc 2015-11-20 18:25:18 +0000
@@ -394,7 +394,8 @@
kBuildGridCellWidth,
kBuildGridCellHeight,
g_gr->images().get("pics/but1.png"),
- descr.representative_image(),
+ descr.representative_image(&iplayer().get_player()
+ ->get_playercolor()),
"",
false,
true);
=== modified file 'src/wui/fieldaction.cc'
--- src/wui/fieldaction.cc 2015-11-11 09:53:54 +0000
+++ src/wui/fieldaction.cc 2015-11-20 18:25:18 +0000
@@ -56,7 +56,7 @@
// The BuildGrid presents a selection of buildable buildings
struct BuildGrid : public UI::IconGrid {
BuildGrid(UI::Panel* parent,
- const Widelands::TribeDescr& tribe,
+ Widelands::Player* plr,
int32_t x,
int32_t y,
int32_t cols);
@@ -73,14 +73,14 @@
void mousein_slot(int32_t idx);
private:
- const Widelands::TribeDescr& tribe_;
+ Widelands::Player* plr_;
};
BuildGrid::BuildGrid(
- UI::Panel* parent, const Widelands::TribeDescr& tribe,
+ UI::Panel* parent, Widelands::Player* plr,
int32_t x, int32_t y, int32_t cols) :
UI::IconGrid(parent, x, y, kBuildGridCellSize, kBuildGridCellSize, cols),
- tribe_(tribe)
+ plr_(plr)
{
clicked.connect(boost::bind(&BuildGrid::click_slot, this, _1));
mouseout.connect(boost::bind(&BuildGrid::mouseout_slot, this, _1));
@@ -95,15 +95,16 @@
void BuildGrid::add(Widelands::DescriptionIndex id)
{
const Widelands::BuildingDescr & descr =
- *tribe_.get_building_descr(Widelands::DescriptionIndex(id));
+ *plr_->tribe().get_building_descr(Widelands::DescriptionIndex(id));
+
// TODO(sirver): change this to take a Button subclass instead of
// parameters. This will allow overriding the way it is rendered
// to bring back player colors.
UI::IconGrid::add(descr.name(),
- descr.representative_image(),
+ descr.representative_image(&plr_->get_playercolor()),
reinterpret_cast<void*>(id),
descr.descname() + "<br><font size=11>" + _("Construction costs:") +
- "</font><br>" + waremap_to_richtext(tribe_, descr.buildcost()));
+ "</font><br>" + waremap_to_richtext(plr_->tribe(), descr.buildcost()));
}
@@ -531,7 +532,7 @@
// Allocate the tab's grid if necessary
if (!*ppgrid) {
- *ppgrid = new BuildGrid(&m_tabpanel, tribe, 0, 0, 5);
+ *ppgrid = new BuildGrid(&m_tabpanel, m_plr, 0, 0, 5);
(*ppgrid)->buildclicked.connect(boost::bind(&FieldActionWindow::act_build, this, _1));
(*ppgrid)->buildmouseout.connect
(boost::bind(&FieldActionWindow::building_icon_mouse_out, this, _1));
Follow ups