/[classpath]/classpath/java/awt/geom/CubicCurve2D.java
ViewVC logotype

Diff of /classpath/java/awt/geom/CubicCurve2D.java

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.6 by brawer, Mon Jan 5 00:27:39 2004 UTC revision 1.7 by smarothy, Sun Aug 1 22:27:36 2004 UTC
# Line 1  Line 1 
1  /* CubicCurve2D.java -- represents a parameterized cubic curve in 2-D space  /* CubicCurve2D.java -- represents a parameterized cubic curve in 2-D space
2     Copyright (C) 2002, 2003 Free Software Foundation     Copyright (C) 2002, 2003, 2004 Free Software Foundation
3    
4  This file is part of GNU Classpath.  This file is part of GNU Classpath.
5    
# Line 35  this exception to your version of the li Line 35  this exception to your version of the li
35  obligated to do so.  If you do not wish to do so, delete this  obligated to do so.  If you do not wish to do so, delete this
36  exception statement from your version. */  exception statement from your version. */
37    
   
38  package java.awt.geom;  package java.awt.geom;
39    
40  import java.awt.Rectangle;  import java.awt.Rectangle;
# Line 53  import java.util.NoSuchElementException; Line 52  import java.util.NoSuchElementException;
52   * @author Eric Blake (ebb9@email.byu.edu)   * @author Eric Blake (ebb9@email.byu.edu)
53   * @author Graydon Hoare (graydon@redhat.com)   * @author Graydon Hoare (graydon@redhat.com)
54   * @author Sascha Brawer (brawer@dandelis.ch)   * @author Sascha Brawer (brawer@dandelis.ch)
55     * @author Sven de Marothy (sven@physto.se)
56   *   *
57   * @since 1.2   * @since 1.2
58   */   */
59  public abstract class CubicCurve2D  public abstract class CubicCurve2D implements Shape, Cloneable
   implements Shape, Cloneable  
