[ VIGRA Homepage | Function Index | Class Index | Namespaces | File List | Main Page ]

diff2d.hxx VIGRA

1 /************************************************************************/
2 /* */
3 /* Copyright 1998-2003 by Hans Meine */
4 /* */
5 /* This file is part of the VIGRA computer vision library. */
6 /* The VIGRA Website is */
7 /* http://hci.iwr.uni-heidelberg.de/vigra/ */
8 /* Please direct questions, bug reports, and contributions to */
9 /* ullrich.koethe@iwr.uni-heidelberg.de or */
10 /* vigra@informatik.uni-hamburg.de */
11 /* */
12 /* Permission is hereby granted, free of charge, to any person */
13 /* obtaining a copy of this software and associated documentation */
14 /* files (the "Software"), to deal in the Software without */
15 /* restriction, including without limitation the rights to use, */
16 /* copy, modify, merge, publish, distribute, sublicense, and/or */
17 /* sell copies of the Software, and to permit persons to whom the */
18 /* Software is furnished to do so, subject to the following */
19 /* conditions: */
20 /* */
21 /* The above copyright notice and this permission notice shall be */
22 /* included in all copies or substantial portions of the */
23 /* Software. */
24 /* */
25 /* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND */
26 /* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES */
27 /* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND */
28 /* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT */
29 /* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, */
30 /* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING */
31 /* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR */
32 /* OTHER DEALINGS IN THE SOFTWARE. */
33 /* */
34 /************************************************************************/
35 
36 #ifndef VIGRA_DIFF2D_HXX
37 #define VIGRA_DIFF2D_HXX
38 
39 #include <cmath> // for sqrt()
40 #include <iosfwd>
41 #include "config.hxx"
42 #include "iteratortags.hxx"
43 #include "iteratortraits.hxx"
44 #include "iteratoradapter.hxx"
45 #include "tuple.hxx"
46 
47 
48 namespace vigra {
49 
50 
51 template <class Diff>
52 class Diff2DConstRowIteratorPolicy
53 {
54  public:
55  typedef Diff BaseType;
56  typedef Diff value_type;
57  typedef typename Diff::MoveX difference_type;
58  typedef Diff const & reference;
59  typedef Diff index_reference;
60  typedef Diff const * pointer;
61  typedef std::random_access_iterator_tag iterator_category;
62 
63  static void initialize(BaseType &) {}
64 
65  static reference dereference(BaseType const & d)
66  { return d; }
67 
68  static index_reference dereference(BaseType d, difference_type n)
69  {
70  d.x += n;
71  return d;
72  }
73 
74  static bool equal(BaseType const & d1, BaseType const & d2)
75  { return d1.x == d2.x; }
76 
77  static bool less(BaseType const & d1, BaseType const & d2)
78  { return d1.x < d2.x; }
79 
80  static difference_type difference(BaseType const & d1, BaseType const & d2)
81  { return d1.x - d2.x; }
82 
83  static void increment(BaseType & d)
84  { ++d.x; }
85 
86  static void decrement(BaseType & d)
87  { --d.x; }
88 
89  static void advance(BaseType & d, difference_type n)
90  { d.x += n; }
91 };
92 
93 template <class Diff>
94 class Diff2DConstColumnIteratorPolicy
95 {
96  public:
97  typedef Diff BaseType;
98  typedef Diff value_type;
99  typedef typename Diff::MoveY difference_type;
100  typedef Diff const & reference;
101  typedef Diff index_reference;
102  typedef Diff const * pointer;
103  typedef std::random_access_iterator_tag iterator_category;
104 
105  static void initialize(BaseType & /*d*/) {}
106 
107  static reference dereference(BaseType const & d)
108  { return d; }
109 
110  static index_reference dereference(BaseType d, difference_type n)
111  {
112  d.y += n;
113  return d;
114  }
115 
116  static bool equal(BaseType const & d1, BaseType const & d2)
117  { return d1.y == d2.y; }
118 
119  static bool less(BaseType const & d1, BaseType const & d2)
120  { return d1.y < d2.y; }
121 
122  static difference_type difference(BaseType const & d1, BaseType const & d2)
123  { return d1.y - d2.y; }
124 
125  static void increment(BaseType & d)
126  { ++d.y; }
127 
128  static void decrement(BaseType & d)
129  { --d.y; }
130 
131  static void advance(BaseType & d, difference_type n)
132  { d.y += n; }
133 };
134 
135 /** \addtogroup RangesAndPoints Ranges and Points
136 
137  Specify 2-D and N-D positions, extents, and boxes.
138 */
139 //@{
140 
141 /********************************************************/
142 /* */
143 /* Diff2D */
144 /* */
145 /********************************************************/
146 
147 /** \brief Two dimensional difference vector.
148 
149  This class acts primarily as a difference vector for specifying
150  pixel coordinates and region sizes. In addition, Diff2D fulfills
151  the requirements of an \ref ImageIterator, so that it can be used to
152  simulate an image whose pixels' values equal their coordinates. This
153  secondary usage is explained on page \ref CoordinateIterator.
154 
155  Standard usage as a difference vector is mainly needed in the context
156  of images. For example, Diff2D may be used as an index for <TT>operator[]</TT>:
157 
158  \code
159  vigra::Diff2D location(...);
160 
161  value = image[location];
162  \endcode
163 
164  This is especially important in connection with accessors, where the
165  offset variant of <TT>operator()</TT> takes only one offset object:
166 
167  \code
168  // accessor(iterator, dx, dy); is not allowed
169  value = accessor(iterator, vigra::Diff2D(dx, dy));
170  \endcode
171 
172 
173  Diff2D is also returned by <TT>image.size()</TT>, so that we can create
174  new images by calculating their size using Diff2D's arithmetic
175  functions:
176 
177  \code
178  // create an image that is 10 pixels smaller in each direction
179  Image new_image(old_image.size() - Diff2D(10,10));
180  \endcode
181 
182  <b>\#include</b> <vigra/diff2d.hxx><br>
183  Namespace: vigra
184 */
185 class Diff2D
186 {
187  public:
188  /** The iterator's value type: a coordinate.
189  */
190  typedef Diff2D PixelType;
191 
192  /** The iterator's value type: a coordinate.
193  */
195 
196  /** the iterator's reference type (return type of <TT>*iter</TT>)
197  */
198  typedef Diff2D const & reference;
199 
200  /** the iterator's index reference type (return type of <TT>iter[diff]</TT>)
201  */
203 
204  /** the iterator's pointer type (return type of <TT>iter.operator->()</TT>)
205  */
206  typedef Diff2D const * pointer;
207 
208  /** the iterator's difference type (argument type of <TT>iter[diff]</TT>)
209  */
211 
212  /** the iterator tag (image traverser)
213  */
214  typedef image_traverser_tag iterator_category;
215 
216  /** The associated row iterator.
217  */
219 
220  /** The associated column iterator.
221  */
223 
224  /** type of the iterator's x-navigator
225  */
226  typedef int MoveX;
227  /** type of the iterator's y-navigator
228  */
229  typedef int MoveY;
230 
231 
232  /** Default Constructor. Init iterator at position (0,0)
233  */
235  : x(0), y(0)
236  {}
237 
238  /** Construct at given position.
239  */
240  Diff2D(int ax, int ay)
241  : x(ax), y(ay)
242  {}
243 
244  /** Copy Constructor.
245  */
246  Diff2D(Diff2D const & v)
247  : x(v.x), y(v.y)
248  {}
249 
250  /** Copy Assigment.
251  */
252  Diff2D & operator=(Diff2D const & v)
253  {
254  if(this != &v)
255  {
256  x = v.x;
257  y = v.y;
258  }
259  return *this;
260  }
261 
262  /** Unary negation.
263  */
265  {
266  return Diff2D(-x, -y);
267  }
268 
269  /** Increase coordinate by specified offset.
270  */
271  Diff2D & operator+=(Diff2D const & offset)
272  {
273  x += offset.x;
274  y += offset.y;
275  return *this;
276  }
277 
278  /** Decrease coordinate by specified vector.
279  */
280  Diff2D & operator-=(Diff2D const & offset)
281  {
282  x -= offset.x;
283  y -= offset.y;
284  return *this;
285  }
286 
287  /** Create vector by scaling by factor.
288  */
289  Diff2D & operator*=(int factor)
290  {
291  x *= factor;
292  y *= factor;
293  return *this;
294  }
295 
296  /** Create vector by scaling by factor.
297  */
298  Diff2D & operator*=(double factor)
299  {
300  x = (int)(x * factor);
301  y = (int)(y * factor);
302  return *this;
303  }
304 
305  /** Create vector by scaling by 1/factor.
306  */
307  Diff2D & operator/=(int factor)
308  {
309  x /= factor;
310  y /= factor;
311  return *this;
312  }
313 
314  /** Create vector by scaling by 1/factor.
315  */
316  Diff2D & operator/=(double factor)
317  {
318  x = (int)(x / factor);
319  y = (int)(y / factor);
320  return *this;
321  }
322 
323  /** Create vector by scaling by factor.
324  */
325  Diff2D operator*(int factor) const
326  {
327  return Diff2D(x * factor, y * factor);
328  }
329 
330  /** Create vector by scaling by factor.
331  */
332  Diff2D operator*(double factor) const
333  {
334  return Diff2D((int)(x * factor), (int)(y * factor));
335  }
336 
337  /** Create vector by scaling by 1/factor.
338  */
339  Diff2D operator/(int factor) const
340  {
341  return Diff2D(x / factor, y / factor);
342  }
343 
344  /** Create vector by scaling by 1/factor.
345  */
346  Diff2D operator/(double factor) const
347  {
348  return Diff2D((int)(x / factor), (int)(y / factor));
349  }
350 
351  /** Calculate length of difference vector.
352  */
353  int squaredMagnitude() const
354  {
355  return x*x + y*y;
356  }
357 
358  /** Calculate length of difference vector.
359  */
360  double magnitude() const
361  {
362  return VIGRA_CSTD::sqrt((double)squaredMagnitude());
363  }
364 
365  /** Equality.
366  */
367  bool operator==(Diff2D const & r) const
368  {
369  return (x == r.x) && (y == r.y);
370  }
371 
372  /** Inequality.
373  */
374  bool operator!=(Diff2D const & r) const
375  {
376  return (x != r.x) || (y != r.y);
377  }
378 
379  /** Used for both access to the current x-coordinate \em and
380  to specify that an iterator navigation command is to be
381  applied in x-direction. <br>
382  usage: <TT> x = diff2d.x </TT> (use \p Diff2D::x as component of difference vector) <br>
383  or <TT>&nbsp; ++diff.x &nbsp; </TT> (use Diff2D as iterator, move right)
384  */
385  int x;
386  /** Used for both access to the current y-coordinate \em and
387  to specify that an iterator navigation command is to be
388  applied in y-direction. <br>
389  usage: <TT> y = diff2d.y </TT> (use \p Diff2D::y as component of difference vector) <br>
390  or <TT>&nbsp; ++diff.y &nbsp; </TT> (use Diff2D as iterator, move right)
391  */
392  int y;
393 
394  /** Access current coordinate.
395  */
397  {
398  return *this;
399  }
400 
401  /** Read coordinate at an offset.
402  */
403  index_reference operator()(int const & dx, int const & dy) const
404  {
405  return Diff2D(x + dx, y + dy);
406  }
407 
408  /** Read coordinate at an offset.
409  */
410  index_reference operator[](Diff2D const & offset) const
411  {
412  return Diff2D(x + offset.x, y + offset.y);
413  }
414 
415  /** Read vector components.
416  */
417  int operator[](int index) const
418  {
419  return (&x)[index];
420  }
421 
422  /** Access current coordinate.
423  */
425  {
426  return this;
427  }
428 
429  /** Get a row iterator at the current position.
430  */
432  { return row_iterator(*this); }
433 
434  /** Get a column iterator at the current position.
435  */
437  { return column_iterator(*this); }
438 };
439 
440 
441 template <>
442 struct IteratorTraits<Diff2D >
443 {
444  typedef Diff2D Iterator;
445  typedef Iterator iterator;
446  typedef Iterator const_iterator;
447  // typedef multable_iterator; undefined
448  typedef iterator::iterator_category iterator_category;
449  typedef iterator::value_type value_type;
450  typedef iterator::reference reference;
451  typedef iterator::index_reference index_reference;
452  typedef iterator::pointer pointer;
453  typedef iterator::difference_type difference_type;
454  typedef iterator::row_iterator row_iterator;
455  typedef iterator::column_iterator column_iterator;
456  typedef StandardConstValueAccessor<Diff2D> DefaultAccessor;
457  typedef StandardConstValueAccessor<Diff2D> default_accessor;
458  typedef VigraTrueType hasConstantStrides;
459 
460 };
461 
462 /********************************************************/
463 /* */
464 /* Size2D */
465 /* */
466 /********************************************************/
467 
468 /** \brief Two dimensional size object.
469 
470  Specializes \ref Diff2D for the specification of a 2-dimensional
471  extent, in contrast to a point or position (for the latter
472  use \ref Point2D).
473 
474  \code
475  // create an image that is 10 pixels squared
476  Image new_image(Size2D(10,10));
477  \endcode
478 
479  <b>\#include</b> <vigra/diff2d.hxx><br>
480  Namespace: vigra
481 */
482 class Size2D : public Diff2D
483 {
484 public:
485  /** Default Constructor. Init point at position (0,0)
486  */
488  {}
489 
490  /** Construct point at given position.
491  */
492  Size2D(int width, int height)
493  : Diff2D(width, height)
494  {}
495 
496  /** Copy Constructor.
497  */
498  Size2D(Size2D const & v)
499  : Diff2D(v)
500  {}
501 
502  /** Explicit conversion Constructor.
503  */
504  explicit Size2D(Diff2D const & v)
505  : Diff2D(v)
506  {}
507 
508  /** Query the width.
509  */
510  int width() const
511  {
512  return x;
513  }
514 
515  /** Query the height.
516  */
517  int height() const
518  {
519  return y;
520  }
521 
522  /** Change the width.
523  */
524  void setWidth(int w)
525  {
526  x = w;
527  }
528 
529  /** Change the height.
530  */
531  void setHeight(int h)
532  {
533  y = h;
534  }
535 
536  /** Returns width()*height(), the area of a rectangle of this size.
537  */
538  int area() const
539  {
540  return width()*height();
541  }
542 
543  /** Copy Assigment.
544  */
545  Size2D & operator=(Diff2D const & v)
546  {
547  return static_cast<Size2D &>(Diff2D::operator=(v));
548  }
549 
550  /** Unary negation.
551  */
553  {
554  return Size2D(-x, -y);
555  }
556 
557  /** Increase size by specified offset.
558  */
559  Size2D & operator+=(Diff2D const & offset)
560  {
561  return static_cast<Size2D &>(Diff2D::operator+=(offset));
562  }
563 
564  /** Decrease size by specified offset.
565  */
566  Size2D & operator-=(Diff2D const & offset)
567  {
568  return static_cast<Size2D &>(Diff2D::operator-=(offset));
569  }
570 };
571 
572 /********************************************************/
573 /* */
574 /* Point2D */
575 /* */
576 /********************************************************/
577 
578 /** \brief Two dimensional point or position.
579 
580  Specializes \ref Diff2D for the specification of a 2-dimensional
581  point or position, in contrast to an extent (for the latter
582  use \ref Size2D).
583 
584  \code
585  // access an image at a point
586  value = image[Point2D(10, 20)];
587  \endcode
588 
589  <b>\#include</b> <vigra/diff2d.hxx><br>
590  Namespace: vigra
591 */
592 class Point2D : public Diff2D
593 {
594 public:
595  /** The iterator's value type: a coordinate.
596  */
598 
599  /** The iterator's value type: a coordinate.
600  */
602 
603  /** the iterator's reference type (return type of <TT>*iter</TT>)
604  */
605  typedef Point2D const & reference;
606 
607  /** the iterator's index reference type (return type of <TT>iter[diff]</TT>)
608  */
610 
611  /** the iterator's pointer type (return type of <TT>iter.operator->()</TT>)
612  */
613  typedef Point2D const * pointer;
614 
615  /** Default Constructor. Init point at position (0,0)
616  */
618  {}
619 
620  /** Construct point at given position.
621  */
622  Point2D(int x, int y)
623  : Diff2D(x, y)
624  {}
625 
626  /** Copy Constructor.
627  */
628  Point2D(Point2D const & v)
629  : Diff2D(v)
630  {}
631 
632  /** Explicit conversion Constructor.
633  */
634  explicit Point2D(Diff2D const & v)
635  : Diff2D(v)
636  {}
637 
638  /** Query the points' x coordinate
639  */
640  int px() const
641  {
642  return x;
643  }
644 
645  /** Query the points' y coordinate
646  */
647  int py() const
648  {
649  return y;
650  }
651 
652  /** Copy Assigment.
653  */
654  Point2D & operator=(Diff2D const & v)
655  {
656  return static_cast<Point2D &>(Diff2D::operator=(v));
657  }
658 
659  /** Unary negation.
660  */
662  {
663  return Point2D(-x, -y);
664  }
665 
666  /** Increase point coordinates by specified offset.
667  */
668  Point2D & operator+=(Diff2D const & offset)
669  {
670  return static_cast<Point2D &>(Diff2D::operator+=(offset));
671  }
672 
673  /** Decrease point coordinates by specified offset.
674  */
675  Point2D & operator-=(Diff2D const & offset)
676  {
677  return static_cast<Point2D &>(Diff2D::operator-=(offset));
678  }
679 
680  /** Access current point coordinate.
681  */
683  {
684  return *this;
685  }
686 
687  /** Read point coordinate at an offset.
688  */
689  index_reference operator()(int const & dx, int const & dy) const
690  {
691  return Point2D(x + dx, y + dy);
692  }
693 
694  /** Read point coordinate at an offset.
695  */
696  index_reference operator[](Diff2D const & offset) const
697  {
698  return Point2D(x + offset.x, y + offset.y);
699  }
700 
701  /** Access current point coordinate.
702  */
704  {
705  return this;
706  }
707 };
708 
709 /** Create vector by subtracting specified offset.
710  */
711 inline Diff2D operator-(Diff2D const &a, Diff2D const &b)
712 {
713  return Diff2D(a.x - b.x, a.y - b.y);
714 }
715 
716 /** Create size by subtracting specified offset.
717  */
718 inline Size2D operator-(Size2D const & s, Diff2D const &offset)
719 {
720  return Size2D(s.x - offset.x, s.y - offset.y);
721 }
722 
723 /** Calculate size of rect between two points.
724  */
725 inline Point2D operator-(Point2D const & s, Diff2D const & offset)
726 {
727  return Point2D(s.x - offset.x, s.y - offset.y);
728 }
729 
730 /** The difference of two points is a size
731  */
732 inline Size2D operator-(Point2D const & s, Point2D const & p)
733 {
734  return Size2D(s.x - p.x, s.y - p.y);
735 }
736 
737 /** Create vector by adding specified offset.
738  */
739 inline Diff2D operator+(Diff2D const &a, Diff2D const &b)
740 {
741  return Diff2D(a.x + b.x, a.y + b.y);
742 }
743 
744 /** Create size by adding specified offset.
745  */
746 inline Size2D operator+(Size2D const &a, Diff2D const &b)
747 {
748  return Size2D(a.x + b.x, a.y + b.y);
749 }
750 
751 /** Create point by adding specified offset.
752  */
753 inline Point2D operator+(Point2D const &a, Diff2D const &b)
754 {
755  return Point2D(a.x + b.x, a.y + b.y);
756 }
757 
758 /** Add size and point
759  */
760 inline Point2D operator+(Size2D const & s, Point2D const & p)
761 {
762  return Point2D(s.x + p.x, s.y + p.y);
763 }
764 
765 inline Point2D operator*(Point2D l, double r)
766 {
767  l *= r;
768  return l;
769 }
770 
771 inline Point2D operator*(double l, Point2D r)
772 {
773  r *= l;
774  return r;
775 }
776 
777 inline Size2D operator*(Size2D l, double r)
778 {
779  l *= r;
780  return l;
781 }
782 
783 inline Size2D operator*(double l, Size2D r)
784 {
785  r *= l;
786  return r;
787 }
788 
789 inline Point2D operator/(Point2D l, double r)
790 {
791  l /= r;
792  return l;
793 }
794 
795 inline Size2D operator/(Size2D l, double r)
796 {
797  l /= r;
798  return l;
799 }
800 
801 inline Point2D operator*(Point2D l, int r)
802 {
803  l *= r;
804  return l;
805 }
806 
807 inline Point2D operator*(int l, Point2D r)
808 {
809  r *= l;
810  return r;
811 }
812 
813 inline Size2D operator*(Size2D l, int r)
814 {
815  l *= r;
816  return l;
817 }
818 
819 inline Size2D operator*(int l, Size2D r)
820 {
821  r *= l;
822  return r;
823 }
824 
825 inline Point2D operator/(Point2D l, int r)
826 {
827  l /= r;
828  return l;
829 }
830 
831 inline Size2D operator/(Size2D l, int r)
832 {
833  l /= r;
834  return l;
835 }
836 
837 
838 /********************************************************/
839 /* */
840 /* Rect2D */
841 /* */
842 /********************************************************/
843 
844 /** \brief Two dimensional rectangle.
845 
846  This class stores a 2-dimensional rectangular range or region. Thus,
847  it follows the VIGRA convention that the upper left corner is inside
848  the rectangle, while the lower right is 1 pixel to the right and below the
849  last pixel in the rectangle.
850 
851  A major advantage of this class is that it can be constructed from either
852  a pair of \ref Point2D, or from a \ref Point2D and an extend
853  (\ref Size2D). Rect2D overloads operators |=, &=, |, & to realize set
854  union (in the sense of a minimal bounding rectangle) and set intersection.
855 
856  \code
857  Rect2D r1(Point2D(0,0), Point2D(10, 20)),
858  r2(Point2D(10, 15), Size2D(20, 20));
859  Point2D p(0,100);
860 
861  Rect2D r3 = r1 | r2; // upper left is (0,0), lower right is (30, 35)
862  assert(r3.contains(r2));
863  assert(!r3.contains(p));
864 
865  r3 |= p; // lower right now (30,101) so that p is inside r3
866  assert(r3.contains(p));
867  \endcode
868 
869  <b>\#include</b> <vigra/diff2d.hxx><br>
870  Namespace: vigra
871 */
872 class Rect2D
873 {
874  Point2D upperLeft_, lowerRight_;
875 
876 public:
877  /** Construct a null rectangle (isEmpty() will return true)
878  */
880  {}
881 
882  /** Construct a rectangle representing the given range
883  * (lowerRight is considered to be outside the rectangle as
884  * usual in the VIGRA)
885  */
887  : upperLeft_(upperLeft), lowerRight_(lowerRight)
888  {}
889 
890  /** Construct a rectangle representing the given range
891  */
892  Rect2D(int left, int top, int right, int bottom)
893  : upperLeft_(left, top), lowerRight_(right, bottom)
894  {}
895 
896  /** Construct a rectangle of given position and size
897  */
899  : upperLeft_(upperLeft), lowerRight_(upperLeft + size)
900  {}
901 
902  /** Construct a rectangle of given size at position (0,0)
903  */
904  explicit Rect2D(Size2D const &size)
905  : lowerRight_(Point2D(size))
906  {}
907 
908  /** Return the first point (scan-order wise) which is
909  * considered to be "in" the rectangle.
910  */
911  Point2D const & upperLeft() const
912  {
913  return upperLeft_;
914  }
915 
916  /** Return the first point to the right and below the
917  * rectangle.
918  */
919  Point2D const & lowerRight() const
920  {
921  return lowerRight_;
922  }
923 
924  /** Change upperLeft() without changing lowerRight(), which
925  * will change the size most probably.
926  */
927  void setUpperLeft(Point2D const &ul)
928  {
929  upperLeft_ = ul;
930  }
931 
932  /** Change lowerRight() without changing upperLeft(), which
933  * will change the size most probably.
934  */
935  void setLowerRight(Point2D const &lr)
936  {
937  lowerRight_ = lr;
938  }
939 
940  /** Move the whole rectangle so that the given point will be
941  * upperLeft() afterwards.
942  */
943  void moveTo(Point2D const &newUpperLeft)
944  {
945  lowerRight_ += newUpperLeft - upperLeft_;
946  upperLeft_ = newUpperLeft;
947  }
948 
949  /** Move the whole rectangle so that upperLeft() will become
950  * Point2D(left, top) afterwards.
951  */
952  void moveTo(int left, int top)
953  {
954  moveTo(Point2D(left, top));
955  }
956 
957  /** Move the whole rectangle by the given 2D offset.
958  */
959  void moveBy(Diff2D const &offset)
960  {
961  upperLeft_ += offset;
962  lowerRight_ += offset;
963  }
964 
965  /** Move the whole rectangle by the given x- and y-offsets.
966  */
967  void moveBy(int xOffset, int yOffset)
968  {
969  moveBy(Diff2D(xOffset, yOffset));
970  }
971 
972  /** Return the left coordinate of this rectangle.
973  */
974  int left() const
975  {
976  return upperLeft_.x;
977  }
978 
979  /** Return the top coordinate of this rectangle.
980  */
981  int top() const
982  {
983  return upperLeft_.y;
984  }
985 
986  /** Return the right coordinate of this rectangle. That is the
987  * first column to the right of the rectangle.
988  */
989  int right() const
990  {
991  return lowerRight_.x;
992  }
993 
994  /** Return the bottom coordinate of this rectangle. That is the
995  * first row below the rectangle.
996  */
997  int bottom() const
998  {
999  return lowerRight_.y;
1000  }
1001 
1002  /** Determine and return the width of this rectangle. It might be
1003  * zero or even negative, and if so, isEmpty() will return true.
1004  */
1005  int width() const
1006  {
1007  return lowerRight_.x - upperLeft_.x;
1008  }
1009 
1010  /** Determine and return the height of this rectangle. It might be
1011  * zero or even negative, and if so, isEmpty() will return true.
1012  */
1013  int height() const
1014  {
1015  return lowerRight_.y - upperLeft_.y;
1016  }
1017 
1018  /** Determine and return the area of this rectangle. That is, if
1019  * this rect isEmpty(), returns zero, otherwise returns
1020  * width()*height().
1021  */
1022  int area() const
1023  {
1024  return isEmpty() ? 0 : width()*height();
1025  }
1026 
1027  /** Determine and return the size of this rectangle. The width
1028  * and/or height might be zero or even negative, and if so,
1029  * isEmpty() will return true.
1030  */
1031  Size2D size() const
1032  {
1033  return lowerRight_ - upperLeft_;
1034  }
1035 
1036  /** Resize this rectangle to the given extents. This will move
1037  * the lower right corner only.
1038  */
1039  void setSize(Size2D const &size)
1040  {
1041  lowerRight_ = upperLeft_ + size;
1042  }
1043 
1044  /** Resize this rectangle to the given extents. This will move
1045  * the lower right corner only.
1046  */
1047  void setSize(int width, int height)
1048  {
1049  lowerRight_ = upperLeft_ + Size2D(width, height);
1050  }
1051 
1052  /** Increase the size of the rectangle by the given offset. This
1053  * will move the lower right corner only. (If any of offset's
1054  * components is negative, the rectangle will get smaller
1055  * accordingly.)
1056  */
1057  void addSize(Size2D const &offset)
1058  {
1059  lowerRight_ += offset;
1060  }
1061 
1062  /** Adds a border of the given width around the rectangle. That
1063  * means, upperLeft()'s components are moved by -borderWidth
1064  * and lowerRight()'s by borderWidth. (If borderWidth is
1065  * negative, the rectangle will get smaller accordingly.)
1066  */
1067  void addBorder(int borderWidth)
1068  {
1069  upperLeft_ += Diff2D(-borderWidth, -borderWidth);
1070  lowerRight_ += Diff2D(borderWidth, borderWidth);
1071  }
1072 
1073  /** Adds a border with possibly different widths in x- and
1074  * y-directions around the rectangle. That means, each x
1075  * component is moved borderWidth pixels and each y component
1076  * is moved borderHeight pixels to the outside. (If
1077  * borderWidth is negative, the rectangle will get smaller
1078  * accordingly.)
1079  */
1080  void addBorder(int borderWidth, int borderHeight)
1081  {
1082  upperLeft_ += Diff2D(-borderWidth, -borderHeight);
1083  lowerRight_ += Diff2D(borderWidth, borderHeight);
1084  }
1085 
1086  /// equality check
1087  bool operator==(Rect2D const &r) const
1088  {
1089  return (upperLeft_ == r.upperLeft_) && (lowerRight_ == r.lowerRight_);
1090  }
1091 
1092  /// inequality check
1093  bool operator!=(Rect2D const &r) const
1094  {
1095  return (upperLeft_ != r.upperLeft_) || (lowerRight_ != r.lowerRight_);
1096  }
1097 
1098  /** Return whether this rectangle is considered empty. It is
1099  * non-empty if both coordinates of the lower right corner are
1100  * greater than the corresponding coordinate of the upper left
1101  * corner. Uniting an empty rectangle with something will return
1102  * the bounding rectangle of the 'something', intersecting with an
1103  * empty rectangle will yield again an empty rectangle.
1104  */
1105  bool isEmpty() const
1106  {
1107  return ((lowerRight_.x <= upperLeft_.x) ||
1108  (lowerRight_.y <= upperLeft_.y));
1109  }
1110 
1111  /** Return whether this rectangle contains the given point. That
1112  * is, if the point lies within the valid range of an
1113  * ImageIterator walking from upperLeft() to lowerRight()
1114  * (excluding the latter).
1115  */
1116  bool contains(Point2D const &p) const
1117  {
1118  return ((upperLeft_.x <= p.x) &&
1119  (upperLeft_.y <= p.y) &&
1120  (p.x < lowerRight_.x) &&
1121  (p.y < lowerRight_.y));
1122  }
1123 
1124  /** Return whether this rectangle contains the given
1125  * one. <tt>r1.contains(r2)</tt> returns the same as
1126  * <tt>r1 == (r1|r2)</tt> (but is of course more
1127  * efficient). That also means, a rectangle (even an empty one!)
1128  * contains() any empty rectangle.
1129  */
1130  bool contains(Rect2D const &r) const
1131  {
1132  return r.isEmpty() ||
1133  (contains(r.upperLeft()) && contains(r.lowerRight()-Diff2D(1,1)));
1134  }
1135 
1136  /** Return whether this rectangle overlaps with the given
1137  * one. <tt>r1.intersects(r2)</tt> returns the same as
1138  * <tt>!(r1&r2).isEmpty()</tt> (but is of course much more
1139  * efficient).
1140  */
1141  bool intersects(Rect2D const &r) const
1142  {
1143  return ((r.upperLeft_.x < lowerRight_.x) &&
1144  (upperLeft_.x < r.lowerRight_.x) &&
1145  (r.upperLeft_.y < lowerRight_.y) &&
1146  (upperLeft_.y < r.lowerRight_.y))
1147  && !r.isEmpty();
1148  }
1149 
1150  /** Modifies this rectangle by including the given point. The
1151  * result is the bounding rectangle of the rectangle and the
1152  * point. If isEmpty returns true, the union will be a
1153  * rectangle containing only the given point.
1154  */
1156  {
1157  if(isEmpty())
1158  {
1159  upperLeft_ = p;
1160  lowerRight_ = p + Diff2D(1, 1);
1161  }
1162  else
1163  {
1164  if(p.x < upperLeft_.x)
1165  upperLeft_.x = p.x;
1166  if(p.y < upperLeft_.y)
1167  upperLeft_.y = p.y;
1168  if(lowerRight_.x <= p.x)
1169  lowerRight_.x = p.x + 1;
1170  if(lowerRight_.y <= p.y)
1171  lowerRight_.y = p.y + 1;
1172  }
1173  return *this;
1174  }
1175 
1176  /** Returns the union of this rectangle and the given
1177  * point. The result is the bounding rectangle of the
1178  * rectangle and the point. If isEmpty returns true, the union
1179  * will be a rectangle containing only the given point.
1180  */
1181  Rect2D operator|(Point2D const &p) const
1182  {
1183  Rect2D result(*this);
1184  result |= p;
1185  return result;
1186  }
1187 
1188  /** Modifies this rectangle by uniting it with the given
1189  * one. The result is the bounding rectangle of both
1190  * rectangles. If one of the rectangles isEmpty(), the union
1191  * will be the other one.
1192  */
1194  {
1195  if(r.isEmpty())
1196  return *this;
1197  if(isEmpty())
1198  return operator=(r);
1199 
1200  if(r.upperLeft_.x < upperLeft_.x)
1201  upperLeft_.x = r.upperLeft_.x;
1202  if(r.upperLeft_.y < upperLeft_.y)
1203  upperLeft_.y = r.upperLeft_.y;
1204  if(lowerRight_.x < r.lowerRight_.x)
1205  lowerRight_.x = r.lowerRight_.x;
1206  if(lowerRight_.y < r.lowerRight_.y)
1207  lowerRight_.y = r.lowerRight_.y;
1208  return *this;
1209  }
1210 
1211  /** Returns the union of this rectangle and the given one. The
1212  * result is the bounding rectangle of both rectangles. If one
1213  * of the rectangles isEmpty(), the union will be the other
1214  * one.
1215  */
1216  Rect2D operator|(Rect2D const &r) const
1217  {
1218  Rect2D result(*this);
1219  result |= r;
1220  return result;
1221  }
1222 
1223  /** Modifies this rectangle by intersecting it with the given
1224  * point. The result is the bounding rect of the point (with
1225  * width and height equal to 1) if it was contained in the
1226  * original rect, or an empty rect otherwise.
1227  */
1229  {
1230  if(contains(p))
1231  {
1232  upperLeft_ = p;
1233  lowerRight_ = p + Diff2D(1, 1);
1234  }
1235  else
1236  lowerRight_ = upperLeft_;
1237  return *this;
1238  }
1239 
1240  /** Intersects this rectangle with the given point. The result
1241  * is the bounding rect of the point (with width and height
1242  * equal to 1) if it was contained in the original rect, or an
1243  * empty rect otherwise.
1244  */
1245  Rect2D operator&(Point2D const &p) const
1246  {
1247  Rect2D result(*this);
1248  result &= p;
1249  return result;
1250  }
1251 
1252  /** Modifies this rectangle by intersecting it with the given
1253  * one. The result is the maximal rectangle contained in both
1254  * original ones. Intersecting with an empty rectangle will
1255  * yield again an empty rectangle.
1256  */
1258  {
1259  if(isEmpty())
1260  return *this;
1261  if(r.isEmpty())
1262  return operator=(r);
1263 
1264  if(upperLeft_.x < r.upperLeft_.x)
1265  upperLeft_.x = r.upperLeft_.x;
1266  if(upperLeft_.y < r.upperLeft_.y)
1267  upperLeft_.y = r.upperLeft_.y;
1268  if(r.lowerRight_.x < lowerRight_.x)
1269  lowerRight_.x = r.lowerRight_.x;
1270  if(r.lowerRight_.y < lowerRight_.y)
1271  lowerRight_.y = r.lowerRight_.y;
1272  return *this;
1273  }
1274 
1275  /** Scale this rectangle by the given factor.
1276  * To be specific, both upperLeft() and lowerRight() are
1277  * multiplied by `factor`.
1278  */
1279  Rect2D & operator*=(int factor)
1280  {
1281  upperLeft_ *= factor;
1282  lowerRight_ *= factor;
1283  return *this;
1284  }
1285 
1286  /** Scale this rectangle by the given factor.
1287  * To be specific, both upperLeft() and lowerRight() are
1288  * multiplied by `factor`.
1289  */
1290  Rect2D & operator*=(double factor)
1291  {
1292  upperLeft_ *= factor;
1293  lowerRight_ *= factor;
1294  return *this;
1295  }
1296 
1297  /** Return rectangle scaled by the given factor.
1298  * To be specific, both upperLeft() and lowerRight() are
1299  * multiplied by `factor`.
1300  */
1301  Rect2D operator*(int factor) const
1302  {
1303  return Rect2D(*this)*=factor;
1304  }
1305 
1306  /** Return rectangle scaled by the given factor.
1307  * To be specific, both upperLeft() and lowerRight() are
1308  * multiplied by `factor`.
1309  */
1310  Rect2D operator*(double factor) const
1311  {
1312  return Rect2D(*this)*=factor;
1313  }
1314 
1315  /** Intersects this rectangle with the given one. The result
1316  * is the maximal rectangle contained in both original ones.
1317  * Intersecting with an empty rectangle will yield again an
1318  * empty rectangle.
1319  */
1320  Rect2D operator&(Rect2D const &r) const
1321  {
1322  Rect2D result(*this);
1323  result &= r;
1324  return result;
1325  }
1326 };
1327 
1328 
1329 /********************************************************/
1330 /* */
1331 /* Dist2D */
1332 /* */
1333 /********************************************************/
1334 
1335 /** @deprecated use \ref vigra::Diff2D instead
1336 */
1337 class Dist2D
1338 {
1339  public:
1340  Dist2D(int the_width, int the_height)
1341  : width(the_width),
1342  height(the_height)
1343  {}
1344 
1345  Dist2D(Dist2D const & s)
1346  : width(s.width),
1347  height(s.height)
1348  {}
1349 
1350  Dist2D & operator=(Dist2D const & s)
1351  {
1352  if(this != &s)
1353  {
1354  width = s.width;
1355  height = s.height;
1356  }
1357  return *this;
1358  }
1359 
1360  Dist2D & operator+=(Dist2D const & s)
1361  {
1362  width += s.width;
1363  height += s.height;
1364 
1365  return *this;
1366  }
1367 
1368  Dist2D operator+(Dist2D const & s) const
1369  {
1370  Dist2D ret(*this);
1371  ret += s;
1372 
1373  return ret;
1374  }
1375 
1376  operator Diff2D()
1377  { return Diff2D(width, height); }
1378 
1379  int width;
1380  int height;
1381  };
1382 
1383 //@}
1384 
1385 } // namespace vigra
1386 
1387 namespace std {
1388 
1389 /**
1390  * Output a \ref vigra::Diff2D as a tuple.
1391  * Example Diff2D(-12, 13) -> "(-12, 13)"
1392  */
1393 inline
1394 ostream & operator<<(ostream & o, vigra::Diff2D const & d)
1395 {
1396  o << '(' << d.x << ", " << d.y << ')';
1397  return o;
1398 }
1399 
1400 /**
1401  * Output a \ref vigra::Size2D.
1402  * Example Size2D(100, 200) -> "(100x200)"
1403  */
1404 inline
1405 ostream &operator <<(ostream &s, vigra::Size2D const &d)
1406 {
1407  s << '(' << d.x << 'x' << d.y << ')';
1408  return s;
1409 }
1410 
1411 /**
1412  * Output a description of a \ref vigra::Rect2D.
1413  * Example Rect2D(10, 10, 30, 20) -> "[(10, 10) to (30, 20) = (20x10)]"
1414  */
1415 inline
1416 ostream &operator <<(ostream &s, vigra::Rect2D const &r)
1417 {
1418  s << "[" << r.upperLeft() << " to " << r.lowerRight()
1419  << " = " << r.size() << "]";
1420  return s;
1421 }
1422 
1423 } // namespace std
1424 
1425 #endif // VIGRA_DIFF2D_HXX
Diff2D operator*(double factor) const
Definition: diff2d.hxx:332
int MoveY
Definition: diff2d.hxx:229
bool intersects(Rect2D const &r) const
Definition: diff2d.hxx:1141
int left() const
Definition: diff2d.hxx:974
Rect2D(int left, int top, int right, int bottom)
Definition: diff2d.hxx:892
Rect2D & operator*=(double factor)
Definition: diff2d.hxx:1290
int operator[](int index) const
Definition: diff2d.hxx:417
Diff2D(int ax, int ay)
Definition: diff2d.hxx:240
bool isEmpty() const
Definition: diff2d.hxx:1105
Diff2D & operator/=(double factor)
Definition: diff2d.hxx:316
Definition: diff2d.hxx:1337
int width() const
Definition: diff2d.hxx:1005
Rect2D operator|(Rect2D const &r) const
Definition: diff2d.hxx:1216
int area() const
Definition: diff2d.hxx:538
Diff2D const * pointer
Definition: diff2d.hxx:206
Rect2D & operator&=(Rect2D const &r)
Definition: diff2d.hxx:1257
Rect2D()
Definition: diff2d.hxx:879
bool operator==(Rect2D const &r) const
equality check
Definition: diff2d.hxx:1087
int y
Definition: diff2d.hxx:392
void moveBy(Diff2D const &offset)
Definition: diff2d.hxx:959
Diff2D operator-(Diff2D const &a, Diff2D const &b)
Definition: diff2d.hxx:711
Rect2D operator|(Point2D const &p) const
Definition: diff2d.hxx:1181
Point2D & operator=(Diff2D const &v)
Definition: diff2d.hxx:654
bool operator!=(Diff2D const &r) const
Definition: diff2d.hxx:374
Point2D()
Definition: diff2d.hxx:617
index_reference operator[](Diff2D const &offset) const
Definition: diff2d.hxx:696
Rect2D(Point2D const &upperLeft, Size2D const &size)
Definition: diff2d.hxx:898
int right() const
Definition: diff2d.hxx:989
int px() const
Definition: diff2d.hxx:640
Rect2D operator&(Rect2D const &r) const
Definition: diff2d.hxx:1320
Size2D operator-() const
Definition: diff2d.hxx:552
int x
Definition: diff2d.hxx:385
Diff2D PixelType
Definition: diff2d.hxx:190
Diff2D operator+(Diff2D const &a, Diff2D const &b)
Definition: diff2d.hxx:739
Two dimensional difference vector.
Definition: diff2d.hxx:185
int top() const
Definition: diff2d.hxx:981
Rect2D(Point2D const &upperLeft, Point2D const &lowerRight)
Definition: diff2d.hxx:886
void addSize(Size2D const &offset)
Definition: diff2d.hxx:1057
Point2D operator-() const
Definition: diff2d.hxx:661
Point2D const & reference
Definition: diff2d.hxx:605
Diff2D & operator=(Diff2D const &v)
Definition: diff2d.hxx:252
void setUpperLeft(Point2D const &ul)
Definition: diff2d.hxx:927
Rect2D & operator&=(Point2D const &p)
Definition: diff2d.hxx:1228
void addBorder(int borderWidth)
Definition: diff2d.hxx:1067
Size2D()
Definition: diff2d.hxx:487
index_reference operator[](Diff2D const &offset) const
Definition: diff2d.hxx:410
Diff2D()
Definition: diff2d.hxx:234
reference operator*() const
Definition: diff2d.hxx:396
void setLowerRight(Point2D const &lr)
Definition: diff2d.hxx:935
int width() const
Definition: diff2d.hxx:510
Two dimensional size object.
Definition: diff2d.hxx:482
Point2D const & upperLeft() const
Definition: diff2d.hxx:911
Two dimensional point or position.
Definition: diff2d.hxx:592
index_reference operator()(int const &dx, int const &dy) const
Definition: diff2d.hxx:689
index_reference operator()(int const &dx, int const &dy) const
Definition: diff2d.hxx:403
Diff2D value_type
Definition: diff2d.hxx:194
Size2D & operator=(Diff2D const &v)
Definition: diff2d.hxx:545
Point2D const * pointer
Definition: diff2d.hxx:613
Diff2D & operator/=(int factor)
Definition: diff2d.hxx:307
row_iterator rowIterator() const
Definition: diff2d.hxx:431
int height() const
Definition: diff2d.hxx:517
Diff2D & operator+=(Diff2D const &offset)
Definition: diff2d.hxx:271
Diff2D difference_type
Definition: diff2d.hxx:210
int MoveX
Definition: diff2d.hxx:226
Size2D size() const
Definition: diff2d.hxx:1031
int bottom() const
Definition: diff2d.hxx:997
Rect2D & operator|=(Rect2D const &r)
Definition: diff2d.hxx:1193
image_traverser_tag iterator_category
Definition: diff2d.hxx:214
pointer operator->() const
Definition: diff2d.hxx:424
Point2D & operator+=(Diff2D const &offset)
Definition: diff2d.hxx:668
Point2D(Point2D const &v)
Definition: diff2d.hxx:628
Point2D value_type
Definition: diff2d.hxx:601
Diff2D index_reference
Definition: diff2d.hxx:202
Point2D PixelType
Definition: diff2d.hxx:597
Diff2D & operator-=(Diff2D const &offset)
Definition: diff2d.hxx:280
pointer operator->() const
Definition: diff2d.hxx:703
Rect2D(Size2D const &size)
Definition: diff2d.hxx:904
Point2D & operator-=(Diff2D const &offset)
Definition: diff2d.hxx:675
Rect2D operator*(int factor) const
Definition: diff2d.hxx:1301
Rect2D & operator|=(Point2D const &p)
Definition: diff2d.hxx:1155
Diff2D operator/(int factor) const
Definition: diff2d.hxx:339
Diff2D & operator*=(double factor)
Definition: diff2d.hxx:298
void moveBy(int xOffset, int yOffset)
Definition: diff2d.hxx:967
double magnitude() const
Definition: diff2d.hxx:360
void setSize(Size2D const &size)
Definition: diff2d.hxx:1039
Size2D(int width, int height)
Definition: diff2d.hxx:492
Diff2D operator/(double factor) const
Definition: diff2d.hxx:346
Diff2D(Diff2D const &v)
Definition: diff2d.hxx:246
void addBorder(int borderWidth, int borderHeight)
Definition: diff2d.hxx:1080
void setHeight(int h)
Definition: diff2d.hxx:531
Diff2D operator*(int factor) const
Definition: diff2d.hxx:325
Two dimensional rectangle.
Definition: diff2d.hxx:872
column_iterator columnIterator() const
Definition: diff2d.hxx:436
bool contains(Point2D const &p) const
Definition: diff2d.hxx:1116
Diff2D & operator*=(int factor)
Definition: diff2d.hxx:289
bool operator==(Diff2D const &r) const
Definition: diff2d.hxx:367
Rect2D operator&(Point2D const &p) const
Definition: diff2d.hxx:1245
Rect2D operator*(double factor) const
Definition: diff2d.hxx:1310
int area() const
Definition: diff2d.hxx:1022
Diff2D const & reference
Definition: diff2d.hxx:198
void moveTo(Point2D const &newUpperLeft)
Definition: diff2d.hxx:943
IteratorAdaptor< Diff2DConstColumnIteratorPolicy< Diff2D > > column_iterator
Definition: diff2d.hxx:222
void setSize(int width, int height)
Definition: diff2d.hxx:1047
bool operator!=(Rect2D const &r) const
inequality check
Definition: diff2d.hxx:1093
void moveTo(int left, int top)
Definition: diff2d.hxx:952
Size2D(Size2D const &v)
Definition: diff2d.hxx:498
Size2D(Diff2D const &v)
Definition: diff2d.hxx:504
reference operator*() const
Definition: diff2d.hxx:682
bool contains(Rect2D const &r) const
Definition: diff2d.hxx:1130
Quickly create 1-dimensional iterator adapters.
Definition: iteratoradapter.hxx:147
Rect2D & operator*=(int factor)
Definition: diff2d.hxx:1279
int height() const
Definition: diff2d.hxx:1013
Point2D(int x, int y)
Definition: diff2d.hxx:622
Size2D & operator-=(Diff2D const &offset)
Definition: diff2d.hxx:566
Point2D index_reference
Definition: diff2d.hxx:609
int squaredMagnitude() const
Definition: diff2d.hxx:353
SquareRootTraits< FixedPoint< IntBits, FracBits > >::SquareRootResult sqrt(FixedPoint< IntBits, FracBits > v)
square root.
Definition: fixedpoint.hxx:616
Point2D(Diff2D const &v)
Definition: diff2d.hxx:634
void setWidth(int w)
Definition: diff2d.hxx:524
Diff2D operator-() const
Definition: diff2d.hxx:264
int py() const
Definition: diff2d.hxx:647
Size2D & operator+=(Diff2D const &offset)
Definition: diff2d.hxx:559
IteratorAdaptor< Diff2DConstRowIteratorPolicy< Diff2D > > row_iterator
Definition: diff2d.hxx:218
Point2D const & lowerRight() const
Definition: diff2d.hxx:919

© Ullrich Köthe (ullrich.koethe@iwr.uni-heidelberg.de)
Heidelberg Collaboratory for Image Processing, University of Heidelberg, Germany

html generated using doxygen and Python
vigra 1.11.1 (Fri May 19 2017)