View Javadoc

1   package org.lcsim.recon.tracking.spacegeom;
2   import static java.lang.Math.atan2;
3   import static java.lang.Math.PI;
4   /**
5    * A line segment in two dimensions.
6    *
7    *
8    *@author Norman A. Graf
9    *@version 1.0
10   *
11   */
12  
13  public class TwoSegment
14  {
15      private TwoSpacePoint _a;
16      private TwoSpacePoint _b;
17      private double _length;
18      
19      /**
20       * Constructor
21       *
22       * @param   a beginning TwoSpacePoint
23       * @param   b ending TwoSpacePoint
24       */
25      public TwoSegment(TwoSpacePoint a, TwoSpacePoint b)
26      {
27          _a = a;
28          _b = b;
29          _length = TwoSpacePoint.distance(_a,_b);
30      }
31      
32      
33      /**
34       * Fetch the starting point
35       *
36       * @return beginning TwoSpacePoint
37       */
38      public TwoSpacePoint startPoint()
39      {
40          return _a;
41      }
42      
43      
44      /**
45       * Fetch the ending point
46       *
47       * @return  ending TwoSpacePoint
48       */
49      public TwoSpacePoint endPoint()
50      {
51          return _b;
52      }
53      
54      
55      /**
56       * Return the length of the segment
57       *
58       * @return  length of the segment
59       */
60      public double length()
61      {
62          return _length;
63      }
64      
65      /**
66       * Return the azimuthal angle of this segment, the angle from point 1 to 2
67       * zero & 3pi/4 is vertical
68       * pi and 2pi is horizontal
69       * @return the angle from point 1 to point 2
70       */
71      public double phi()
72      {
73          double x = _a.x() - _b.x();
74          double y = _a.y() - _b.y();
75          double phi = atan2(y,x);
76          if(phi<0) phi+= 2.*PI;
77          return phi;
78      }
79      
80      
81      /**
82       * calculate the minimum distance between this segment and a point p
83       *
84       * @param   p The TwoSpacePoint
85       * @return  the distance between the point and this segment
86       */
87      public double minimumDistance(TwoSpacePoint p)
88      {
89          double u = ( ( ( p.x() - _a.x() ) * ( _b.x() - _a.x() ) ) +
90          ( ( p.y() - _a.y() ) * ( _b.y() - _a.y() ) ) )/(_length*_length);
91          double xint = ( _a.x() + u * (_b.x() - _a.x()) ) - p.x();
92          double yint = ( _a.y() + u * (_b.y() - _a.y()) ) - p.y();
93          double dist = Math.sqrt( xint*xint + yint*yint );
94          return dist;
95      }
96      
97      
98      
99      /**
100      * return intersection point of two line segments
101      *
102      * @param   a The first line segment
103      * @param   b The second line segment
104      * @return    The intersection point of the two segments.
105      *            null if lines are parallel or intersect outside of segment boundaries.
106      */
107     public static TwoSpacePoint intersection(TwoSegment a, TwoSegment b)
108     {
109         // set some things up
110         double x1 = a.startPoint().x();
111         double y1 = a.startPoint().y();
112         double x2 = a.endPoint().x();
113         double y2 = a.endPoint().y();
114         double x3 = b.startPoint().x();
115         double y3 = b.startPoint().y();
116         double x4 = b.endPoint().x();
117         double y4 = b.endPoint().y();
118         
119         double denom = (y4-y3)*(x2-x1)-(x4-x3)*(y2-y1);
120         
121         if(denom==0) return null;// lines are parallel
122         
123         double numa = (x4-x3)*(y1-y3)-(y4-y3)*(x1-x3);
124         
125         if(numa==0) return null; // lines are coincident, no unique intersection
126         
127         double ua = numa/denom;
128         
129         if(ua<0 || ua >1.) return null; // intersect outside of segment a
130         
131         double numb = (x2-x1)*(y1-y3)-(y2-y1)*(x1-x3);
132         double ub = numb/denom;
133         if(ub<0 || ub >1.) return null; // intersect outside of segment b
134         
135         // should now have a valid intersection point...
136         double xend = x3+ub*(x4-x3);
137         double yend = y3+ub*(y4-y3);
138         
139         return new CartesianTwoPoint(xend, yend);
140         
141     }
142     
143     
144     /** String representation of this object
145      *
146      *
147      * @return  String representation of this object
148      */
149     public String toString()
150     {
151         return "TwoSegment from "+_a+" \n to "+_b +" \n length: "+_length;
152     }
153     
154 }