60  {  {
61      private static final double BIG_VALUE = java.lang.Double.MAX_VALUE / 10.0;
62    
63    /**    /**
64     * Constructs a new CubicCurve2D. Typical users will want to     * Constructs a new CubicCurve2D. Typical users will want to
65     * construct instances of a subclass, such as {@link     * construct instances of a subclass, such as {@link
# Line 68  public abstract class CubicCurve2D Line 69  public abstract class CubicCurve2D
69    {    {
70    }    }
71    
   
72    /**    /**
73     * Returns the <i>x</i> coordinate of the curve&#x2019;s start     * Returns the <i>x</i> coordinate of the curve&#x2019;s start
74     * point.     * point.
75     */     */
76    public abstract double getX1();    public abstract double getX1();
77    
   
78    /**    /**
79     * Returns the <i>y</i> coordinate of the curve&#x2019;s start     * Returns the <i>y</i> coordinate of the curve&#x2019;s start
80     * point.     * point.
81     */     */
82    public abstract double getY1();    public abstract double getY1();
83    
   
84    /**    /**
85     * Returns the curve&#x2019;s start point.     * Returns the curve&#x2019;s start point.
86     */     */
87    public abstract Point2D getP1();    public abstract Point2D getP1();
88    
   
89    /**    /**
90     * Returns the <i>x</i> coordinate of the curve&#x2019;s first     * Returns the <i>x</i> coordinate of the curve&#x2019;s first
91     * control point.     * control point.
92     */     */
93    public abstract double getCtrlX1();    public abstract double getCtrlX1();
94    
   
95    /**    /**
96     * Returns the <i>y</i> coordinate of the curve&#x2019;s first     * Returns the <i>y</i> coordinate of the curve&#x2019;s first
97     * control point.     * control point.
98     */     */
99    public abstract double getCtrlY1();    public abstract double getCtrlY1();
100    
   
101    /**    /**
102     * Returns the curve&#x2019;s first control point.     * Returns the curve&#x2019;s first control point.
103     */     */
104    public abstract Point2D getCtrlP1();    public abstract Point2D getCtrlP1();
105    
   
106    /**    /**
107     * Returns the <i>x</i> coordinate of the curve&#x2019;s second     * Returns the <i>x</i> coordinate of the curve&#x2019;s second
108     * control point.     * control point.
109     */     */
110    public abstract double getCtrlX2();    public abstract double getCtrlX2();
111    
   
112    /**    /**
113     * Returns the <i>y</i> coordinate of the curve&#x2019;s second     * Returns the <i>y</i> coordinate of the curve&#x2019;s second
114     * control point.     * control point.
115     */     */
116    public abstract double getCtrlY2();    public abstract double getCtrlY2();
117    
   
118    /**    /**
119     * Returns the curve&#x2019;s second control point.     * Returns the curve&#x2019;s second control point.
120     */     */
121    public abstract Point2D getCtrlP2();    public abstract Point2D getCtrlP2();
122    
   
123    /**    /**
124     * Returns the <i>x</i> coordinate of the curve&#x2019;s end     * Returns the <i>x</i> coordinate of the curve&#x2019;s end
125     * point.     * point.
126     */     */
127    public abstract double getX2();    public abstract double getX2();
128    
   
129    /**    /**
130     * Returns the <i>y</i> coordinate of the curve&#x2019;s end     * Returns the <i>y</i> coordinate of the curve&#x2019;s end
131     * point.     * point.
132     */     */
133    public abstract double getY2();    public abstract double getY2();
134    
   
135    /**    /**
136     * Returns the curve&#x2019;s end point.     * Returns the curve&#x2019;s end point.
137     */     */
138    public abstract Point2D getP2();    public abstract Point2D getP2();
139    
   
140    /**    /**
141     * Changes the curve geometry, separately specifying each coordinate     * Changes the curve geometry, separately specifying each coordinate
142     * value.     * value.
# Line 183  public abstract class CubicCurve2D Line 171  public abstract class CubicCurve2D
171    public abstract void setCurve(double x1, double y1, double cx1, double cy1,    public abstract void setCurve(double x1, double y1, double cx1, double cy1,
172                                  double cx2, double cy2, double x2, double y2);                                  double cx2, double cy2, double x2, double y2);
173    
   
174    /**    /**
175     * Changes the curve geometry, specifying coordinate values in an     * Changes the curve geometry, specifying coordinate values in an
176     * array.     * array.
# Line 206  public abstract class CubicCurve2D Line 193  public abstract class CubicCurve2D
193     */     */
194    public void setCurve(double[] coords, int offset)    public void setCurve(double[] coords, int offset)
195    {    {
196      setCurve(coords[offset++], coords[offset++],      setCurve(coords[offset++], coords[offset++], coords[offset++],
197               coords[offset++], coords[offset++],               coords[offset++], coords[offset++], coords[offset++],
              coords[offset++], coords[offset++],  
198               coords[offset++], coords[offset++]);               coords[offset++], coords[offset++]);
199    }    }
200    
   
201    /**    /**
202     * Changes the curve geometry, specifying coordinate values in     * Changes the curve geometry, specifying coordinate values in
203     * separate Point objects.     * separate Point objects.
# Line 232  public abstract class CubicCurve2D Line 217  public abstract class CubicCurve2D
217     */     */
218    public void setCurve(Point2D p1, Point2D c1, Point2D c2, Point2D p2)    public void setCurve(Point2D p1, Point2D c1, Point2D c2, Point2D p2)
219    {    {
220      setCurve(p1.getX(), p1.getY(), c1.getX(), c1.getY(),      setCurve(p1.getX(), p1.getY(), c1.getX(), c1.getY(), c2.getX(), c2.getY(),
221               c2.getX(), c2.getY(), p2.getX(), p2.getY());               p2.getX(), p2.getY());
222    }    }
223    
   
224    /**    /**
225     * Changes the curve geometry, specifying coordinate values in an     * Changes the curve geometry, specifying coordinate values in an
226     * array of Point objects.     * array of Point objects.
# Line 258  public abstract class CubicCurve2D Line 242  public abstract class CubicCurve2D
242     */     */
243    public void setCurve(Point2D[] pts, int offset)    public void setCurve(Point2D[] pts, int offset)
244    {    {
245      setCurve(pts[offset].getX(), pts[offset++].getY(),      setCurve(pts[offset].getX(), pts[offset++].getY(), pts[offset].getX(),
246               pts[offset].getX(), pts[offset++].getY(),               pts[offset++].getY(), pts[offset].getX(), pts[offset++].getY(),
              pts[offset].getX(), pts[offset++].getY(),  
247               pts[offset].getX(), pts[offset++].getY());               pts[offset].getX(), pts[offset++].getY());
248    }    }
     
249    
250    /**    /**
251     * Changes the curve geometry to that of another curve.     * Changes the curve geometry to that of another curve.
# Line 276  public abstract class CubicCurve2D Line 258  public abstract class CubicCurve2D
258               c.getCtrlX2(), c.getCtrlY2(), c.getX2(), c.getY2());               c.getCtrlX2(), c.getCtrlY2(), c.getX2(), c.getY2());
259    }    }
260    
   
261    /**    /**
262     * Calculates the squared flatness of a cubic curve, directly     * Calculates the squared flatness of a cubic curve, directly
263     * specifying each coordinate value. The flatness is the maximal     * specifying each coordinate value. The flatness is the maximal
# Line 309  public abstract class CubicCurve2D Line 290  public abstract class CubicCurve2D
290                      Line2D.ptSegDistSq(x1, y1, x2, y2, cx2, cy2));                      Line2D.ptSegDistSq(x1, y1, x2, y2, cx2, cy2));
291    }    }
292    
   
293    /**    /**
294     * Calculates the flatness of a cubic curve, directly specifying     * Calculates the flatness of a cubic curve, directly specifying
295     * each coordinate value. The flatness is the maximal distance of a     * each coordinate value. The flatness is the maximal distance of a
# Line 340  public abstract class CubicCurve2D Line 320  public abstract class CubicCurve2D
320      return Math.sqrt(getFlatnessSq(x1, y1, cx1, cy1, cx2, cy2, x2, y2));      return Math.sqrt(getFlatnessSq(x1, y1, cx1, cy1, cx2, cy2, x2, y2));
321    }    }
322    
   
323    /**    /**
324     * Calculates the squared flatness of a cubic curve, specifying the     * Calculates the squared flatness of a cubic curve, specifying the
325     * coordinate values in an array. The flatness is the maximal     * coordinate values in an array. The flatness is the maximal
# Line 374  public abstract class CubicCurve2D Line 353  public abstract class CubicCurve2D
353     */     */
354    public static double getFlatnessSq(double[] coords, int offset)    public static double getFlatnessSq(double[] coords, int offset)
355    {    {
356      return getFlatnessSq(coords[offset++], coords[offset++],      return getFlatnessSq(coords[offset++], coords[offset++], coords[offset++],
357                           coords[offset++], coords[offset++],                           coords[offset++], coords[offset++], coords[offset++],
                          coords[offset++], coords[offset++],  
358                           coords[offset++], coords[offset++]);                           coords[offset++], coords[offset++]);
359    }    }
360    
   
361    /**    /**
362     * Calculates the flatness of a cubic curve, specifying the     * Calculates the flatness of a cubic curve, specifying the
363     * coordinate values in an array. The flatness is the maximal     * coordinate values in an array. The flatness is the maximal
# Line 420  public abstract class CubicCurve2D Line 397  public abstract class CubicCurve2D
397                                     coords[offset++], coords[offset++]));                                     coords[offset++], coords[offset++]));
398    }    }
399    
   
400    /**    /**
401     * Calculates the squared flatness of this curve.  The flatness is     * Calculates the squared flatness of this curve.  The flatness is
402     * the maximal distance of a control point to the line between start     * the maximal distance of a control point to the line between start
# Line 441  public abstract class CubicCurve2D Line 417  public abstract class CubicCurve2D
417                           getCtrlX2(), getCtrlY2(), getX2(), getY2());                           getCtrlX2(), getCtrlY2(), getX2(), getY2());
418    }    }
419    
   
420    /**    /**
421     * Calculates the flatness of this curve.  The flatness is the     * Calculates the flatness of this curve.  The flatness is the
422     * maximal distance of a control point to the line between start and     * maximal distance of a control point to the line between start and
# Line 458  public abstract class CubicCurve2D Line 433  public abstract class CubicCurve2D
433     */     */
434    public double getFlatness()    public double getFlatness()
435    {    {
436      return Math.sqrt(getFlatnessSq(getX1(), getY1(), getCtrlX1(),      return Math.sqrt(getFlatnessSq(getX1(), getY1(), getCtrlX1(), getCtrlY1(),
437                                     getCtrlY1(), getCtrlX2(), getCtrlY2(),                                     getCtrlX2(), getCtrlY2(), getX2(), getY2()));
                                    getX2(), getY2()));  
438    }    }
439    
   
440    /**    /**
441     * Subdivides this curve into two halves.     * Subdivides this curve into two halves.
442     *     *
# Line 482  public abstract class CubicCurve2D Line 455  public abstract class CubicCurve2D
455    public void subdivide(CubicCurve2D left, CubicCurve2D right)    public void subdivide(CubicCurve2D left, CubicCurve2D right)
456    {    {
457      // Use empty slots at end to share single array.      // Use empty slots at end to share single array.
458      double[] d = new double[] { getX1(), getY1(), getCtrlX1(), getCtrlY1(),      double[] d = new double[]
459                                  getCtrlX2(), getCtrlY2(), getX2(), getY2(),                   {
460                                  0, 0, 0, 0, 0, 0 };                     getX1(), getY1(), getCtrlX1(), getCtrlY1(), getCtrlX2(),
461                       getCtrlY2(), getX2(), getY2(), 0, 0, 0, 0, 0, 0
462                     };
463      subdivide(d, 0, d, 0, d, 6);      subdivide(d, 0, d, 0, d, 6);
464      if (left != null)      if (left != null)
465        left.setCurve(d, 0);        left.setCurve(d, 0);
# Line 492  public abstract class CubicCurve2D Line 467  public abstract class CubicCurve2D
467        right.setCurve(d, 6);        right.setCurve(d, 6);
468    }    }
469    
   
470    /**    /**
471     * Subdivides a cubic curve into two halves.     * Subdivides a cubic curve into two halves.
472     *     *
# Line 510  public abstract class CubicCurve2D Line 484  public abstract class CubicCurve2D
484     * of <code>src</code>, or <code>null</code> if the caller is not     * of <code>src</code>, or <code>null</code> if the caller is not
485     * interested in the right half.     * interested in the right half.
486     */     */
487    public static void subdivide(CubicCurve2D src,    public static void subdivide(CubicCurve2D src, CubicCurve2D left,
488                                 CubicCurve2D left, CubicCurve2D right)                                 CubicCurve2D right)
489    {    {
490      src.subdivide(left, right);      src.subdivide(left, right);
491    }    }
492    
   
493    /**    /**
494     * Subdivides a cubic curve into two halves, passing all coordinates     * Subdivides a cubic curve into two halves, passing all coordinates
495     * in an array.     * in an array.
# Line 563  public abstract class CubicCurve2D Line 536  public abstract class CubicCurve2D
536     * index where the start point&#x2019;s <i>x</i> coordinate will be     * index where the start point&#x2019;s <i>x</i> coordinate will be
537     * stored.     * stored.
538     */     */
539    public static void subdivide(double[] src, int srcOff,    public static void subdivide(double[] src, int srcOff, double[] left,
540                                 double[] left, int leftOff,                                 int leftOff, double[] right, int rightOff)
                                double[] right, int rightOff)  
541    {    {
542      // To understand this code, please have a look at the image      // To understand this code, please have a look at the image
543      // "CubicCurve2D-3.png" in the sub-directory "doc-files".      // "CubicCurve2D-3.png" in the sub-directory "doc-files".
544      double src_C1_x, src_C1_y, src_C2_x, src_C2_y;      double src_C1_x;
545      double left_P1_x, left_P1_y;      double src_C1_y;
546      double left_C1_x, left_C1_y, left_C2_x, left_C2_y;      double src_C2_x;
547      double right_C1_x, right_C1_y, right_C2_x, right_C2_y;      double src_C2_y;
548      double right_P2_x, right_P2_y;      double left_P1_x;
549      double Mid_x, Mid_y; // Mid = left.P2 = right.P1      double left_P1_y;
550        double left_C1_x;
551        double left_C1_y;
552        double left_C2_x;
553        double left_C2_y;
554        double right_C1_x;
555        double right_C1_y;
556        double right_C2_x;
557        double right_C2_y;
558        double right_P2_x;
559        double right_P2_y;
560        double Mid_x; // Mid = left.P2 = right.P1
561        double Mid_y; // Mid = left.P2 = right.P1
562    
563      left_P1_x = src[srcOff];      left_P1_x = src[srcOff];
564      left_P1_y = src[srcOff + 1];      left_P1_y = src[srcOff + 1];
# Line 599  public abstract class CubicCurve2D Line 583  public abstract class CubicCurve2D
583      Mid_y = (left_C2_y + right_C1_y) / 2;      Mid_y = (left_C2_y + right_C1_y) / 2;
584    
585      if (left != null)      if (left != null)
586      {        {
587        left[leftOff] = left_P1_x;          left[leftOff] = left_P1_x;
588        left[leftOff + 1] = left_P1_y;          left[leftOff + 1] = left_P1_y;
589        left[leftOff + 2] = left_C1_x;          left[leftOff + 2] = left_C1_x;
590        left[leftOff + 3] = left_C1_y;          left[leftOff + 3] = left_C1_y;
591        left[leftOff + 4] = left_C2_x;          left[leftOff + 4] = left_C2_x;
592        left[leftOff + 5] = left_C2_y;          left[leftOff + 5] = left_C2_y;
593        left[leftOff + 6] = Mid_x;          left[leftOff + 6] = Mid_x;
594        left[leftOff + 7] = Mid_y;          left[leftOff + 7] = Mid_y;
595      }        }
596    
597      if (right != null)      if (right != null)
598      {        {
599        right[rightOff] = Mid_x;          right[rightOff] = Mid_x;
600        right[rightOff + 1] = Mid_y;          right[rightOff + 1] = Mid_y;
601        right[rightOff + 2] = right_C1_x;          right[rightOff + 2] = right_C1_x;
602        right[rightOff + 3] = right_C1_y;          right[rightOff + 3] = right_C1_y;
603        right[rightOff + 4] = right_C2_x;          right[rightOff + 4] = right_C2_x;
604        right[rightOff + 5] = right_C2_y;          right[rightOff + 5] = right_C2_y;
605        right[rightOff + 6] = right_P2_x;          right[rightOff + 6] = right_P2_x;
606        right[rightOff + 7] = right_P2_y;          right[rightOff + 7] = right_P2_y;
607      }        }
608    }    }
609    
   
610    /**    /**
611     * Finds the non-complex roots of a cubic equation, placing the     * Finds the non-complex roots of a cubic equation, placing the
612     * results into the same array as the equation coefficients. The     * results into the same array as the equation coefficients. The
# Line 670  public abstract class CubicCurve2D Line 653  public abstract class CubicCurve2D
653      return solveCubic(eqn, eqn);      return solveCubic(eqn, eqn);
654    }    }
655    
   
656    /**    /**
657     * Finds the non-complex roots of a cubic equation. The following     * Finds the non-complex roots of a cubic equation. The following
658     * equation is being solved:     * equation is being solved:
# Line 727  public abstract class CubicCurve2D Line 709  public abstract class CubicCurve2D
709      // The Java implementation is very similar to the GSL code, but      // The Java implementation is very similar to the GSL code, but
710      // not a strict one-to-one copy. For example, GSL would sort the      // not a strict one-to-one copy. For example, GSL would sort the
711      // result.      // result.
712        double a;
713    
714        // Adapted from poly/solve_cubic.c in the GNU Scientific Library
715        // (GSL), revision 1.7 of 2003-07-26. For the original source, see
716        // http://www.gnu.org/software/gsl/
717        //
718        // Brian Gough, the author of that code, has granted the
719        // permission to use it in GNU Classpath under the GNU Classpath
720        // license, and has assigned the copyright to the Free Software
721        // Foundation.
722        //
723        // The Java implementation is very similar to the GSL code, but
724        // not a strict one-to-one copy. For example, GSL would sort the
725        // result.
726        double b;
727    
728        // Adapted from poly/solve_cubic.c in the GNU Scientific Library
729        // (GSL), revision 1.7 of 2003-07-26. For the original source, see
730        // http://www.gnu.org/software/gsl/
731        //
732        // Brian Gough, the author of that code, has granted the
733        // permission to use it in GNU Classpath under the GNU Classpath
734        // license, and has assigned the copyright to the Free Software
735        // Foundation.
736        //
737        // The Java implementation is very similar to the GSL code, but
738        // not a strict one-to-one copy. For example, GSL would sort the
739        // result.
740        double c;
741    
742        // Adapted from poly/solve_cubic.c in the GNU Scientific Library
743        // (GSL), revision 1.7 of 2003-07-26. For the original source, see
744        // http://www.gnu.org/software/gsl/
745        //
746        // Brian Gough, the author of that code, has granted the
747        // permission to use it in GNU Classpath under the GNU Classpath
748        // license, and has assigned the copyright to the Free Software
749        // Foundation.
750        //
751        // The Java implementation is very similar to the GSL code, but
752        // not a strict one-to-one copy. For example, GSL would sort the
753        // result.
754        double q;
755    
756      double a, b, c, q, r, Q, R;      // Adapted from poly/solve_cubic.c in the GNU Scientific Library
757      double c3, Q3, R2, CR2, CQ3;      // (GSL), revision 1.7 of 2003-07-26. For the original source, see
758        // http://www.gnu.org/software/gsl/
759        //
760        // Brian Gough, the author of that code, has granted the
761        // permission to use it in GNU Classpath under the GNU Classpath
762        // license, and has assigned the copyright to the Free Software
763        // Foundation.
764        //
765        // The Java implementation is very similar to the GSL code, but
766        // not a strict one-to-one copy. For example, GSL would sort the
767        // result.
768        double r;
769    
770        // Adapted from poly/solve_cubic.c in the GNU Scientific Library
771        // (GSL), revision 1.7 of 2003-07-26. For the original source, see
772        // http://www.gnu.org/software/gsl/
773        //
774        // Brian Gough, the author of that code, has granted the
775        // permission to use it in GNU Classpath under the GNU Classpath
776        // license, and has assigned the copyright to the Free Software
777        // Foundation.
778        //
779        // The Java implementation is very similar to the GSL code, but
780        // not a strict one-to-one copy. For example, GSL would sort the
781        // result.
782        double Q;
783    
784        // Adapted from poly/solve_cubic.c in the GNU Scientific Library
785        // (GSL), revision 1.7 of 2003-07-26. For the original source, see
786        // http://www.gnu.org/software/gsl/
787        //
788        // Brian Gough, the author of that code, has granted the
789        // permission to use it in GNU Classpath under the GNU Classpath
790        // license, and has assigned the copyright to the Free Software
791        // Foundation.
792        //
793        // The Java implementation is very similar to the GSL code, but
794        // not a strict one-to-one copy. For example, GSL would sort the
795        // result.
796        double R;
797        double c3;
798        double Q3;
799        double R2;
800        double CR2;
801        double CQ3;
802    
803      // If the cubic coefficient is zero, we have a quadratic equation.      // If the cubic coefficient is zero, we have a quadratic equation.
804      c3 = eqn[3];      c3 = eqn[3];
# Line 755  public abstract class CubicCurve2D Line 824  public abstract class CubicCurve2D
824      CQ3 = 2916 * q * q * q;      CQ3 = 2916 * q * q * q;
825    
826      if (R == 0 && Q == 0)      if (R == 0 && Q == 0)
     {  
       // The GNU Scientific Library would return three identical  
       // solutions in this case.  
       res[0] = -a/3;  
       return 1;  
     }  
   
     if (CR2 == CQ3)  
     {  
       /* this test is actually R2 == Q3, written in a form suitable  
          for exact computation with integers */  
   
       /* Due to finite precision some double roots may be missed, and  
          considered to be a pair of complex roots z = x +/- epsilon i  
          close to the real axis. */  
   
       double sqrtQ = Math.sqrt(Q);  
   
       if (R > 0)  
827        {        {
828          res[0] = -2 * sqrtQ - a/3;          // The GNU Scientific Library would return three identical
829          res[1] = sqrtQ - a/3;          // solutions in this case.
830            res[0] = -a / 3;
831            return 1;
832        }        }
833        else  
834        if (CR2 == CQ3)
835        {        {
836          res[0] = -sqrtQ - a/3;          /* this test is actually R2 == Q3, written in a form suitable
837          res[1] = 2 * sqrtQ - a/3;             for exact computation with integers */
838            /* Due to finite precision some double roots may be missed, and
839               considered to be a pair of complex roots z = x +/- epsilon i
840               close to the real axis. */
841            double sqrtQ = Math.sqrt(Q);
842    
843            if (R > 0)
844              {
845                res[0] = -2 * sqrtQ - a / 3;
846                res[1] = sqrtQ - a / 3;
847              }
848            else
849              {
850                res[0] = -sqrtQ - a / 3;
851                res[1] = 2 * sqrtQ - a / 3;
852              }
853            return 2;
854        }        }
       return 2;  
     }  
855    
856      if (CR2 < CQ3) /* equivalent to R2 < Q3 */      if (CR2 < CQ3) /* equivalent to R2 < Q3 */
857      {        {
858        double sqrtQ = Math.sqrt(Q);          double sqrtQ = Math.sqrt(Q);
859        double sqrtQ3 = sqrtQ * sqrtQ * sqrtQ;          double sqrtQ3 = sqrtQ * sqrtQ * sqrtQ;
860        double theta = Math.acos(R / sqrtQ3);          double theta = Math.acos(R / sqrtQ3);
861        double norm = -2 * sqrtQ;          double norm = -2 * sqrtQ;
862        res[0] = norm * Math.cos(theta / 3) - a / 3;          res[0] = norm * Math.cos(theta / 3) - a / 3;
863        res[1] = norm * Math.cos((theta + 2.0 * Math.PI) / 3) - a/3;          res[1] = norm * Math.cos((theta + 2.0 * Math.PI) / 3) - a / 3;
864        res[2] = norm * Math.cos((theta - 2.0 * Math.PI) / 3) - a/3;          res[2] = norm * Math.cos((theta - 2.0 * Math.PI) / 3) - a / 3;
865    
866        // The GNU Scientific Library sorts the results. We don't.          // The GNU Scientific Library sorts the results. We don't.
867        return 3;          return 3;
868      }        }
869    
870      double sgnR = (R >= 0 ? 1 : -1);      double sgnR = (R >= 0 ? 1 : -1);
871      double A = -sgnR * Math.pow(Math.abs(R) + Math.sqrt(R2 - Q3), 1.0/3.0);      double A = -sgnR * Math.pow(Math.abs(R) + Math.sqrt(R2 - Q3), 1.0 / 3.0);
872      double B = Q / A ;      double B = Q / A;
873      res[0] = A + B - a/3;      res[0] = A + B - a / 3;
874      return 1;      return 1;
875    }    }
876    
   
