mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-03-16 09:30:38 +08:00
Makefile.in: Rebuilt.
* Makefile.in: Rebuilt. * Makefile.am (awt_java_source_files): Added Polygon.java. * java/awt/Polygon.java: New file. * java/awt/geom/AffineTransform.java (setToRotation(double,double,double)): New method. (AffineTransform): Set type to TYPE_GENERAL_TRANSFORM. (setToShear): Likewise. From-SVN: r41954
This commit is contained in:
parent
d466c016c5
commit
dac975d3d9
@ -1,3 +1,14 @@
|
||||
2001-05-10 Tom Tromey <tromey@redhat.com>
|
||||
|
||||
* Makefile.in: Rebuilt.
|
||||
* Makefile.am (awt_java_source_files): Added Polygon.java.
|
||||
* java/awt/Polygon.java: New file.
|
||||
|
||||
* java/awt/geom/AffineTransform.java
|
||||
(setToRotation(double,double,double)): New method.
|
||||
(AffineTransform): Set type to TYPE_GENERAL_TRANSFORM.
|
||||
(setToShear): Likewise.
|
||||
|
||||
2001-05-10 Tom Tromey <tromey@redhat.com>
|
||||
|
||||
* java/util/GregorianCalendar.java: Imported from Classpath.
|
||||
|
422
libjava/java/awt/Polygon.java
Normal file
422
libjava/java/awt/Polygon.java
Normal file
@ -0,0 +1,422 @@
|
||||
/* Copyright (C) 2001 Free Software Foundation
|
||||
|
||||
This file is part of libjava.
|
||||
|
||||
This software is copyrighted work licensed under the terms of the
|
||||
Libjava License. Please consult the file "LIBJAVA_LICENSE" for
|
||||
details. */
|
||||
|
||||
package java.awt;
|
||||
|
||||
import java.awt.geom.*;
|
||||
import java.io.Serializable;
|
||||
import java.util.Arrays;
|
||||
|
||||
/**
|
||||
* @author Tom Tromey <tromey@redhat.com>
|
||||
* @date May 10, 2001
|
||||
*/
|
||||
|
||||
/** The Polygon class represents a closed region whose boundary is
|
||||
made of line segments. The Polygon is defined by its vertices. */
|
||||
public class Polygon implements Shape, Serializable
|
||||
{
|
||||
/** The bounds of the polygon. This is null until the bounds have
|
||||
* been computed for the first time; then it is correctly
|
||||
* maintained whenever it is modified. */
|
||||
protected Rectangle bounds;
|
||||
|
||||
/** The number of points in the polygon. */
|
||||
public int npoints;
|
||||
|
||||
/** The x coordinates of the points. */
|
||||
public int[] xpoints;
|
||||
|
||||
/** The y coordinates of the points. */
|
||||
public int[] ypoints;
|
||||
|
||||
/** Create a new, empty Polygon. */
|
||||
public Polygon ()
|
||||
{
|
||||
this.xpoints = new int[0];
|
||||
this.ypoints = new int[0];
|
||||
this.npoints = 0;
|
||||
}
|
||||
|
||||
/** Create a new Polygon from the given vertices.
|
||||
* @param xpoints The x coordinates
|
||||
* @param ypoints The y coordinates
|
||||
* @param npoints The number of points
|
||||
*/
|
||||
public Polygon (int[] xpoints, int[] ypoints, int npoints)
|
||||
{
|
||||
// We make explicit copies instead of relying on clone so that we
|
||||
// ensure the new arrays are the same size.
|
||||
this.xpoints = new int[npoints];
|
||||
this.ypoints = new int[npoints];
|
||||
System.arraycopy (xpoints, 0, this.xpoints, 0, npoints);
|
||||
System.arraycopy (ypoints, 0, this.ypoints, 0, npoints);
|
||||
}
|
||||
|
||||
/** Append the specified point to this Polygon.
|
||||
* @param x The x coordinate
|
||||
* @param y The y coordinate
|
||||
*/
|
||||
public void addPoint (int x, int y)
|
||||
{
|
||||
int[] newx = new int[npoints + 1];
|
||||
System.arraycopy (xpoints, 0, newx, 0, npoints);
|
||||
int[] newy = new int[npoints + 1];
|
||||
System.arraycopy (ypoints, 0, newy, 0, npoints);
|
||||
newx[npoints] = x;
|
||||
newy[npoints] = y;
|
||||
++npoints;
|
||||
xpoints = newx;
|
||||
ypoints = newy;
|
||||
|
||||
// It is simpler to just recompute.
|
||||
if (bounds != null)
|
||||
computeBoundingBox ();
|
||||
}
|
||||
|
||||
/** Return true if the indicated point is inside this Polygon.
|
||||
* This uses an even-odd rule to determine insideness.
|
||||
* @param x The x coordinate
|
||||
* @param y The y coordinate
|
||||
* @returns true if the point is contained by this Polygon.
|
||||
*/
|
||||
public boolean contains (double x, double y)
|
||||
{
|
||||
// What we do is look at each line segment. If the line segment
|
||||
// crosses the "scan line" at y at a point x' < x, then we
|
||||
// increment our counter. At the end, an even number means the
|
||||
// point is outside the polygon. Instead of a number, though, we
|
||||
// use a boolean.
|
||||
boolean inside = false;
|
||||
for (int i = 0; i < npoints; ++i)
|
||||
{
|
||||
// Handle the wrap case.
|
||||
int x2 = (i == npoints) ? xpoints[0] : xpoints[i + 1];
|
||||
int y2 = (i == npoints) ? ypoints[0] : ypoints[i + 1];
|
||||
|
||||
if (ypoints[i] == y2)
|
||||
{
|
||||
// We ignore horizontal lines. This might give weird
|
||||
// results in some situations -- ?
|
||||
continue;
|
||||
}
|
||||
|
||||
double t = (y - ypoints[i]) / (double) (y2 - ypoints[i]);
|
||||
double x3 = xpoints[i] + t * (x2 - xpoints[i]);
|
||||
if (x3 < x)
|
||||
inside = ! inside;
|
||||
}
|
||||
|
||||
return inside;
|
||||
}
|
||||
|
||||
/** Return true if the indicated rectangle is entirely inside this
|
||||
* Polygon.
|
||||
* This uses an even-odd rule to determine insideness.
|
||||
* @param x The x coordinate
|
||||
* @param y The y coordinate
|
||||
* @param w The width
|
||||
* @param h The height
|
||||
* @returns true if the rectangle is contained by this Polygon.
|
||||
*/
|
||||
public boolean contains (double x, double y, double w, double h)
|
||||
{
|
||||
return intersectOrContains (x, y, w, h, false);
|
||||
}
|
||||
|
||||
/** Return true if the indicated point is inside this Polygon.
|
||||
* This uses an even-odd rule to determine insideness.
|
||||
* @param x The x coordinate
|
||||
* @param y The y coordinate
|
||||
* @returns true if the point is contained by this Polygon.
|
||||
*/
|
||||
public boolean contains (int x, int y)
|
||||
{
|
||||
return contains ((double) x, (double) y);
|
||||
}
|
||||
|
||||
/** Return true if the indicated point is inside this Polygon.
|
||||
* This uses an even-odd rule to determine insideness.
|
||||
* @param p The point
|
||||
* @returns true if the point is contained by this Polygon.
|
||||
*/
|
||||
public boolean contains (Point p)
|
||||
{
|
||||
return contains (p.x, p.y);
|
||||
}
|
||||
|
||||
/** Return true if the indicated point is inside this Polygon.
|
||||
* This uses an even-odd rule to determine insideness.
|
||||
* @param p The point
|
||||
* @returns true if the point is contained by this Polygon.
|
||||
*/
|
||||
public boolean contains (Point2D p)
|
||||
{
|
||||
return contains (p.getX (), p.getY ());
|
||||
}
|
||||
|
||||
/** Return true if the indicated rectangle is entirely inside this
|
||||
* Polygon. This uses an even-odd rule to determine insideness.
|
||||
* @param r The rectangle
|
||||
* @returns true if the rectangle is contained by this Polygon.
|
||||
*/
|
||||
public boolean contains (Rectangle2D r)
|
||||
{
|
||||
return contains (r.getX (), r.getY (), r.getWidth (), r.getHeight ());
|
||||
}
|
||||
|
||||
/** Returns the bounds of this Polygon.
|
||||
* @deprecated Use getBounds() instead.
|
||||
*/
|
||||
public Rectangle getBoundingBox ()
|
||||
{
|
||||
if (bounds == null)
|
||||
computeBoundingBox ();
|
||||
return bounds;
|
||||
}
|
||||
|
||||
/** Returns the bounds of this Polygon. */
|
||||
public Rectangle getBounds ()
|
||||
{
|
||||
if (bounds == null)
|
||||
computeBoundingBox ();
|
||||
return bounds;
|
||||
}
|
||||
|
||||
/** Returns the bounds of this Polygon. */
|
||||
public Rectangle2D getBounds2D ()
|
||||
{
|
||||
if (bounds == null)
|
||||
computeBoundingBox ();
|
||||
return bounds; // Why not?
|
||||
}
|
||||
|
||||
/** Return an iterator for the boundary of this Polygon.
|
||||
* @param at A transform to apply to the coordinates.
|
||||
* @returns A path iterator for the Polygon's boundary.
|
||||
*/
|
||||
public PathIterator getPathIterator (AffineTransform at)
|
||||
{
|
||||
return new Iterator (at);
|
||||
}
|
||||
|
||||
/** Return an iterator for the boundary of this Polygon.
|
||||
* @param at A transform to apply to the coordinates.
|
||||
* @param flatness The flatness of the result; it is ignored by
|
||||
* this class.
|
||||
* @returns A path iterator for the Polygon's boundary.
|
||||
*/
|
||||
public PathIterator getPathIterator (AffineTransform at, double flatness)
|
||||
{
|
||||
// We ignore the flatness.
|
||||
return new Iterator (at);
|
||||
}
|
||||
|
||||
/** @deprecated use contains(int,int). */
|
||||
public boolean inside (int x, int y)
|
||||
{
|
||||
return contains (x, y);
|
||||
}
|
||||
|
||||
/** Return true if this Polygon's interior intersects the given
|
||||
* rectangle's interior.
|
||||
* @param x The x coordinate
|
||||
* @param y The y coordinate
|
||||
* @param w The width
|
||||
* @param h The height
|
||||
*/
|
||||
public boolean intersects (double x, double y, double w, double h)
|
||||
{
|
||||
return intersectOrContains (x, y, w, h, true);
|
||||
}
|
||||
|
||||
/** Return true if this Polygon's interior intersects the given
|
||||
* rectangle's interior.
|
||||
* @param r The rectangle
|
||||
*/
|
||||
public boolean intersects (Rectangle2D r)
|
||||
{
|
||||
return intersects (r.getX (), r.getY (), r.getWidth (), r.getHeight ());
|
||||
}
|
||||
|
||||
// This tests for intersection with or containment of a rectangle,
|
||||
// depending on the INTERSECT argument.
|
||||
private boolean intersectOrContains (double x, double y, double w, double h,
|
||||
boolean intersect)
|
||||
{
|
||||
// First compute the rectangle of possible intersection points.
|
||||
Rectangle r = getBounds ();
|
||||
int minx = Math.max (r.x, (int) x);
|
||||
int maxx = Math.min (r.x + r.width, (int) (x + w));
|
||||
int miny = Math.max (r.y, (int) y);
|
||||
int maxy = Math.min (r.y + r.height, (int) (y + h));
|
||||
|
||||
if (miny > maxy)
|
||||
return false;
|
||||
|
||||
double[] crosses = new double[npoints + 1];
|
||||
|
||||
for (; miny < maxy; ++miny)
|
||||
{
|
||||
// First compute every place where the polygon might intersect
|
||||
// the scan line at Y.
|
||||
int ins = 0;
|
||||
for (int i = 0; i < npoints; ++i)
|
||||
{
|
||||
// Handle the wrap case.
|
||||
int x2 = (i == npoints) ? xpoints[0] : xpoints[i + 1];
|
||||
int y2 = (i == npoints) ? ypoints[0] : ypoints[i + 1];
|
||||
|
||||
if (ypoints[i] == y2)
|
||||
{
|
||||
// We ignore horizontal lines. This might give weird
|
||||
// results in some situations -- ?
|
||||
continue;
|
||||
}
|
||||
|
||||
double t = (((double) miny - ypoints[i])
|
||||
/ (double) (y2 - ypoints[i]));
|
||||
double x3 = xpoints[i] + t * (x2 - xpoints[i]);
|
||||
crosses[ins++] = x3;
|
||||
}
|
||||
|
||||
// Now we can sort into increasing order and look to see if
|
||||
// any point in the rectangle is in the polygon. We examine
|
||||
// every other pair due to our even-odd rule.
|
||||
Arrays.sort (crosses, 0, ins);
|
||||
int i = intersect ? 0 : 1;
|
||||
for (; i < ins - 1; i += 2)
|
||||
{
|
||||
// Pathological case.
|
||||
if (crosses[i] == crosses[i + 1])
|
||||
continue;
|
||||
|
||||
// Found a point on the inside.
|
||||
if ((crosses[i] >= x && crosses[i] < x + w)
|
||||
|| (crosses[i + 1] >= x && crosses[i + 1] < x + w))
|
||||
{
|
||||
// If we're checking containment then we just lost.
|
||||
// But if we're checking intersection then we just
|
||||
// won.
|
||||
return intersect;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/** Translates all the vertices of the polygon via a given vector.
|
||||
* @param deltaX The X offset
|
||||
* @param deltaY The Y offset
|
||||
*/
|
||||
public void translate (int deltaX, int deltaY)
|
||||
{
|
||||
for (int i = 0; i < npoints; ++i)
|
||||
{
|
||||
xpoints[i] += deltaX;
|
||||
ypoints[i] += deltaY;
|
||||
}
|
||||
|
||||
if (bounds != null)
|
||||
{
|
||||
bounds.x += deltaX;
|
||||
bounds.y += deltaY;
|
||||
}
|
||||
}
|
||||
|
||||
// This computes the bounding box if required.
|
||||
private void computeBoundingBox ()
|
||||
{
|
||||
if (npoints == 0)
|
||||
{
|
||||
// This is wrong if the user adds a new point, but we
|
||||
// account for that in addPoint().
|
||||
bounds = new Rectangle (0, 0, 0, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
int maxx = xpoints[0];
|
||||
int minx = xpoints[0];
|
||||
int maxy = ypoints[0];
|
||||
int miny = ypoints[0];
|
||||
|
||||
for (int i = 1; i < npoints; ++i)
|
||||
{
|
||||
maxx = Math.max (maxx, xpoints[i]);
|
||||
minx = Math.min (minx, xpoints[i]);
|
||||
maxy = Math.max (maxy, ypoints[i]);
|
||||
miny = Math.min (miny, ypoints[i]);
|
||||
}
|
||||
|
||||
bounds = new Rectangle (minx, miny, maxx - minx, maxy - miny);
|
||||
}
|
||||
}
|
||||
|
||||
private class Iterator implements PathIterator
|
||||
{
|
||||
public AffineTransform xform;
|
||||
public int where;
|
||||
|
||||
public Iterator (AffineTransform xform)
|
||||
{
|
||||
this.xform = xform;
|
||||
where = 0;
|
||||
}
|
||||
|
||||
public int currentSegment (double[] coords)
|
||||
{
|
||||
int r;
|
||||
|
||||
if (where < npoints)
|
||||
{
|
||||
coords[0] = xpoints[where];
|
||||
coords[1] = ypoints[where];
|
||||
r = (where == 0) ? SEG_MOVETO : SEG_LINETO;
|
||||
xform.transform (coords, 0, coords, 0, 1);
|
||||
++where;
|
||||
}
|
||||
else
|
||||
r = SEG_CLOSE;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
public int currentSegment (float[] coords)
|
||||
{
|
||||
int r;
|
||||
|
||||
if (where < npoints)
|
||||
{
|
||||
coords[0] = xpoints[where];
|
||||
coords[1] = ypoints[where];
|
||||
r = (where == 0) ? SEG_MOVETO : SEG_LINETO;
|
||||
xform.transform (coords, 0, coords, 0, 1);
|
||||
}
|
||||
else
|
||||
r = SEG_CLOSE;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
public int getWindingRule ()
|
||||
{
|
||||
return WIND_EVEN_ODD;
|
||||
}
|
||||
|
||||
public boolean isDone ()
|
||||
{
|
||||
return where == npoints + 1;
|
||||
}
|
||||
|
||||
public void next ()
|
||||
{
|
||||
++where;
|
||||
}
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2000 Free Software Foundation
|
||||
/* Copyright (C) 2000, 2001 Free Software Foundation
|
||||
|
||||
This file is part of libjava.
|
||||
|
||||
@ -51,7 +51,7 @@ public class AffineTransform implements Cloneable, Serializable
|
||||
this.m11 = m11;
|
||||
this.m02 = m02;
|
||||
this.m12 = m12;
|
||||
this.type = 0; // fixme;
|
||||
this.type = TYPE_GENERAL_TRANSFORM;
|
||||
}
|
||||
|
||||
public AffineTransform (float[] flatmatrix)
|
||||
@ -260,6 +260,20 @@ public class AffineTransform implements Cloneable, Serializable
|
||||
type = TYPE_GENERAL_ROTATION;
|
||||
}
|
||||
|
||||
public void setToRotation (double theta, double x, double y)
|
||||
{
|
||||
double c = Math.cos (theta);
|
||||
double s = Math.sin (theta);
|
||||
|
||||
m00 = c;
|
||||
m01 = -s;
|
||||
m02 = x - x * c + y * s;
|
||||
m10 = s;
|
||||
m11 = c;
|
||||
m12 = y - x * s - y * c;
|
||||
type = TYPE_GENERAL_TRANSFORM;
|
||||
}
|
||||
|
||||
public void setToScale (double sx, double sy)
|
||||
{
|
||||
m00 = sx;
|
||||
@ -274,7 +288,7 @@ public class AffineTransform implements Cloneable, Serializable
|
||||
m01 = shx;
|
||||
m10 = shy;
|
||||
m02 = m12 = 0;
|
||||
type = 0; // FIXME
|
||||
type = TYPE_GENERAL_TRANSFORM;
|
||||
}
|
||||
|
||||
public void setTransform (AffineTransform tx)
|
||||
|
Loading…
x
Reference in New Issue
Block a user