1 // This is oxl/mvl/HomgMetric.h
2 #ifndef HomgMetric_h_
3 #define HomgMetric_h_
4 //:
5 // \file
6 // \brief Measurements on homogeneous coordinates
7 //
8 //    HomgMetric is a class that allows measurements to be made between
9 //    homogeneous primitives.  If attached to an ImageMetric (q.v.), uses
10 //    that, otherwise uses HomgOperator2D.
11 //
12 //    HomgMetric is an ImageMetric pointer, it behaves just like one, and
13 //    {\em does not} have responsibility for memory management, no more
14 //    than any other pointer.
15 //
16 // \author
17 //     Andrew W. Fitzgibbon, Oxford RRG, 28 Jan 97
18 //
19 // \verbatim
20 // Modifications
21 //    22 Oct 2002 - Peter Vanroose - added vgl_homg_point_2d interface
22 // \endverbatim
23 //
24 //-----------------------------------------------------------------------------
25 
26 #include <iostream>
27 #include <iosfwd>
28 #include <vnl/vnl_fwd.h>
29 #include <vgl/vgl_fwd.h>
30 #ifdef _MSC_VER
31 #  include <vcl_msvc_warnings.h>
32 #endif
33 
34 class ImageMetric;
35 class HomgPoint2D;
36 class HomgLine2D;
37 class HomgLineSeg2D;
38 class FMatrix;
39 class TriTensor;
40 class HMatrix2D;
41 class PMatrix;
42 
43 class HomgMetric
44 {
45   // Data Members--------------------------------------------------------------
46   const ImageMetric *metric_{nullptr};
47 
48 public:
49   // Constructors/Destructors--------------------------------------------------
50 
51   HomgMetric() = default;
52   HomgMetric(const ImageMetric* metric);
53 
54   // HomgMetric(const HomgMetric& that); - use default
55   ~HomgMetric();
56   // HomgMetric& operator=(const HomgMetric& that); - use default
57 
58   // Operations----------------------------------------------------------------
59 
60   // ** Conversion to/from homogeneous coordinates
61   vgl_point_2d<double> homg_to_image(vgl_homg_point_2d<double> const&) const;
62   vnl_double_2 homg_to_image(const HomgPoint2D&) const;
63   void homg_to_image(const HomgPoint2D&, double* ix, double* iy) const;
64   void homg_to_image(vgl_homg_point_2d<double> const&, double& ix, double& iy) const;
65 
66   vgl_homg_point_2d<double> image_to_homg(vgl_point_2d<double> const&) const;
67   HomgPoint2D image_to_homg(const vnl_double_2&) const;
68   HomgPoint2D image_to_homg(double x, double y) const;
69 
70   HomgPoint2D homg_to_imagehomg(const HomgPoint2D&) const;
71   HomgPoint2D imagehomg_to_homg(const HomgPoint2D&) const;
72 
73   vgl_homg_point_2d<double> homg_to_imagehomg(vgl_homg_point_2d<double> const&) const;
74   vgl_homg_point_2d<double> imagehomg_to_homg(vgl_homg_point_2d<double> const&) const;
75 
76   HomgLine2D homg_to_image_line(const HomgLine2D&) const;
77   HomgLine2D image_to_homg_line(const HomgLine2D&) const;
78 
79   vgl_homg_line_2d<double> homg_to_image_line(vgl_homg_line_2d<double> const&) const;
80   vgl_homg_line_2d<double> image_to_homg_line(vgl_homg_line_2d<double> const&) const;
81 
82   HomgLineSeg2D image_to_homg_line(const HomgLineSeg2D&) const;
83   HomgLineSeg2D homg_line_to_image(const HomgLineSeg2D&) const;
84 
85   // ** Measurements
86   double perp_dist_squared(const HomgPoint2D&, const HomgLine2D&) const;
87   double perp_dist_squared(vgl_homg_point_2d<double> const& p,
88                            vgl_homg_line_2d<double> const& l) const;
89   HomgPoint2D perp_projection(const HomgLine2D& l, const HomgPoint2D& p) const;
90   vgl_homg_point_2d<double> perp_projection(vgl_homg_line_2d<double> const& l,
91                                             vgl_homg_point_2d<double> const& p) const;
92 
93   double distance_squared(double x1, double y1, double x2, double y2) const;
94   double distance_squared(const HomgPoint2D&, const HomgPoint2D&) const;
95   double distance_squared(vgl_homg_point_2d<double> const&,
96                           vgl_homg_point_2d<double> const&) const;
97   double distance_squared(const HomgLineSeg2D& segment, const HomgLine2D& line) const;
98   double distance_squared(vgl_line_segment_2d<double> const& segment,
99                           vgl_homg_line_2d<double> const& line) const;
100 
101   bool is_within_distance(const HomgPoint2D&, const HomgPoint2D&, double distance) const;
102   bool is_within_distance(vgl_homg_point_2d<double> const&,
103                           vgl_homg_point_2d<double> const&,
104                           double distance) const;
105 
106   // ** Speedups available for certain systems.
107   bool is_linear() const;
108   vnl_double_3x3 get_C() const;
109   vnl_double_3x3 get_C_inverse() const;
110 
111   bool can_invert_distance() const;
112   double image_to_homg_distance(double image_distance) const;
113   double homg_to_image_distance(double homg_distance) const;
114 
115   double image_to_homg_distance_sqr(double image_distance) const;
116   double homg_to_image_distance_sqr(double homg_distance) const;
117 
118   std::ostream& print(std::ostream&) const;
119 
120   operator const ImageMetric* () const { return metric_; }
121 
122   // Static functions to condition/decondition image relations-----------------
123   static PMatrix homg_to_image_P(const PMatrix&, const HomgMetric& c);
124   static PMatrix image_to_homg_P(const PMatrix&, const HomgMetric& c);
125 
126   static FMatrix homg_to_image_F(const FMatrix&, const HomgMetric& c1, const HomgMetric& c2);
127   static FMatrix image_to_homg_F(const FMatrix&, const HomgMetric& c1, const HomgMetric& c2);
128 
129   static TriTensor homg_to_image_T(const TriTensor&, const HomgMetric& c1, const HomgMetric& c2, const HomgMetric& c3);
130   static TriTensor image_to_homg_T(const TriTensor&, const HomgMetric& c1, const HomgMetric& c2, const HomgMetric& c3);
131 
132   static HMatrix2D homg_to_image_H(const HMatrix2D&, const HomgMetric& c1, const HomgMetric& c2);
133   static HMatrix2D image_to_homg_H(const HMatrix2D&, const HomgMetric& c1, const HomgMetric& c2);
134 };
135 
136 inline std::ostream& operator<<(std::ostream& s, const HomgMetric& h) { return h.print(s); }
137 
138 #endif // HomgMetric_h_
139