877    /**    /**
878     * Determines whether a position lies inside the area that is bounded     * Determines whether a position lies inside the area bounded
879     * by the curve and the straight line connecting its end points.     * by the curve and the straight line connecting its end points.
880     *     *
881     * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"     * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"
882     * alt="A drawing of the area spanned by the curve" />     * alt="A drawing of the area spanned by the curve" />
883     *     *
884     * <p>The above drawing illustrates in which area points are     * <p>The above drawing illustrates in which area points are
885     * considered &#x201c;contained&#x201d; in a CubicCurve2D.     * considered &#x201c;inside&#x201d; a CubicCurve2D.
886     */     */
887    public boolean contains(double x, double y)    public boolean contains(double x, double y)
888    {    {
889      // XXX Implement.      if (! getBounds2D().contains(x, y))
890      throw new Error("not implemented");        return false;
   }  
891    
892        return ((getAxisIntersections(x, y, true, BIG_VALUE) & 1) != 0);
893      }
894    
895    /**    /**
896     * Determines whether a point lies inside the area that is bounded     * Determines whether a point lies inside the area bounded
897     * by the curve and the straight line connecting its end points.     * by the curve and the straight line connecting its end points.
898     *     *
899     * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"     * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"
900     * alt="A drawing of the area spanned by the curve" />     * alt="A drawing of the area spanned by the curve" />
901     *     *
902     * <p>The above drawing illustrates in which area points are     * <p>The above drawing illustrates in which area points are
903     * considered &#x201c;contained&#x201d; in a CubicCurve2D.     * considered &#x201c;inside&#x201d; a CubicCurve2D.
904     */     */
905    public boolean contains(Point2D p)    public boolean contains(Point2D p)
906    {    {
907      return contains(p.getX(), p.getY());      return contains(p.getX(), p.getY());
908    }    }
909    
910      /**
911       * Determines whether any part of a rectangle is inside the area bounded
912       * by the curve and the straight line connecting its end points.
913       *
914       * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"
915       * alt="A drawing of the area spanned by the curve" />
916       *
917       * <p>The above drawing illustrates in which area points are
918       * considered &#x201c;inside&#x201d; in a CubicCurve2D.
919       * @see #contains(double, double)
920       */
921    public boolean intersects(double x, double y, double w, double h)    public boolean intersects(double x, double y, double w, double h)
922    {    {
923      // XXX Implement.      if (! getBounds2D().contains(x, y, w, h))
924      throw new Error("not implemented");        return false;
925    }  
926        /* Does any edge intersect? */
927        if (getAxisIntersections(x, y, true, w) != 0 /* top */
928            || getAxisIntersections(x, y + h, true, w) != 0 /* bottom */
929            || getAxisIntersections(x + w, y, false, h) != 0 /* right */
930            || getAxisIntersections(x, y, false, h) != 0) /* left */
931          return true;
932    
933        /* No intersections, is any point inside? */
934        if ((getAxisIntersections(x, y, true, BIG_VALUE) & 1) != 0)
935          return true;
936    
937        return false;
938      }
939    
940      /**
941       * Determines whether any part of a Rectangle2D is inside the area bounded
942       * by the curve and the straight line connecting its end points.
943       * @see #intersects(double, double, double, double)
944       */
945    public boolean intersects(Rectangle2D r)    public boolean intersects(Rectangle2D r)
946    {    {
947      return intersects(r.getX(), r.getY(), r.getWidth(), r.getHeight());      return intersects(r.getX(), r.getY(), r.getWidth(), r.getHeight());
948    }    }
949    
950      /**
951       * Determine whether a rectangle is entirely inside the area that is bounded
952       * by the curve and the straight line connecting its end points.
953       *
954       * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"
955       * alt="A drawing of the area spanned by the curve" />
956       *
957       * <p>The above drawing illustrates in which area points are
958       * considered &#x201c;inside&#x201d; a CubicCurve2D.
959       * @see #contains(double, double)
960       */
961    public boolean contains(double x, double y, double w, double h)    public boolean contains(double x, double y, double w, double h)
962    {    {
963      // XXX Implement.      if (! getBounds2D().intersects(x, y, w, h))
964      throw new Error("not implemented");        return false;
965    }  
966        /* Does any edge intersect? */
967        if (getAxisIntersections(x, y, true, w) != 0 /* top */
968            || getAxisIntersections(x, y + h, true, w) != 0 /* bottom */
969            || getAxisIntersections(x + w, y, false, h) != 0 /* right */
970            || getAxisIntersections(x, y, false, h) != 0) /* left */
971          return false;
972    
973        /* No intersections, is any point inside? */
974        if ((getAxisIntersections(x, y, true, BIG_VALUE) & 1) != 0)
975          return true;
976    
977        return false;
978      }
979    
980      /**
981       * Determine whether a Rectangle2D is entirely inside the area that is
982       * bounded by the curve and the straight line connecting its end points.
983       *
984       * <p><img src="doc-files/CubicCurve2D-5.png" width="350" height="180"
985       * alt="A drawing of the area spanned by the curve" />
986       *
987       * <p>The above drawing illustrates in which area points are
988       * considered &#x201c;inside&#x201d; a CubicCurve2D.
989       * @see #contains(double, double)
990       */
991    public boolean contains(Rectangle2D r)    public boolean contains(Rectangle2D r)
992    {    {
993      return contains(r.getX(), r.getY(), r.getWidth(), r.getHeight());      return contains(r.getX(), r.getY(), r.getWidth(), r.getHeight());
994    }    }
995    
   
