Geant4 Cross Reference |
1 // -*- C++ -*- 2 // --------------------------------------------------------------------------- 3 // 4 // This file is a part of the CLHEP - a Class Library for High Energy Physics. 5 // 6 // History: 7 // 22.09.96 E.Chernyaev - initial version 8 // 19.10.96 J.Allison - added == and <<. 9 // 15.04.03 E.Chernyaev - CLHEP-1.9: template version 10 11 #ifndef HEP_PLANE3D_H 12 #define HEP_PLANE3D_H 13 14 #include <iosfwd> 15 #include "CLHEP/Geometry/Point3D.h" 16 #include "CLHEP/Geometry/Normal3D.h" 17 #include "CLHEP/Geometry/Transform3D.h" 18 19 namespace HepGeom { 20 21 /** 22 * Template class for geometrical plane in 3D. 23 * 24 * @author Evgeni Chernyaev <Evgueni.Tcherniaev@cern.ch> 25 * @ingroup geometry 26 */ 27 template<class T> 28 class Plane3D { 29 protected: 30 T a_, b_, c_, d_; 31 32 public: 33 /** 34 * Default constructor - creates plane z=0. */ 35 Plane3D() : a_(0.), b_(0.), c_(1.), d_(0.) {} 36 37 /** 38 * Constructor from four numbers - creates plane a*x+b*y+c*z+d=0. */ 39 Plane3D(T a1, T b1, T c1, T d1) : a_(a1), b_(b1), c_(c1), d_(d1) {} 40 41 /** 42 * Constructor from normal and point. */ 43 Plane3D(const Normal3D<T> & n, const Point3D<T> & p) 44 : a_(n.x()), b_(n.y()), c_(n.z()), d_(-n*p) {} 45 46 /** 47 * Constructor from three points. */ 48 Plane3D(const Point3D<T> & p1, 49 const Point3D<T> & p2, 50 const Point3D<T> & p3) { 51 Normal3D<T> n = (p2-p1).cross(p3-p1); 52 a_ = n.x(); b_ = n.y(); c_ = n.z(); d_ = -n*p1; 53 } 54 55 /** 56 * Copy constructor. */ 57 Plane3D(const Plane3D<T> &) = default; 58 59 /** 60 * Constructor for Plane3D<double> from Plane3D<float>. */ 61 template<typename U = T, 62 typename = typename std::enable_if<!std::is_same<U,float>::value >::type> 63 Plane3D(const Plane3D<float> & p) 64 : a_(p.a_), b_(p.b_), c_(p.c_), d_(p.d_) {} 65 66 /** 67 * Move constructor. */ 68 Plane3D(Plane3D<T> &&) = default; 69 70 /** 71 * Destructor. */ 72 ~Plane3D() = default; 73 74 /** 75 * Assignment. */ 76 Plane3D<T> & operator=(const Plane3D<T> &) = default; 77 78 /** 79 * Move assignment. */ 80 Plane3D<T> & operator=(Plane3D<T> &&) = default; 81 82 /** 83 * Returns the a-coefficient in the plane equation: a*x+b*y+c*z+d=0. */ 84 T a() const { return a_; } 85 /** 86 * Returns the b-coefficient in the plane equation: a*x+b*y+c*z+d=0. */ 87 T b() const { return b_; } 88 /** 89 * Returns the c-coefficient in the plane equation: a*x+b*y+c*z+d=0. */ 90 T c() const { return c_; } 91 /** 92 * Returns the free member of the plane equation: a*x+b*y+c*z+d=0. */ 93 T d() const { return d_; } 94 95 /** 96 * Returns normal. */ 97 Normal3D<T> normal() const { return Normal3D<T>(a_,b_,c_); } 98 99 /** 100 * Normalization. */ 101 Plane3D<T> & normalize() { 102 double ll = std::sqrt(a_*a_ + b_*b_ + c_*c_); 103 if (ll > 0.) { a_ /= ll; b_ /= ll; c_ /= ll, d_ /= ll; } 104 return *this; 105 } 106 107 /** 108 * Returns distance to the point. */ 109 T distance(const Point3D<T> & p) const { 110 return a()*p.x() + b()*p.y() + c()*p.z() + d(); 111 } 112 113 /** 114 * Returns projection of the point to the plane. */ 115 Point3D<T> point(const Point3D<T> & p) const { 116 T k = distance(p)/(a()*a()+b()*b()+c()*c()); 117 return Point3D<T>(p.x()-a()*k, p.y()-b()*k, p.z()-c()*k); 118 } 119 120 /** 121 * Returns projection of the origin to the plane. */ 122 Point3D<T> point() const { 123 T k = -d()/(a()*a()+b()*b()+c()*c()); 124 return Point3D<T>(a()*k, b()*k, c()*k); 125 } 126 127 /** 128 * Test for equality. */ 129 bool operator == (const Plane3D<T> & p) const { 130 return a() == p.a() && b() == p.b() && c() == p.c() && d() == p.d(); 131 } 132 133 /** 134 * Test for inequality. */ 135 bool operator != (const Plane3D<T> & p) const { 136 return a() != p.a() || b() != p.b() || c() != p.c() || d() != p.d(); 137 } 138 139 /** 140 * Transformation by Transform3D. */ 141 Plane3D<T> & transform(const Transform3D & m) { 142 Normal3D<T> n = normal(); 143 n.transform(m); 144 d_ = -n*point().transform(m); a_ = n.x(); b_ = n.y(); c_ = n.z(); 145 return *this; 146 } 147 }; 148 149 /** 150 * Output to the stream. 151 * @relates Plane3D 152 */ 153 std::ostream & operator<<(std::ostream & os, const Plane3D<float> & p); 154 155 /** 156 * Output to the stream. 157 * @relates Plane3D 158 */ 159 std::ostream & operator<<(std::ostream & os, const Plane3D<double> & p); 160 161 } /* namespace HepGeom */ 162 163 #endif /* HEP_PLANE3D_H */ 164