1 // This is core/vgl/vgl_ray_3d.h
2 #ifndef vgl_ray_3d_h_
3 #define vgl_ray_3d_h_
4 //:
5 // \file
6 // \brief A 3-d ray defined by an origin and a direction vector
7 // \author J.L. Mundy
8 //
9 // \verbatim
10 // Modifications
11 // Initial version Sept. 17, 2010
12 // \endverbatim
13
14 #include <iosfwd>
15 #ifdef _MSC_VER
16 # include <vcl_msvc_warnings.h>
17 #endif
18 #include "vgl_vector_3d.h"
19 #include "vgl_point_3d.h"
20 #include "vgl_line_segment_3d.h"
21 #include "vgl_line_3d_2_points.h"
22
23 //: Represents a 3-d ray
24 // The ray origin is p0 and the direction is t_.
25
26 template <class Type>
27 class vgl_ray_3d
28 {
29 vgl_point_3d<Type> p0_; //!< The ray origin
30 vgl_vector_3d<Type> t_; //!< ray direction vector
31 public:
32 //: Default constructor - does not initialise!
33 inline vgl_ray_3d() = default;
34
35 //: Copy constructor
vgl_ray_3d(vgl_ray_3d<Type> const & l)36 inline vgl_ray_3d(vgl_ray_3d<Type> const& l)
37 : p0_(l.origin()), t_(l.direction()) {}
38
39 //: Construct from orign and direction
vgl_ray_3d(vgl_point_3d<Type> const & p0,vgl_vector_3d<Type> const & direction)40 inline vgl_ray_3d(vgl_point_3d<Type> const& p0,
41 vgl_vector_3d<Type> const& direction)
42 : p0_(p0), t_(direction) {t_ = t_/static_cast<Type>(t_.length());}
43
44 //: Construct from two points
vgl_ray_3d(vgl_point_3d<Type> const & origin,vgl_point_3d<Type> const & p)45 inline vgl_ray_3d(vgl_point_3d<Type> const& origin,
46 vgl_point_3d<Type> const& p)
47 : p0_(origin), t_(p-origin) {t_ = t_/static_cast<Type>(t_.length());}
48 //: Construct from a line segment, direction from 1 to 2
vgl_ray_3d(vgl_line_segment_3d<Type> const & ls)49 inline vgl_ray_3d(vgl_line_segment_3d<Type> const& ls)
50 {
51 p0_ = ls.point1(); t_ = ls.point2()-p0_;
52 t_ = t_/static_cast<Type>(t_.length());
53 }
54
55 //: Construct from a line 2 points direction from 1 to 2
vgl_ray_3d(vgl_line_3d_2_points<Type> const & ls)56 inline vgl_ray_3d(vgl_line_3d_2_points<Type> const& ls)
57 {
58 p0_ = ls.point1(); t_ = ls.point2()-p0_;
59 t_ = t_/static_cast<Type>(t_.length());
60 }
61
62 //: Destructor
63 inline ~vgl_ray_3d() = default;
64
65 //: Accessors
origin()66 inline vgl_point_3d<Type> origin() const { return p0_; } // return a copy
67
direction()68 inline vgl_vector_3d<Type> direction() const
69 { return t_/static_cast<Type>(t_.length()); } // return a copy
70
71 //: The comparison operator
72 inline bool operator==(vgl_ray_3d<Type> const& r) const
73 { return (this==&r)||(direction()==r.direction() && origin()==r.origin());}
74
75 inline bool operator!=(vgl_ray_3d<Type>const& other) const
76 { return !operator==(other); }
77
78 //: Assignment
set(vgl_point_3d<Type> const & p0,vgl_vector_3d<Type> const & direction)79 inline void set(vgl_point_3d<Type> const& p0, vgl_vector_3d<Type> const& direction)
80 {
81 p0_ = p0; t_ = direction;
82 t_=t_/static_cast<Type>(t_.length());
83 }
84
85 //: Check if point \a p is on the ray and lies in the positive ray direction
86 bool contains(const vgl_point_3d<Type>& p ) const;
87
88 };
89
90 //: Write to stream
91 // \relatesalso vgl_ray_3d
92 template <class Type>
93 std::ostream& operator<<(std::ostream& s, const vgl_ray_3d<Type>& p);
94
95 //: Read from stream
96 // \relatesalso vgl_ray_3d
97 template <class Type>
98 std::istream& operator>>(std::istream& is, vgl_ray_3d<Type>& p);
99 //: public functions
100 template <class Type>
101 //: angle between rays
angle(vgl_ray_3d<Type> const & r0,vgl_ray_3d<Type> const & r1)102 double angle(vgl_ray_3d<Type> const& r0, vgl_ray_3d<Type> const& r1)
103 {
104 return angle(r0.direction(), r1.direction());
105 }
106 #define VGL_RAY_3D_INSTANTIATE(T) extern "please include vgl/vgl_ray_3d.hxx first"
107
108 #endif // vgl_ray_3d_h_
109