996    /**    /**
997     * Determines the smallest rectangle that encloses the     * Determines the smallest rectangle that encloses the
998     * curve&#x2019;s start, end and control points. As the illustration     * curve&#x2019;s start, end and control points.
    * below shows, the invisible control points may cause the bounds to  
    * be much larger than the area that is actually covered by the  
    * curve.  
    *  
    * <p><img src="doc-files/CubicCurve2D-2.png" width="350" height="180"  
    * alt="An illustration of the bounds of a CubicCurve2D" />  
999     */     */
1000    public Rectangle getBounds()    public Rectangle getBounds()
1001    {    {
1002      return getBounds2D().getBounds();      return getBounds2D().getBounds();
1003    }    }
1004    
   
1005    public PathIterator getPathIterator(final AffineTransform at)    public PathIterator getPathIterator(final AffineTransform at)
1006    {    {
1007      return new PathIterator()      return new PathIterator()
     {  
       /** Current coordinate. */  
       private int current = 0;  
   
       public int getWindingRule()  
       {  
         return WIND_NON_ZERO;  
       }  
   
       public boolean isDone()  
       {  
         return current >= 2;  
       }  
   
       public void next()  
       {  
         current++;  
       }  
   
       public int currentSegment(float[] coords)  
1008        {        {
1009          int result;          /** Current coordinate. */
1010          switch (current)          private int current = 0;
           {  
           case 0:  
             coords[0] = (float) getX1();  
             coords[1] = (float) getY1();  
             result = SEG_MOVETO;  
             break;              
           case 1:  
             coords[0] = (float) getCtrlX1();  
             coords[1] = (float) getCtrlY1();  
             coords[2] = (float) getCtrlX2();  
             coords[3] = (float) getCtrlY2();  
             coords[4] = (float) getX2();  
             coords[5] = (float) getY2();  
             result = SEG_CUBICTO;  
             break;  
           default:  
             throw new NoSuchElementException("cubic iterator out of bounds");              
           }  
         if (at != null)  
           at.transform(coords, 0, coords, 0, 3);  
         return result;  
       }  
1011    
1012        public int currentSegment(double[] coords)          public int getWindingRule()
1013        {          {
1014          int result;            return WIND_NON_ZERO;
1015          switch (current)          }
1016            {  
1017            case 0:          public boolean isDone()
1018              coords[0] = getX1();          {
1019              coords[1] = getY1();            return current >= 2;
1020              result = SEG_MOVETO;          }
1021              break;  
1022            case 1:          public void next()
1023              coords[0] = getCtrlX1();          {
1024              coords[1] = getCtrlY1();            current++;
1025              coords[2] = getCtrlX2();          }
1026              coords[3] = getCtrlY2();  
1027              coords[4] = getX2();          public int currentSegment(float[] coords)
1028              coords[5] = getY2();          {
1029              result = SEG_CUBICTO;            int result;
1030              break;            switch (current)
1031            default:              {
1032              throw new NoSuchElementException("cubic iterator out of bounds");              case 0:
1033            }                        coords[0] = (float) getX1();
1034          if (at != null)                coords[1] = (float) getY1();
1035            at.transform(coords, 0, coords, 0, 3);                result = SEG_MOVETO;
1036          return result;                break;
1037        }              case 1:
1038      };                coords[0] = (float) getCtrlX1();
1039                  coords[1] = (float) getCtrlY1();
1040                  coords[2] = (float) getCtrlX2();
1041                  coords[3] = (float) getCtrlY2();
1042                  coords[4] = (float) getX2();
1043                  coords[5] = (float) getY2();
1044                  result = SEG_CUBICTO;
1045                  break;
1046                default:
1047                  throw new NoSuchElementException("cubic iterator out of bounds");
1048                }
1049              if (at != null)
1050                at.transform(coords, 0, coords, 0, 3);
1051              return result;
1052            }
1053    
1054            public int currentSegment(double[] coords)
1055            {
1056              int result;
1057              switch (current)
1058                {
1059                case 0:
1060                  coords[0] = getX1();
1061                  coords[1] = getY1();
1062                  result = SEG_MOVETO;
1063                  break;
1064                case 1:
1065                  coords[0] = getCtrlX1();
1066                  coords[1] = getCtrlY1();
1067                  coords[2] = getCtrlX2();
1068                  coords[3] = getCtrlY2();
1069                  coords[4] = getX2();
1070                  coords[5] = getY2();
1071                  result = SEG_CUBICTO;
1072                  break;
1073                default:
1074                  throw new NoSuchElementException("cubic iterator out of bounds");
1075                }
1076              if (at != null)
1077                at.transform(coords, 0, coords, 0, 3);
1078              return result;
1079            }
1080          };
1081    }    }
1082    
   
