1 /***************************************************************************
2  *   Copyright (C) 2005-2019 by the FIFE team                              *
3  *   http://www.fifengine.net                                              *
4  *   This file is part of FIFE.                                            *
5  *                                                                         *
6  *   FIFE is free software; you can redistribute it and/or                 *
7  *   modify it under the terms of the GNU Lesser General Public            *
8  *   License as published by the Free Software Foundation; either          *
9  *   version 2.1 of the License, or (at your option) any later version.    *
10  *                                                                         *
11  *   This library is distributed in the hope that it will be useful,       *
12  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
13  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU     *
14  *   Lesser General Public License for more details.                       *
15  *                                                                         *
16  *   You should have received a copy of the GNU Lesser General Public      *
17  *   License along with this library; if not, write to the                 *
18  *   Free Software Foundation, Inc.,                                       *
19  *   51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA          *
20  ***************************************************************************/
21 
22 #ifndef FIFE_VIEW_VISUAL_H
23 #define FIFE_VIEW_VISUAL_H
24 
25 // Standard C++ library includes
26 
27 // 3rd party library includes
28 
29 // FIFE includes
30 // These includes are split up in two parts, separated by one empty line
31 // First block: files included from the FIFE root src directory
32 // Second block: files included from the same folder
33 #include "model/metamodel/ivisual.h"
34 #include "util/math/angles.h"
35 #include "util/structures/rect.h"
36 #include "video/animation.h"
37 #include "video/color.h"
38 
39 
40 namespace FIFE {
41 	class Object;
42 	class Instance;
43 	class Action;
44 	class Image;
45 
46 	class OverlayColors {
47 	public:
48 		/** Constructors
49 		 */
50 		OverlayColors();
51 		OverlayColors(ImagePtr image);
52 		OverlayColors(AnimationPtr animation);
53 
54 		/** Destructor
55 		 */
56 		~OverlayColors();
57 
58 		void setColorOverlayImage(ImagePtr image);
59 		ImagePtr getColorOverlayImage();
60 		void setColorOverlayAnimation(AnimationPtr animation);
61 		AnimationPtr getColorOverlayAnimation();
62 		void changeColor(const Color& source, const Color& target);
63 		const std::map<Color, Color>& getColors();
64 		void resetColors();
65 
66 	private:
67 		std::map<Color, Color> m_colorMap;
68 		ImagePtr m_image;
69 		AnimationPtr m_animation;
70 	};
71 
72 	/** Base class for all 2 dimensional visual classes
73 	 * Visual classes are extensions to visualize the stuff in model (e.g. instances)
74 	 * The reason why its separated is to keep model view-agnostic, so that we could
75 	 * have e.g. 3d, 2d and character based visualizations to the same data
76 	 */
77 	class Visual2DGfx: public IVisual {
78 	public:
79 		/** Destructor
80 		 */
81 		virtual ~Visual2DGfx();
82 
83 	protected:
84 		/** Constructor
85 		 */
86 		Visual2DGfx();
87 	};
88 
89 	/** Object visual contains data that is needed for visualizing objects
90 	 */
91 	class ObjectVisual: public Visual2DGfx {
92 	public:
93 		/** Constructs and assigns it to the passed item
94 		 */
95 		static ObjectVisual* create(Object* object);
96 
97 		/** Destructor
98 		 */
99 		virtual ~ObjectVisual();
100 
101 		/** Adds new static image with given angle (degrees)
102 		 * Static images are used in case there are no actions active in the instance
103 		 * There can be several static images for different angles, that are used in
104 		 * case view / layer is rotated
105 		 * In case there are no exact matches for current view angles, closest one is used
106 		 * @param angle angle for image. 0 degrees starts from right and turns counter-clockwise
107 		 *              (normal math notation)
108 		  @param image_index index of image to use for given degress
109 		 */
110 		void addStaticImage(uint32_t angle, int32_t image_index);
111 
112 		/** Returns closest matching static image for given angle
113 		 * @return id for static image
114 		 */
115 		int32_t getStaticImageIndexByAngle(int32_t angle);
116 
117 		/** Adds new static color overlay with given angle (degrees).
118 		 */
119 		void addStaticColorOverlay(uint32_t angle, const OverlayColors& colors);
120 
121 		/** Returns closest matching static color overlay for given angle
122 		 * @return pointer to OverlayColor class
123 		 */
124 		OverlayColors* getStaticColorOverlay(int32_t angle);
125 
126 		/** Removes a static color overlay with given angle (degrees).
127 		 */
128 		void removeStaticColorOverlay(int32_t angle);
129 
130 		/** Returns closest matching image angle for given angle
131 		 * @return closest matching angle
132 		 */
133 		int32_t getClosestMatchingAngle(int32_t angle);
134 
135 		/** Returns list of available static image angles for this object
136 		 */
137 		void getStaticImageAngles(std::vector<int32_t>& angles);
138 
139 		/** Indicates if there exists a color overlay.
140 		 */
isColorOverlay()141 		bool isColorOverlay() { return !m_colorOverlayMap.empty(); }
142 
143 	private:
144 		/** Constructor
145 		 */
146 		ObjectVisual();
147 
148 		type_angle2id m_angle2img;
149 
150 		typedef std::map<uint32_t, OverlayColors> AngleColorOverlayMap;
151 		AngleColorOverlayMap m_colorOverlayMap;
152 		type_angle2id m_map;
153 	};
154 
155 
156 	/** Instance visual contains data that is needed to visualize the instance on screen
157 	 */
158 	class InstanceVisual: public Visual2DGfx {
159 	public:
160 		/** Constructs and assigns it to the passed item
161 		 */
162 		static InstanceVisual* create(Instance* instance);
163 
164 		/** Destructor
165 		 */
166 		virtual ~InstanceVisual();
167 
168 		/** Sets transparency value for object to be visualized
169 		 *  @param transparency set the transparency
170 		 */
171 		void setTransparency(uint8_t transparency);
172 
173 		/** Gets current transparency value (0-255)
174 		 *  @return current transparency value
175 		 */
176 		uint8_t getTransparency();
177 
178 		/** Sets visibility value for object to be visualized
179 		 *  @param visible is object visible or not
180 		 */
181 		void setVisible(bool visible);
182 
183 		/** Is instance visible or not
184 		 *  @return is instance visible or not
185 		 */
186 		bool isVisible();
187 
188 		/** Sets stack position of the instance
189 		 *  Stack position is used to define the order in which instances residing
190 		 *  in the same location are drawn
191 		 *  @param stackposition new stack position
192 		 */
193 		void setStackPosition(int32_t stackposition);
194 
195 		/** Gets current stack position of instance
196 		 *  @return current stack position
197 		 */
198 		int32_t getStackPosition();
199 
200 	private:
201 		/** Constructor
202 		 */
203 		InstanceVisual();
204 		uint8_t m_transparency;
205 		bool m_visible;
206 		int32_t m_stackposition;
207 		Instance* m_instance;
208 	};
209 
210 	/** Action visual contains data that is needed to visualize different actions on screen
211 	 */
212 	class ActionVisual: public Visual2DGfx {
213 	public:
214 		/** Constructs and assigns it to the passed item
215 		 */
216 		static ActionVisual* create(Action* action);
217 
218 		/** Destructor
219 		 */
220 		virtual ~ActionVisual();
221 
222 		/** Adds new animation with given angle (degrees)
223 		 */
224 		void addAnimation(uint32_t angle, AnimationPtr animationptr);
225 
226 		/** Gets index to animation closest to given angle
227 		 * @return animation index, -1 if no animations available
228 		 */
229 		AnimationPtr getAnimationByAngle(int32_t angle);
230 
231 		/** Adds new animation overlay with given angle (degrees) and order
232 		 */
233 		void addAnimationOverlay(uint32_t angle, int32_t order, AnimationPtr animationptr);
234 
235 		/** Gets map with animations closest to given angle
236 		 * @return animation map
237 		 */
238 		std::map<int32_t, AnimationPtr> getAnimationOverlay(int32_t angle);
239 
240 		/** Removes animation overlay with given angle (degrees) and order
241 		 */
242 		void removeAnimationOverlay(uint32_t angle, int32_t order);
243 
244 		/** Adds new color overlay with given angle (degrees) and colors.
245 		 * Note: Works only for single animations not for AnimationOverlays. (order is missing)
246 		 */
247 		void addColorOverlay(uint32_t angle, const OverlayColors& colors);
248 
249 		/** Gets OverlayColors for given angle (degrees).
250 		 * @return pointer to OverlayColors or Null
251 		 */
252 		OverlayColors* getColorOverlay(int32_t angle);
253 
254 		/** Removes color overlay with given angle (degrees).
255 		 */
256 		void removeColorOverlay(int32_t angle);
257 
258 		/** Adds new color overlay with given angle (degrees), order and colors.
259 		 * Note: Works only for AnimationOverlays.
260 		 */
261 		void addColorOverlay(uint32_t angle, int32_t order, const OverlayColors& colors);
262 
263 		/** Gets OverlayColors for given angle (degrees) and order.
264 		 * @return pointer to OverlayColors or Null
265 		 */
266 		OverlayColors* getColorOverlay(int32_t angle, int32_t order);
267 
268 		/** Removes color overlay with given angle (degrees) and order.
269 		 */
270 		void removeColorOverlay(int32_t angle, int32_t order);
271 
272 		/** Returns list of available angles for this Action
273 		 */
274 		void getActionImageAngles(std::vector<int32_t>& angles);
275 
276 		/** Convertes animations and optional color overlay to default animation overlay.
277 		 * The default order value for both is 0. The old data remain, so if you remove the animation overlay
278 		 * the old plain animations and colors be used again.
279 		 */
280 		void convertToOverlays(bool color);
281 
282 		/** Returns true if it exists a animation overlay, otherwise false.
283 		 */
isAnimationOverlay()284 		bool isAnimationOverlay() { return !m_animationOverlayMap.empty(); }
285 
286 		/** Returns true if it exists a color overlay, otherwise false.
287 		 */
isColorOverlay()288 		bool isColorOverlay() { return !m_colorOverlayMap.empty() || !m_colorAnimationOverlayMap.empty(); }
289 
290 	private:
291 		/** Constructor
292 		 */
293 		ActionVisual();
294 
295 		// animations associated with this action
296 		typedef std::map<uint32_t, AnimationPtr> AngleAnimationMap;
297 		AngleAnimationMap m_animation_map;
298 
299 		typedef std::map<uint32_t, std::map<int32_t, AnimationPtr> > AngleAnimationOverlayMap;
300 		AngleAnimationOverlayMap m_animationOverlayMap;
301 
302 		typedef std::map<uint32_t, OverlayColors> AngleColorOverlayMap;
303 		AngleColorOverlayMap m_colorOverlayMap;
304 
305 		typedef std::map<uint32_t, std::map<int32_t, OverlayColors> > AngleColorAnimationOverlayMap;
306 		AngleColorAnimationOverlayMap m_colorAnimationOverlayMap;
307 		//need this map to use the getIndexByAngle() function in angles.h
308 		type_angle2id m_map;
309 	};
310 
311 }
312 #endif
313