Visualization Library 2.0.0

A lightweight C++ OpenGL middleware for 2D/3D graphics

VL     Star     Watch     Fork     Issue

[Download] [Tutorials] [All Classes] [Grouped Classes]
Vector2.hpp
Go to the documentation of this file.
1 /**************************************************************************************/
2 /* */
3 /* Visualization Library */
4 /* http://visualizationlibrary.org */
5 /* */
6 /* Copyright (c) 2005-2020, Michele Bosi */
7 /* All rights reserved. */
8 /* */
9 /* Redistribution and use in source and binary forms, with or without modification, */
10 /* are permitted provided that the following conditions are met: */
11 /* */
12 /* - Redistributions of source code must retain the above copyright notice, this */
13 /* list of conditions and the following disclaimer. */
14 /* */
15 /* - Redistributions in binary form must reproduce the above copyright notice, this */
16 /* list of conditions and the following disclaimer in the documentation and/or */
17 /* other materials provided with the distribution. */
18 /* */
19 /* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND */
20 /* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED */
21 /* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE */
22 /* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR */
23 /* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES */
24 /* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; */
25 /* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON */
26 /* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT */
27 /* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS */
28 /* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
29 /* */
30 /**************************************************************************************/
31 
32 #ifndef Vector2_INCLUDE_ONCE
33 #define Vector2_INCLUDE_ONCE
34 
35 #include <vlCore/OpenGLDefs.hpp>
36 #include <vlCore/std_types.hpp>
37 #include <cmath>
38 
39 #ifdef min
40 #undef min
41 #endif
42 
43 #ifdef max
44 #undef max
45 #endif
46 
47 #ifdef dot
48 #undef dot
49 #endif
50 
51 #ifdef cross
52 #undef cross
53 #endif
54 
55 namespace vl
56 {
57  // fast square root
58 
59  #if VL_FAST_SQUARE_ROOTS == 1
60  #define VL_FLOAT_SQRT(x) fast_sqrt(x)
61  #define VL_FLOAT_INVSQRT(x) fast2_inversesqrt(x)
62  #else
63  #define VL_FLOAT_SQRT(x) ((float)::sqrt(x))
64  #define VL_FLOAT_INVSQRT(x) (1.0f/(float)::sqrt(x))
65  #endif
66 
67  // fast square root functions, see Dave Eberly's paper and http://www.beyond3d.com/content/articles/8/
68 
69  inline float fast1_inversesqrt(float x)
70  {
71  float xhalf = 0.5f*x;
72  union { float f; unsigned int i; } num;
73  num.f = x;
74  num.i = 0x5f3759df - (num.i>>1);
75  x = num.f;
76  x = x*(1.5f - xhalf*x*x); // single iteration, very quick, but very poor precision
77  return x;
78  }
79  inline float fast2_inversesqrt(float x)
80  {
81  float xhalf = 0.5f*x;
82  union { float f; unsigned int i; } num;
83  num.f = x;
84  num.i = 0x5f3759df - (num.i>>1);
85  x = num.f;
86  x = x*(1.5f - xhalf*x*x);
87  x = x*(1.5f - xhalf*x*x); // two iterations, sligthtly better precision
88  return x;
89  }
90  inline float fast_sqrt(float x) { if (x == 0.0f) return 0.0f; else return x * fast2_inversesqrt(x); }
91 
96  template<typename T_Scalar>
97  class Vector2
98  {
99  public:
100  typedef T_Scalar scalar_type;
101  static const int scalar_count = 2;
102  Vector2(const Vector2& other) { *this = other; }
103  Vector2() { x() = y() = 0; }
104 
105  template<class T>
106  explicit Vector2(const T& other)
107  {
108  x() = (T_Scalar)other.x();
109  y() = (T_Scalar)other.y();
110  }
111 
112  explicit Vector2(T_Scalar val)
113  {
114  mScalar[0] = mScalar[1] = val;
115  }
116 
117  //explicit Vector2(const T_Scalar* pval)
118  //{
119  // mScalar[0] = pval[0];
120  // mScalar[1] = pval[1];
121  //}
122 
123  explicit Vector2(T_Scalar x, T_Scalar y)
124  {
125  mScalar[0] = x;
126  mScalar[1] = y;
127  }
128 
129  T_Scalar* ptr() { return mScalar; }
130  const T_Scalar* ptr() const { return mScalar; }
131 
132  const T_Scalar& x() const { return mScalar[0]; }
133  const T_Scalar& y() const { return mScalar[1]; }
134 
135  T_Scalar& x() { return mScalar[0]; }
136  T_Scalar& y() { return mScalar[1]; }
137 
138  const T_Scalar& r() const { return mScalar[0]; }
139  const T_Scalar& g() const { return mScalar[1]; }
140 
141  T_Scalar& r() { return mScalar[0]; }
142  T_Scalar& g() { return mScalar[1]; }
143 
144  const T_Scalar& s() const { return mScalar[0]; }
145  const T_Scalar& t() const { return mScalar[1]; }
146 
147  T_Scalar& s() { return mScalar[0]; }
148  T_Scalar& t() { return mScalar[1]; }
149 
150  Vector2 operator+(const Vector2& other) const
151  {
152  return Vector2(x()+other.x(), y()+other.y());
153  }
154  Vector2 operator-(const Vector2& other) const
155  {
156  return Vector2(x()-other.x(), y()-other.y());
157  }
158  Vector2 operator*(const Vector2& other) const
159  {
160  return Vector2(x()*other.x(), y()*other.y());
161  }
162  Vector2 operator/(const Vector2& other) const
163  {
164  return Vector2(x()/other.x(), y()/other.y());
165  }
166  Vector2 operator+(T_Scalar val) const
167  {
168  return Vector2(x()+val, y()+val);
169  }
170  Vector2 operator-(T_Scalar val) const
171  {
172  return Vector2(x()-val, y()-val);
173  }
174  Vector2 operator*(T_Scalar val) const
175  {
176  return Vector2(x()*val, y()*val);
177  }
178  Vector2 operator/(T_Scalar val) const
179  {
180  return Vector2(x()/val, y()/val);
181  }
183  {
184  return Vector2(-x(), -y());
185  }
186  Vector2& operator+=(const Vector2& other)
187  {
188  *this = *this + other;
189  return *this;
190  }
191  Vector2& operator-=(const Vector2& other)
192  {
193  *this = *this - other;
194  return *this;
195  }
196  Vector2& operator*=(const Vector2& other)
197  {
198  *this = *this * other;
199  return *this;
200  }
201  Vector2& operator/=(const Vector2& other)
202  {
203  *this = *this / other;
204  return *this;
205  }
206  Vector2& operator+=(T_Scalar val)
207  {
208  *this = *this + val;
209  return *this;
210  }
211  Vector2& operator-=(T_Scalar val)
212  {
213  *this = *this - val;
214  return *this;
215  }
216  Vector2& operator*=(T_Scalar val)
217  {
218  *this = *this * val;
219  return *this;
220  }
221  Vector2& operator/=(T_Scalar val)
222  {
223  *this = *this / val;
224  return *this;
225  }
226  Vector2& operator=(const Vector2& other)
227  {
228  x() = other.x();
229  y() = other.y();
230  return *this;
231  }
232  Vector2& operator=(T_Scalar val)
233  {
234  x() = y() = val;
235  return *this;
236  }
237  bool operator==(const Vector2& other) const
238  {
239  return x() == other.x() && y() == other.y();
240  }
241  bool operator!=(const Vector2& other) const
242  {
243  return !operator==(other);
244  }
245  bool operator<(const Vector2& other) const
246  {
247  if (x() != other.x())
248  return x() < other.x();
249  else
250  return y() < other.y();
251  }
252  T_Scalar& operator[](unsigned i) { return mScalar[i]; }
253  const T_Scalar& operator[](unsigned i) const { return mScalar[i]; }
254  T_Scalar length() const { return ::sqrt(x()*x()+y()*y()); }
255  T_Scalar lengthSquared() const { return x()*x()+y()*y(); }
256  bool isNull() const { return !x() && !y(); }
257  const Vector2& normalize(T_Scalar *len=NULL)
258  {
259  T_Scalar l = length();
260  if (len)
261  *len = l;
262  if (l)
263  *this *= (T_Scalar)(1.0/l);
264  return *this;
265  }
266 
267  protected:
269  };
270 
271  template<typename T>
272  inline const Vector2<T> operator*(T val, const Vector2<T>& v)
273  {
274  return v * val;
275  }
276 
293 
294  #if VL_PIPELINE_PRECISION == 2
295  typedef dvec2 vec2;
297  #else
298  typedef fvec2 vec2;
300  #endif
301 
302  inline float dot(const fvec2& v1, const fvec2& v2) { return v1.x()*v2.x() + v1.y()*v2.y(); }
303  inline double dot(const dvec2& v1, const dvec2& v2) { return v1.x()*v2.x() + v1.y()*v2.y(); }
304  inline float dot(const ivec2& v1, const ivec2& v2) { return (float)(v1.x()*v2.x() + v1.y()*v2.y()); }
305  inline float dot(const uvec2& v1, const uvec2& v2) { return (float)(v1.x()*v2.x() + v1.y()*v2.y()); }
306 
307  inline float min(float a, float b) { return a < b ? a : b; }
308  inline double min(double a, double b) { return a < b ? a : b; }
309  inline int min(int a, int b) { return a < b ? a : b; }
310  inline unsigned int min(unsigned int a, unsigned int b) { return a < b ? a : b; }
311  inline float max(float a, float b) { return a > b ? a : b; }
312  inline double max(double a, double b) { return a > b ? a : b; }
313  inline int max(int a, int b) { return a > b ? a : b; }
314  inline unsigned int max(unsigned int a, unsigned int b) { return a > b ? a : b; }
315  inline float clamp(float x, float minval, float maxval) { return min(max(x,minval),maxval); }
316  inline double clamp(double x, double minval, double maxval) { return min(max(x,minval),maxval); }
317  inline int clamp(int x, int minval, int maxval) { return min(max(x,minval),maxval); }
318  inline unsigned int clamp(unsigned int x, unsigned int minval, unsigned int maxval) { return min(max(x,minval),maxval); }
319 
320  inline fvec2 min(const fvec2& a, const fvec2& b)
321  {
322  return fvec2( a.x() < b.x() ? a.x() : b.x(),
323  a.y() < b.y() ? a.y() : b.y());
324  }
325  inline fvec2 min(const fvec2& a, float b)
326  {
327  return fvec2( a.x() < b ? a.x() : b,
328  a.y() < b ? a.y() : b);
329  }
330  inline dvec2 min(const dvec2& a, const dvec2& b)
331  {
332  return dvec2( a.x() < b.x() ? a.x() : b.x(),
333  a.y() < b.y() ? a.y() : b.y());
334  }
335  inline dvec2 min(const dvec2& a, double b)
336  {
337  return dvec2( a.x() < b ? a.x() : b,
338  a.y() < b ? a.y() : b);
339  }
340  inline ivec2 min(const ivec2& a, const ivec2& b)
341  {
342  return ivec2( a.x() < b.x() ? a.x() : b.x(),
343  a.y() < b.y() ? a.y() : b.y());
344  }
345  inline ivec2 min(const ivec2& a, int b)
346  {
347  return ivec2( a.x() < b ? a.x() : b,
348  a.y() < b ? a.y() : b);
349  }
350  inline uvec2 min(const uvec2& a, const uvec2& b)
351  {
352  return uvec2( a.x() < b.x() ? a.x() : b.x(),
353  a.y() < b.y() ? a.y() : b.y());
354  }
355  inline uvec2 min(const uvec2& a, unsigned int b)
356  {
357  return uvec2( a.x() < b ? a.x() : b,
358  a.y() < b ? a.y() : b);
359  }
360  inline fvec2 max(const fvec2& a, const fvec2& b)
361  {
362  return fvec2( a.x() > b.x() ? a.x() : b.x(),
363  a.y() > b.y() ? a.y() : b.y());
364  }
365  inline fvec2 max(const fvec2& a, float b)
366  {
367  return fvec2( a.x() > b ? a.x() : b,
368  a.y() > b ? a.y() : b);
369  }
370  inline dvec2 max(const dvec2& a, const dvec2& b)
371  {
372  return dvec2( a.x() > b.x() ? a.x() : b.x(),
373  a.y() > b.y() ? a.y() : b.y());
374  }
375  inline dvec2 max(const dvec2& a, double b)
376  {
377  return dvec2( a.x() > b ? a.x() : b,
378  a.y() > b ? a.y() : b);
379  }
380  inline ivec2 max(const ivec2& a, const ivec2& b)
381  {
382  return ivec2( a.x() > b.x() ? a.x() : b.x(),
383  a.y() > b.y() ? a.y() : b.y());
384  }
385  inline ivec2 max(const ivec2& a, int b)
386  {
387  return ivec2( a.x() > b ? a.x() : b,
388  a.y() > b ? a.y() : b);
389  }
390  inline uvec2 max(const uvec2& a, const uvec2& b)
391  {
392  return uvec2( a.x() > b.x() ? a.x() : b.x(),
393  a.y() > b.y() ? a.y() : b.y());
394  }
395  inline uvec2 max(const uvec2& a, unsigned int b)
396  {
397  return uvec2( a.x() > b ? a.x() : b,
398  a.y() > b ? a.y() : b);
399  }
400  inline fvec2 clamp(const fvec2& x, float minval, float maxval) { return min(max(x,minval),maxval); }
401  inline fvec2 clamp(const fvec2& x, const fvec2& minval, const fvec2& maxval) { return min(max(x,minval),maxval); }
402  inline dvec2 clamp(const dvec2& x, double minval, double maxval) { return min(max(x,minval),maxval); }
403  inline dvec2 clamp(const dvec2& x, const dvec2& minval, const dvec2& maxval) { return min(max(x,minval),maxval); }
404  inline ivec2 clamp(const ivec2& x, int minval, int maxval) { return min(max(x,minval),maxval); }
405  inline ivec2 clamp(const ivec2& x, const ivec2& minval, const ivec2& maxval) { return min(max(x,minval),maxval); }
406  inline uvec2 clamp(const uvec2& x, unsigned int minval, unsigned int maxval) { return min(max(x,minval),maxval); }
407  inline uvec2 clamp(const uvec2& x, const uvec2& minval, const uvec2& maxval) { return min(max(x,minval),maxval); }
408 }
409 
410 #endif
Vector2 operator-(T_Scalar val) const
Definition: Vector2.hpp:170
float clamp(float x, float minval, float maxval)
Definition: Vector2.hpp:315
Vector2< int > ivec2
A 2 components vector with int precision.
Definition: Vector2.hpp:278
const T_Scalar & t() const
Definition: Vector2.hpp:145
Vector2 & operator*=(const Vector2 &other)
Definition: Vector2.hpp:196
Vector2(T_Scalar x, T_Scalar y)
Definition: Vector2.hpp:123
Vector2< double > dvec2
A 2 components vector with double precision.
Definition: Vector2.hpp:284
T sqrt(T a)
Definition: glsl_math.hpp:592
const T_Scalar & g() const
Definition: Vector2.hpp:139
fvec2 vec2
Defined as: &#39;typedef fvec2 vec2&#39;. See also VL_PIPELINE_PRECISION.
Definition: Vector2.hpp:299
static const int scalar_count
Definition: Vector2.hpp:101
T_Scalar & operator[](unsigned i)
Definition: Vector2.hpp:252
Vector2< unsigned int > uvec2
A 2 components vector with unsigned int precision.
Definition: Vector2.hpp:280
T_Scalar mScalar[scalar_count]
Definition: Vector2.hpp:268
const T_Scalar & s() const
Definition: Vector2.hpp:144
Vector2 operator-() const
Definition: Vector2.hpp:182
const Vector2 & normalize(T_Scalar *len=NULL)
Definition: Vector2.hpp:257
T_Scalar lengthSquared() const
Definition: Vector2.hpp:255
T_Scalar & g()
Definition: Vector2.hpp:142
Vector2 operator-(const Vector2 &other) const
Definition: Vector2.hpp:154
T_Scalar & x()
Definition: Vector2.hpp:135
Vector2(T_Scalar val)
Definition: Vector2.hpp:112
Vector2 & operator-=(T_Scalar val)
Definition: Vector2.hpp:211
Vector2 operator+(T_Scalar val) const
Definition: Vector2.hpp:166
Vector2 operator*(T_Scalar val) const
Definition: Vector2.hpp:174
Vector2(const Vector2 &other)
Definition: Vector2.hpp:102
Vector2(const T &other)
Definition: Vector2.hpp:106
Vector2 operator*(const Vector2 &other) const
Definition: Vector2.hpp:158
Vector2 & operator-=(const Vector2 &other)
Definition: Vector2.hpp:191
Visualization Library main namespace.
float dot(float a, float b)
Definition: glsl_math.hpp:1111
T_Scalar * ptr()
Definition: Vector2.hpp:129
Vector2< float > fvec2
A 2 components vector with float precision.
Definition: Vector2.hpp:282
Vector2 & operator/=(const Vector2 &other)
Definition: Vector2.hpp:201
T_Scalar length() const
Definition: Vector2.hpp:254
Vector2< unsigned char > ubvec2
A 2 components vector with unsigned char precision.
Definition: Vector2.hpp:288
bool operator==(const Vector2 &other) const
Definition: Vector2.hpp:237
const T_Scalar & r() const
Definition: Vector2.hpp:138
const T_Scalar & operator[](unsigned i) const
Definition: Vector2.hpp:253
bool operator<(const Vector2 &other) const
Definition: Vector2.hpp:245
float max(float a, float b)
Definition: Vector2.hpp:311
float min(float a, float b)
Definition: Vector2.hpp:307
T_Scalar & t()
Definition: Vector2.hpp:148
Vector2 & operator=(T_Scalar val)
Definition: Vector2.hpp:232
float fast1_inversesqrt(float x)
Definition: Vector2.hpp:69
T_Scalar & y()
Definition: Vector2.hpp:136
#define NULL
Definition: OpenGLDefs.hpp:81
Vector2 & operator+=(T_Scalar val)
Definition: Vector2.hpp:206
Vector2 & operator=(const Vector2 &other)
Definition: Vector2.hpp:226
Vector2< char > bvec2
A 2 components vector with char precision.
Definition: Vector2.hpp:286
float fast2_inversesqrt(float x)
Definition: Vector2.hpp:79
bool isNull() const
Definition: Vector2.hpp:256
The Vector2 class is a template class that implements a generic 2 components vector, see also vl::fvec2, vl::dvec2, vl::uvec2, vl::ivec2, vl::svec2, vl::usvec2, vl::bvec2, vl::ubvec2.
Definition: Vector2.hpp:97
Vector2< short > svec2
A 2 components vector with short precision.
Definition: Vector2.hpp:290
T_Scalar & s()
Definition: Vector2.hpp:147
T_Scalar & r()
Definition: Vector2.hpp:141
Vector2 operator+(const Vector2 &other) const
Definition: Vector2.hpp:150
Vector2 & operator+=(const Vector2 &other)
Definition: Vector2.hpp:186
Vector2 operator/(const Vector2 &other) const
Definition: Vector2.hpp:162
Vector2< unsigned short > usvec2
A 2 components vector with unsigned short precision.
Definition: Vector2.hpp:292
Vector2 operator/(T_Scalar val) const
Definition: Vector2.hpp:178
const T_Scalar & x() const
Definition: Vector2.hpp:132
bool operator!=(const Vector2 &other) const
Definition: Vector2.hpp:241
Vector2 & operator/=(T_Scalar val)
Definition: Vector2.hpp:221
const T_Scalar & y() const
Definition: Vector2.hpp:133
T_Scalar scalar_type
Definition: Vector2.hpp:100
Vector2 & operator*=(T_Scalar val)
Definition: Vector2.hpp:216
const T_Scalar * ptr() const
Definition: Vector2.hpp:130
float fast_sqrt(float x)
Definition: Vector2.hpp:90