1083    public PathIterator getPathIterator(AffineTransform at, double flatness)    public PathIterator getPathIterator(AffineTransform at, double flatness)
1084    {    {
1085      return new FlatteningPathIterator(getPathIterator(at), flatness);      return new FlatteningPathIterator(getPathIterator(at), flatness);
1086    }    }
1087    
   
1088    /**    /**
1089     * Create a new curve with the same contents as this one.     * Create a new curve with the same contents as this one.
1090     *     *
# Line 976  public abstract class CubicCurve2D Line 1093  public abstract class CubicCurve2D
1093    public Object clone()    public Object clone()
1094    {    {
1095      try      try
1096      {        {
1097        return super.clone();          return super.clone();
1098      }        }
1099      catch (CloneNotSupportedException e)      catch (CloneNotSupportedException e)
1100      {        {
1101        throw (Error) new InternalError().initCause(e); // Impossible          throw (Error) new InternalError().initCause(e); // Impossible
1102      }        }
1103    }    }
1104    
1105      /**
1106       * Helper method used by contains() and intersects() methods, that
1107       * returns the number of curve/line intersections on a given axis
1108       * extending from a certain point.
1109       *
1110       * @param x x coordinate of the origin point
1111       * @param y y coordinate of the origin point
1112       * @param useYaxis axis used, if true the positive Y axis is used,
1113       * false uses the positive X axis.
1114       *
1115       * This is an implementation of the line-crossings algorithm,
1116       * Detailed in an article on Eric Haines' page:
1117       * http://www.acm.org/tog/editors/erich/ptinpoly/
1118       *
1119       * A special-case not adressed in this code is self-intersections
1120       * of the curve, e.g. if the axis intersects the self-itersection,
1121       * the degenerate roots of the polynomial will erroneously count as
1122       * a single intersection of the curve, and not two.
1123       */
1124      private int getAxisIntersections(double x, double y, boolean useYaxis,
1125                                       double distance)
1126      {
1127        int nCrossings = 0;
1128        double a0;
1129        double a1;
1130        double a2;
1131        double a3;
1132        double b0;
1133        double b1;
1134        double b2;
1135        double b3;
1136        double[] r = new double[4];
1137        int nRoots;
1138    
1139        a0 = a3 = 0.0;
1140    
1141        if (useYaxis)
1142          {
1143            a0 = getY1() - y;
1144            a1 = getCtrlY1() - y;
1145            a2 = getCtrlY2() - y;
1146            a3 = getY2() - y;
1147            b0 = getX1() - x;
1148            b1 = getCtrlX1() - x;
1149            b2 = getCtrlX2() - x;
1150            b3 = getX2() - x;
1151          }
1152        else
1153          {
1154            a0 = getX1() - x;
1155            a1 = getCtrlX1() - x;
1156            a2 = getCtrlX2() - x;
1157            a3 = getX2() - x;
1158            b0 = getY1() - y;
1159            b1 = getCtrlY1() - y;
1160            b2 = getCtrlY2() - y;
1161            b3 = getY2() - y;
1162          }
1163    
1164        /* If the axis intersects a start/endpoint, shift it up by some small
1165           amount to guarantee the line is 'inside'
1166           If this is not done, bad behaviour may result for points on that axis.*/
1167        if (a0 == 0.0 || a3 == 0.0)
1168          {
1169            double small = getFlatness() * (1E-10);
1170            if (a0 == 0.0)
1171              a0 += small;
1172            if (a3 == 0.0)
1173              a3 += small;
1174          }
1175    
1176        if (useYaxis)
1177          {
1178            if (Line2D.linesIntersect(b0, a0, b3, a3, 0.0, 0.0, distance, 0.0))
1179              nCrossings++;
1180          }
1181        else
1182          {
1183            if (Line2D.linesIntersect(a0, b0, a3, b3, 0.0, 0.0, 0.0, distance))
1184              nCrossings++;
1185          }
1186    
1187        r[0] = a0;
1188        r[1] = 3 * (a1 - a0);
1189        r[2] = 3 * (a2 + a0 - 2 * a1);
1190        r[3] = a3 - 3 * a2 + 3 * a1 - a0;
1191    
1192        if ((nRoots = solveCubic(r)) != 0)
1193          for (int i = 0; i < nRoots; i++)
1194            {
1195              double t = r[i];
1196              if (t >= 0.0 && t <= 1.0)
1197                {
1198                  double crossing = -(t * t * t) * (b0 - 3 * b1 + 3 * b2 - b3)
1199                                    + 3 * t * t * (b0 - 2 * b1 + b2)
1200                                    + 3 * t * (b1 - b0) + b0;
1201                  if (crossing > 0.0 && crossing <= distance)
1202                    nCrossings++;
1203                }
1204            }
1205    
1206        return (nCrossings);
1207      }
1208    
1209    /**    /**
1210     * A two-dimensional curve that is parameterized with a cubic     * A two-dimensional curve that is parameterized with a cubic
# Line 996  public abstract class CubicCurve2D Line 1216  public abstract class CubicCurve2D
1216     * @author Eric Blake (ebb9@email.byu.edu)     * @author Eric Blake (ebb9@email.byu.edu)
1217     * @author Sascha Brawer (brawer@dandelis.ch)     * @author Sascha Brawer (brawer@dandelis.ch)
1218     */     */
1219    public static class Double    public static class Double extends CubicCurve2D
     extends CubicCurve2D  
