1 | /*! |
2 | * \file ScaleTranslate.hpp |
3 | * \brief file ScaleTranslate.hpp |
4 | * |
5 | * Adapted from: WRATHScaleTranslate.hpp of WRATH: |
6 | * |
7 | * Copyright 2013 by Nomovok Ltd. |
8 | * Contact: info@nomovok.com |
9 | * This Source Code Form is subject to the |
10 | * terms of the Mozilla Public License, v. 2.0. |
11 | * If a copy of the MPL was not distributed with |
12 | * this file, You can obtain one at |
13 | * http://mozilla.org/MPL/2.0/. |
14 | * |
15 | * \author Kevin Rogovin <kevin.rogovin@nomovok.com> |
16 | * \author Kevin Rogovin <kevin.rogovin@gmail.com> |
17 | * |
18 | */ |
19 | |
20 | |
21 | |
22 | |
23 | #ifndef FASTUIDRAW_DEMO_SCALETRANSLATE_HPP |
24 | #define FASTUIDRAW_DEMO_SCALETRANSLATE_HPP |
25 | |
26 | #include <cstdlib> |
27 | #include <fastuidraw/util/util.hpp> |
28 | #include <fastuidraw/util/vecN.hpp> |
29 | #include <fastuidraw/util/math.hpp> |
30 | #include <fastuidraw/util/matrix.hpp> |
31 | #include <fastuidraw/painter/painter.hpp> |
32 | |
33 | /*!\class ScaleTranslate |
34 | A ScaleTranslate represents the composition |
35 | of a scaling and a translation, i.e. |
36 | \f[ f(x,y) = (sx,sy) + (A,B) \f] |
37 | where \f$ s \f$ =scale() and \f$ (A,B) \f$ =translation(). |
38 | */ |
39 | template<typename T> |
40 | class ScaleTranslate |
41 | { |
42 | public: |
43 | /*! |
44 | Ctor. Initialize a ScaleTranslate from a |
45 | scaling factor and translation |
46 | \param tr translation to use |
47 | \param s scaling factor to apply to both x-axis and y-axis, |
48 | _absolute_ value is stored, i.e. the sign of s |
49 | is ignored |
50 | */ |
51 | ScaleTranslate(const fastuidraw::vecN<T, 2> &tr = fastuidraw::vecN<T, 2>(T(0), T(0)), |
52 | T s = T(1)): |
53 | m_scale(fastuidraw::t_abs(s)), |
54 | m_translation(tr) |
55 | {} |
56 | |
57 | /*! |
58 | Ctor. Initialize a ScaleTranslate from a |
59 | scaling factor |
60 | \param s scaling factor to apply to both x-axis and y-axis, |
61 | _absolute_ value is stored, i.e. the sign of s |
62 | is ignored |
63 | */ |
64 | ScaleTranslate(T s): |
65 | m_scale(fastuidraw::t_abs(s)), |
66 | m_translation(T(0), T(0)) |
67 | {} |
68 | |
69 | /*! |
70 | Returns the inverse transformation to this. |
71 | */ |
72 | ScaleTranslate |
73 | inverse(void) const |
74 | { |
75 | ScaleTranslate r; |
76 | |
77 | r.m_scale = T(1) / m_scale; |
78 | r.m_translation = -r.m_scale * m_translation; |
79 | |
80 | return r; |
81 | } |
82 | |
83 | /*! |
84 | Returns the translation of this |
85 | ScaleTranslate. |
86 | */ |
87 | const fastuidraw::vecN<T, 2>& |
88 | translation(void) const |
89 | { |
90 | return m_translation; |
91 | } |
92 | |
93 | /*! |
94 | Sets the translation of this. |
95 | \param tr value to set translation to. |
96 | */ |
97 | ScaleTranslate& |
98 | translation(const fastuidraw::vecN<T, 2> &tr) |
99 | { |
100 | m_translation = tr; |
101 | return *this; |
102 | } |
103 | |
104 | /*! |
105 | Sets the x-coordinate of the translation of this. |
106 | \param x value to set translation to. |
107 | */ |
108 | ScaleTranslate& |
109 | translation_x(T x) |
110 | { |
111 | m_translation.x() = x; |
112 | return *this; |
113 | } |
114 | |
115 | /*! |
116 | Sets the y-coordinate of the translation of this. |
117 | \param y value to set translation to. |
118 | */ |
119 | ScaleTranslate& |
120 | translation_y(T y) |
121 | { |
122 | m_translation.y() = y; |
123 | return *this; |
124 | } |
125 | |
126 | /*! |
127 | Returns the scale of this. |
128 | Scaling factor is _NEVER_ |
129 | negative. |
130 | */ |
131 | T |
132 | scale(void) const |
133 | { |
134 | return m_scale; |
135 | } |
136 | |
137 | /*! |
138 | Sets the scale of this. |
139 | If a negative value is passed, |
140 | it's absolute value is used. |
141 | \param s value to set scale to. |
142 | */ |
143 | ScaleTranslate& |
144 | scale(T s) |
145 | { |
146 | m_scale = fastuidraw::t_abs(s); |
147 | return *this; |
148 | } |
149 | |
150 | /*! |
151 | Returns the value of applying the transformation to a point. |
152 | \param pt point to apply the transformation to. |
153 | */ |
154 | fastuidraw::vecN<T, 2> |
155 | apply_to_point(const fastuidraw::vecN<T, 2> &pt) const |
156 | { |
157 | return scale() * pt + translation(); |
158 | } |
159 | |
160 | /*! |
161 | Returns the value of applying the inverse of the |
162 | transformation to a point. |
163 | \param pt point to apply the transformation to. |
164 | */ |
165 | fastuidraw::vecN<T, 2> |
166 | apply_inverse_to_point(const fastuidraw::vecN<T, 2> &pt) const |
167 | { |
168 | return (pt - translation()) / scale(); |
169 | } |
170 | |
171 | /*! |
172 | Returns the transformation of this |
173 | ScaleTranslate as a 3x3 matrix |
174 | */ |
175 | fastuidraw::matrix3x3<T> |
176 | matrix3(void) const |
177 | { |
178 | fastuidraw::matrix3x3<T> M; |
179 | |
180 | M(0,0) = M(1,1) = scale(); |
181 | M(0,2) = translation().x(); |
182 | M(1,2) = translation().y(); |
183 | |
184 | return M; |
185 | } |
186 | |
187 | void |
188 | concat_to_painter(const fastuidraw::reference_counted_ptr<fastuidraw::Painter> &p) const |
189 | { |
190 | p->translate(fastuidraw::vec2(m_translation)); |
191 | p->scale(m_scale); |
192 | } |
193 | |
194 | /*! |
195 | Computes the interpolation between |
196 | two ScaleTranslate objects. |
197 | \param a0 begin value of interpolation |
198 | \param a1 end value of interpolation |
199 | \param t interpolate, t=0 returns a0, t=1 returns a1 |
200 | */ |
201 | static |
202 | ScaleTranslate |
203 | interpolate(const ScaleTranslate &a0, |
204 | const ScaleTranslate &a1, |
205 | T t) |
206 | { |
207 | ScaleTranslate R; |
208 | |
209 | R.translation( a0.translation() + t * (a1.translation()-a0.translation()) ); |
210 | R.scale( a0.scale() + t * (a1.scale() - a0.scale()) ); |
211 | return R; |
212 | } |
213 | |
214 | private: |
215 | T m_scale; |
216 | fastuidraw::vecN<T, 2> m_translation; |
217 | }; |
218 | |
219 | /*! |
220 | Compose two ScaleTranslate so that: |
221 | a*b.apply_to_point(p) "=" a.apply_to_point( b.apply_to_point(p)). |
222 | \param a left hand side of composition |
223 | \param b right hand side of composition |
224 | */ |
225 | template<typename T> |
226 | ScaleTranslate<T> |
227 | operator*(const ScaleTranslate<T> &a, const ScaleTranslate<T> &b) |
228 | { |
229 | ScaleTranslate<T> c; |
230 | |
231 | // |
232 | // c(p)= a( b(p) ) |
233 | // = a.translation + a.scale*( b.scale*p + b.translation ) |
234 | // = (a.translate + a.scale*b.translation) + (a.scale*b.scale)*p |
235 | // |
236 | //thus: |
237 | // |
238 | // c.scale=a.scale*b.scale |
239 | // c.translation= a.apply_to_point(b.translation) |
240 | c.scale( a.scale() * b.scale()); |
241 | c.translation( a.apply_to_point(b.translation()) ); |
242 | |
243 | return c; |
244 | } |
245 | |
246 | /*! @} */ |
247 | |
248 | #endif |
249 | |