1220    {    {
1221      /**      /**
1222       * The <i>x</i> coordinate of the curve&#x2019;s start point.       * The <i>x</i> coordinate of the curve&#x2019;s start point.
1223       */       */
1224      public double x1;      public double x1;
1225    
   
1226      /**      /**
1227       * The <i>y</i> coordinate of the curve&#x2019;s start point.       * The <i>y</i> coordinate of the curve&#x2019;s start point.
1228       */       */
1229      public double y1;      public double y1;
1230    
   
1231      /**      /**
1232       * The <i>x</i> coordinate of the curve&#x2019;s first control point.       * The <i>x</i> coordinate of the curve&#x2019;s first control point.
1233       */       */
1234      public double ctrlx1;      public double ctrlx1;
1235    
   
1236      /**      /**
1237       * The <i>y</i> coordinate of the curve&#x2019;s first control point.       * The <i>y</i> coordinate of the curve&#x2019;s first control point.
1238       */       */
1239      public double ctrly1;      public double ctrly1;
1240    
   
1241      /**      /**
1242       * The <i>x</i> coordinate of the curve&#x2019;s second control point.       * The <i>x</i> coordinate of the curve&#x2019;s second control point.
1243       */       */
1244      public double ctrlx2;      public double ctrlx2;
1245    
   
1246      /**      /**
1247       * The <i>y</i> coordinate of the curve&#x2019;s second control point.       * The <i>y</i> coordinate of the curve&#x2019;s second control point.
1248       */       */
1249      public double ctrly2;      public double ctrly2;
1250    
   
1251      /**      /**
1252       * The <i>x</i> coordinate of the curve&#x2019;s end point.       * The <i>x</i> coordinate of the curve&#x2019;s end point.
1253       */       */
1254      public double x2;      public double x2;
1255    
   
1256      /**      /**
1257       * The <i>y</i> coordinate of the curve&#x2019;s end point.       * The <i>y</i> coordinate of the curve&#x2019;s end point.
1258       */       */
1259      public double y2;      public double y2;
1260    
   
1261      /**      /**
1262       * Constructs a new CubicCurve2D that stores its coordinate values       * Constructs a new CubicCurve2D that stores its coordinate values
1263       * in double-precision floating-point format. All points are       * in double-precision floating-point format. All points are
# Line 1056  public abstract class CubicCurve2D Line 1267  public abstract class CubicCurve2D
1267      {      {
1268      }      }
1269    
   
1270      /**      /**
1271       * Constructs a new CubicCurve2D that stores its coordinate values       * Constructs a new CubicCurve2D that stores its coordinate values
1272       * in double-precision floating-point format, specifying the       * in double-precision floating-point format, specifying the
# Line 1089  public abstract class CubicCurve2D Line 1299  public abstract class CubicCurve2D
1299       * @param y2 the <i>y</i> coordinate of the curve&#x2019;s end       * @param y2 the <i>y</i> coordinate of the curve&#x2019;s end
1300       * point.       * point.
1301       */       */
1302      public Double(double x1, double y1, double cx1, double cy1,      public Double(double x1, double y1, double cx1, double cy1, double cx2,
1303                    double cx2, double cy2, double x2, double y2)                    double cy2, double x2, double y2)
1304      {      {
1305        this.x1 = x1;        this.x1 = x1;
1306        this.y1 = y1;        this.y1 = y1;
# Line 1102  public abstract class CubicCurve2D Line 1312  public abstract class CubicCurve2D
1312        this.y2 = y2;        this.y2 = y2;
1313      }      }
1314    
   
1315      /**      /**
1316       * Returns the <i>x</i> coordinate of the curve&#x2019;s start       * Returns the <i>x</i> coordinate of the curve&#x2019;s start
1317       * point.       * point.
# Line 1112  public abstract class CubicCurve2D Line 1321  public abstract class CubicCurve2D
1321        return x1;        return x1;
1322      }      }
1323    
   
1324      /**      /**
1325       * Returns the <i>y</i> coordinate of the curve&#x2019;s start       * Returns the <i>y</i> coordinate of the curve&#x2019;s start
1326       * point.       * point.
# Line 1122  public abstract class CubicCurve2D Line 1330  public abstract class CubicCurve2D
1330        return y1;        return y1;
1331      }      }
1332    
   
1333      /**      /**
1334       * Returns the curve&#x2019;s start point.       * Returns the curve&#x2019;s start point.
1335       */       */
# Line 1131  public abstract class CubicCurve2D Line 1338  public abstract class CubicCurve2D
1338        return new Point2D.Double(x1, y1);        return new Point2D.Double(x1, y1);
1339      }      }
1340    
   
1341      /**      /**
1342       * Returns the <i>x</i> coordinate of the curve&#x2019;s first       * Returns the <i>x</i> coordinate of the curve&#x2019;s first
1343       * control point.       * control point.
# Line 1141  public abstract class CubicCurve2D Line 1347  public abstract class CubicCurve2D
1347        return ctrlx1;        return ctrlx1;
1348      }      }
1349    
   
1350      /**      /**
1351       * Returns the <i>y</i> coordinate of the curve&#x2019;s first       * Returns the <i>y</i> coordinate of the curve&#x2019;s first
1352       * control point.       * control point.
# Line 1151  public abstract class CubicCurve2D Line 1356  public abstract class CubicCurve2D
1356        return ctrly1;        return ctrly1;
1357      }      }
1358    
   
1359      /**      /**
1360       * Returns the curve&#x2019;s first control point.       * Returns the curve&#x2019;s first control point.
1361       */       */
# Line 1160  public abstract class CubicCurve2D Line 1364  public abstract class CubicCurve2D
1364        return new Point2D.Double(ctrlx1, ctrly1);        return new Point2D.Double(ctrlx1, ctrly1);
1365      }      }
1366    
   
1367      /**      /**
1368       * Returns the <i>x</i> coordinate of the curve&#x2019;s second       * Returns the <i>x</i> coordinate of the curve&#x2019;s second
1369       * control point.       * control point.
# Line 1170  public abstract class CubicCurve2D Line 1373  public abstract class CubicCurve2D
1373        return ctrlx2;        return ctrlx2;
1374      }      }
1375    
   
1376      /**      /**
1377       * Returns the <i>y</i> coordinate of the curve&#x2019;s second       * Returns the <i>y</i> coordinate of the curve&#x2019;s second
1378       * control point.       * control point.
# Line 1180  public abstract class CubicCurve2D Line 1382  public abstract class CubicCurve2D
1382        return ctrly2;        return ctrly2;
1383      }      }
1384    
   
1385      /**      /**
1386       * Returns the curve&#x2019;s second control point.       * Returns the curve&#x2019;s second control point.
1387       */       */
# Line 1189  public abstract class CubicCurve2D Line 1390  public abstract class CubicCurve2D
1390        return new Point2D.Double(ctrlx2, ctrly2);        return new Point2D.Double(ctrlx2, ctrly2);
1391      }      }
1392    
   
1393      /**      /**
1394       * Returns the <i>x</i> coordinate of the curve&#x2019;s end       * Returns the <i>x</i> coordinate of the curve&#x2019;s end
1395       * point.       * point.
# Line 1199  public abstract class CubicCurve2D Line 1399  public abstract class CubicCurve2D
1399        return x2;        return x2;
1400      }      }
1401    
   
1402      /**      /**
1403       * Returns the <i>y</i> coordinate of the curve&#x2019;s end       * Returns the <i>y</i> coordinate of the curve&#x2019;s end
1404       * point.       * point.
# Line 1209  public abstract class CubicCurve2D Line 1408  public abstract class CubicCurve2D
1408        return y2;        return y2;
1409      }      }
1410    
   
1411      /**      /**
1412       * Returns the curve&#x2019;s end point.       * Returns the curve&#x2019;s end point.
1413       */       */
# Line 1218  public abstract class CubicCurve2D Line 1416  public abstract class CubicCurve2D
1416        return new Point2D.Double(x2, y2);        return new Point2D.Double(x2, y2);
1417      }      }
1418    
   
1419      /**      /**
1420       * Changes the curve geometry, separately specifying each coordinate       * Changes the curve geometry, separately specifying each coordinate
1421       * value.       * value.
# Line 1263  public abstract class CubicCurve2D Line 1460  public abstract class CubicCurve2D
1460        this.y2 = y2;        this.y2 = y2;
1461      }      }
1462    
   
1463      /**      /**
1464       * Determines the smallest rectangle that encloses the       * Determines the smallest rectangle that encloses the
1465       * curve&#x2019;s start, end and control points. As the       * curve&#x2019;s start, end and control points. As the
# Line 1284  public abstract class CubicCurve2D Line 1480  public abstract class CubicCurve2D
1480      }      }
1481    }    }
1482    
   
1483    /**    /**
1484     * A two-dimensional curve that is parameterized with a cubic     * A two-dimensional curve that is parameterized with a cubic
1485     * function and stores coordinate values in single-precision     * function and stores coordinate values in single-precision
# Line 1295  public abstract class CubicCurve2D Line 1490  public abstract class CubicCurve2D
1490     * @author Eric Blake (ebb9@email.byu.edu)     * @author Eric Blake (ebb9@email.byu.edu)
1491     * @author Sascha Brawer (brawer@dandelis.ch)     * @author Sascha Brawer (brawer@dandelis.ch)
1492     */     */
1493    public static class Float    public static class Float extends CubicCurve2D
     extends CubicCurve2D  
1494    {    {
1495      /**      /**
1496       * The <i>x</i> coordinate of the curve&#x2019;s start point.       * The <i>x</i> coordinate of the curve&#x2019;s start point.
1497       */       */
1498      public float x1;      public float x1;
1499    
   
1500      /**      /**
1501       * The <i>y</i> coordinate of the curve&#x2019;s start point.       * The <i>y</i> coordinate of the curve&#x2019;s start point.
1502       */       */
1503      public float y1;      public float y1;
1504    
   
1505      /**      /**
1506       * The <i>x</i> coordinate of the curve&#x2019;s first control point.       * The <i>x</i> coordinate of the curve&#x2019;s first control point.
1507       */       */
1508      public float ctrlx1;      public float ctrlx1;
1509    
   
1510      /**      /**
1511       * The <i>y</i> coordinate of the curve&#x2019;s first control point.       * The <i>y</i> coordinate of the curve&#x2019;s first control point.
1512       */       */
1513      public float ctrly1;      public float ctrly1;
1514    
   
1515      /**      /**
1516       * The <i>x</i> coordinate of the curve&#x2019;s second control point.       * The <i>x</i> coordinate of the curve&#x2019;s second control point.
1517       */       */
1518      public float ctrlx2;      public float ctrlx2;
1519    
   
1520      /**      /**
1521       * The <i>y</i> coordinate of the curve&#x2019;s second control point.       * The <i>y</i> coordinate of the curve&#x2019;s second control point.
1522       */       */
1523      public float ctrly2;      public float ctrly2;
1524    
   
1525      /**      /**
1526       * The <i>x</i> coordinate of the curve&#x2019;s end point.       * The <i>x</i> coordinate of the curve&#x2019;s end point.
1527       */       */
1528      public float x2;      public float x2;
1529    
   
1530      /**      /**
1531       * The <i>y</i> coordinate of the curve&#x2019;s end point.       * The <i>y</i> coordinate of the curve&#x2019;s end point.
1532       */       */
1533      public float y2;      public float y2;
1534    
   
1535      /**      /**
1536       * Constructs a new CubicCurve2D that stores its coordinate values       * Constructs a new CubicCurve2D that stores its coordinate values
1537       * in single-precision floating-point format. All points are       * in single-precision floating-point format. All points are
# Line 1355  public abstract class CubicCurve2D Line 1541  public abstract class CubicCurve2D
1541      {      {
1542      }      }
1543    
   
1544      /**      /**
1545       * Constructs a new CubicCurve2D that stores its coordinate values       * Constructs a new CubicCurve2D that stores its coordinate values
1546       * in single-precision floating-point format, specifying the       * in single-precision floating-point format, specifying the
# Line 1388  public abstract class CubicCurve2D Line 1573  public abstract class CubicCurve2D
1573       * @param y2 the <i>y</i> coordinate of the curve&#x2019;s end       * @param y2 the <i>y</i> coordinate of the curve&#x2019;s end
1574       * point.       * point.
1575       */       */
1576      public Float(float x1, float y1, float cx1, float cy1,      public Float(float x1, float y1, float cx1, float cy1, float cx2,
1577                   float cx2, float cy2, float x2, float y2)                   float cy2, float x2, float y2)
1578      {      {
1579        this.x1 = x1;        this.x1 = x1;
1580        this.y1 = y1;        this.y1 = y1;
# Line 1401  public abstract class CubicCurve2D Line 1586  public abstract class CubicCurve2D
1586        this.y2 = y2;        this.y2 = y2;
1587      }      }
1588    
   
1589      /**      /**
1590       * Returns the <i>x</i> coordinate of the curve&#x2019;s start       * Returns the <i>x</i> coordinate of the curve&#x2019;s start
1591       * point.       * point.
# Line 1411  public abstract class CubicCurve2D Line 1595  public abstract class CubicCurve2D
1595        return x1;        return x1;
1596      }      }
1597    
   
1598      /**      /**
1599       * Returns the <i>y</i> coordinate of the curve&#x2019;s start       * Returns the <i>y</i> coordinate of the curve&#x2019;s start
1600       * point.       * point.
# Line 1421  public abstract class CubicCurve2D Line 1604  public abstract class CubicCurve2D
1604        return y1;        return y1;
1605      }      }
1606    
   
1607      /**      /**
1608       * Returns the curve&#x2019;s start point.       * Returns the curve&#x2019;s start point.
1609       */       */
# Line 1430  public abstract class CubicCurve2D Line 1612  public abstract class CubicCurve2D
1612        return new Point2D.Float(x1, y1);        return new Point2D.Float(x1, y1);
1613      }      }
1614    
   
1615      /**      /**
1616       * Returns the <i>x</i> coordinate of the curve&#x2019;s first       * Returns the <i>x</i> coordinate of the curve&#x2019;s first
1617       * control point.       * control point.
# Line 1440  public abstract class CubicCurve2D Line 1621  public abstract class CubicCurve2D
1621        return ctrlx1;        return ctrlx1;
1622      }      }
1623    
   
1624      /**      /**
1625       * Returns the <i>y</i> coordinate of the curve&#x2019;s first       * Returns the <i>y</i> coordinate of the curve&#x2019;s first
1626       * control point.       * control point.
# Line 1450  public abstract class CubicCurve2D Line 1630  public abstract class CubicCurve2D
1630        return ctrly1;        return ctrly1;
1631      }      }
1632    
   
1633      /**      /**
1634       * Returns the curve&#x2019;s first control point.       * Returns the curve&#x2019;s first control point.
1635       */       */
# Line 1459  public abstract class CubicCurve2D Line 1638  public abstract class CubicCurve2D
1638        return new Point2D.Float(ctrlx1, ctrly1);        return new Point2D.Float(ctrlx1, ctrly1);
1639      }      }
1640    
   
1641      /**      /**
1642       * Returns the <i>s</i> coordinate of the curve&#x2019;s second       * Returns the <i>s</i> coordinate of the curve&#x2019;s second
1643       * control point.       * control point.
# Line 1469  public abstract class CubicCurve2D Line 1647  public abstract class CubicCurve2D
1647        return ctrlx2;        return ctrlx2;
1648      }      }
1649    
   
1650      /**      /**
1651       * Returns the <i>y</i> coordinate of the curve&#x2019;s second       * Returns the <i>y</i> coordinate of the curve&#x2019;s second
1652       * control point.       * control point.
# Line 1479  public abstract class CubicCurve2D Line 1656  public abstract class CubicCurve2D
1656        return ctrly2;        return ctrly2;
1657      }      }
1658    
   
1659      /**      /**
1660       * Returns the curve&#x2019;s second control point.       * Returns the curve&#x2019;s second control point.
1661       */       */
# Line 1488  public abstract class CubicCurve2D Line 1664  public abstract class CubicCurve2D
1664        return new Point2D.Float(ctrlx2, ctrly2);        return new Point2D.Float(ctrlx2, ctrly2);
1665      }      }
1666    
   
1667      /**      /**
1668       * Returns the <i>x</i> coordinate of the curve&#x2019;s end       * Returns the <i>x</i> coordinate of the curve&#x2019;s end
1669       * point.       * point.
# Line 1498  public abstract class CubicCurve2D Line 1673  public abstract class CubicCurve2D
1673        return x2;        return x2;
1674      }      }
1675    
   
1676      /**      /**
1677       * Returns the <i>y</i> coordinate of the curve&#x2019;s end       * Returns the <i>y</i> coordinate of the curve&#x2019;s end
1678       * point.       * point.
# Line 1508  public abstract class CubicCurve2D Line 1682  public abstract class CubicCurve2D
1682        return y2;        return y2;
1683      }      }
1684    
   
1685      /**      /**
1686       * Returns the curve&#x2019;s end point.       * Returns the curve&#x2019;s end point.
1687       */       */
# Line 1517  public abstract class CubicCurve2D Line 1690  public abstract class CubicCurve2D
1690        return new Point2D.Float(x2, y2);        return new Point2D.Float(x2, y2);
1691      }      }
1692    
   
1693      /**      /**
1694       * Changes the curve geometry, separately specifying each coordinate       * Changes the curve geometry, separately specifying each coordinate
1695       * value as a double-precision floating-point number.       * value as a double-precision floating-point number.
# Line 1562  public abstract class CubicCurve2D Line 1734  public abstract class CubicCurve2D
1734        this.y2 = (float) y2;        this.y2 = (float) y2;
1735      }      }
1736    
   
1737      /**      /**
1738       * Changes the curve geometry, separately specifying each coordinate       * Changes the curve geometry, separately specifying each coordinate
1739       * value as a single-precision floating-point number.       * value as a single-precision floating-point number.
# Line 1594  public abstract class CubicCurve2D Line 1765  public abstract class CubicCurve2D
1765       * @param y2 the <i>y</i> coordinate of the curve&#x2019;s new end       * @param y2 the <i>y</i> coordinate of the curve&#x2019;s new end
1766       * point.       * point.
1767       */       */
1768      public void setCurve(float x1, float y1, float cx1, float cy1,      public void setCurve(float x1, float y1, float cx1, float cy1, float cx2,
1769                           float cx2, float cy2, float x2, float y2)                           float cy2, float x2, float y2)
1770      {      {
1771        this.x1 = x1;        this.x1 = x1;
1772        this.y1 = y1;        this.y1 = y1;
# Line 1607  public abstract class CubicCurve2D Line 1778  public abstract class CubicCurve2D
1778        this.y2 = y2;        this.y2 = y2;
1779      }      }
1780    
   
1781      /**      /**
1782       * Determines the smallest rectangle that encloses the       * Determines the smallest rectangle that encloses the
1783       * curve&#x2019;s start, end and control points. As the       * curve&#x2019;s start, end and control points. As the

Legend:
Removed from v.1.6  
changed lines
  Added in v.1.7

savannah-hackers-public@gnu.org
ViewVC Help
Powered by ViewVC 1.1.26