| /******************************************************************************* |
| * Copyright (c) 2003, 2010 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| *******************************************************************************/ |
| package org.eclipse.draw2d.geometry; |
| |
| /** |
| * A Rectangle implementation using floating point values which are truncated |
| * into the inherited integer fields. The use of floating point prevents |
| * rounding errors from accumulating. |
| * |
| * @author hudsonr Created on Apr 9, 2003 |
| */ |
| public final class PrecisionRectangle extends Rectangle { |
| |
| /** |
| * Double value for height |
| * |
| * @noreference |
| * @deprecated Use {@link #setPreciseHeight(double)} and |
| * {@link #preciseHeight()} instead. This field will become |
| * private in the future. |
| */ |
| public double preciseHeight; |
| |
| /** |
| * Double value for width |
| * |
| * @noreference |
| * @deprecated Use {@link #setPreciseWidth(double)} and |
| * {@link #preciseWidth()} instead. This field will become |
| * private in the future. |
| */ |
| public double preciseWidth; |
| |
| /** |
| * Double value for X |
| * |
| * @noreference |
| * @deprecated Use {@link #setPreciseX(double)} and {@link #preciseX()} |
| * instead. This field will become private in the future. |
| */ |
| public double preciseX; |
| |
| /** |
| * Double value for Y |
| * |
| * @noreference |
| * @deprecated Use {@link #setPreciseX(double)} and {@link #preciseY()} |
| * instead. This field will become private in the future. |
| */ |
| public double preciseY; |
| |
| /** |
| * Constructs a new PrecisionRectangle with all values 0. |
| */ |
| public PrecisionRectangle() { |
| } |
| |
| /** |
| * Constructs a PrecisionRectangle with the provided values. |
| * |
| * @param x |
| * X location |
| * @param y |
| * Y location |
| * @param width |
| * Width of the rectangle |
| * @param height |
| * Height of the rectangle |
| * @since 3.7 |
| */ |
| public PrecisionRectangle(double x, double y, double width, double height) { |
| setPreciseLocation(x, y); |
| setPreciseSize(width, height); |
| } |
| |
| /** |
| * |
| * Constructs a new PrecisionRectangle from a given Point and a Dimension |
| * |
| * @param p |
| * The Point to specify x and y location of the |
| * PrecisionRectangle |
| * @param d |
| * The Dimension to use for width and height of the |
| * PrecisionRectangle |
| * @since 3.7 |
| */ |
| public PrecisionRectangle(Point p, Dimension d) { |
| this(p.preciseX(), p.preciseY(), d.preciseWidth(), d.preciseHeight()); |
| } |
| |
| /** |
| * Constructs a new PrecisionRectangle from the given integer Rectangle. |
| * |
| * @param rect |
| * the base rectangle |
| */ |
| public PrecisionRectangle(Rectangle rect) { |
| this(rect.preciseX(), rect.preciseY(), rect.preciseWidth(), rect |
| .preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#contains(int, int) |
| */ |
| public boolean contains(int x, int y) { |
| return containsPrecise(x, y); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#contains(org.eclipse.draw2d.geometry.Point) |
| */ |
| public boolean contains(Point p) { |
| return containsPrecise(p.preciseX(), p.preciseY()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#contains(org.eclipse.draw2d.geometry.Rectangle) |
| */ |
| public boolean contains(Rectangle rect) { |
| return preciseX() <= rect.preciseX() && preciseY() <= rect.preciseY() |
| && right() >= rect.right() && bottom() >= rect.bottom(); |
| } |
| |
| /** |
| * Returns whether the given coordinates are within the boundaries of this |
| * Rectangle. The boundaries are inclusive of the top and left edges, but |
| * exclusive of the bottom and right edges. |
| * |
| * @param x |
| * X value |
| * @param y |
| * Y value |
| * @return true if the coordinates are within this Rectangle |
| * @since 3.7 |
| */ |
| private boolean containsPrecise(double x, double y) { |
| return y >= preciseY() && y < preciseY() + preciseHeight() |
| && x >= preciseX() && x < preciseX() + preciseWidth(); |
| } |
| |
| /** |
| * @see Rectangle#equals(Object) |
| */ |
| public boolean equals(Object o) { |
| if (o instanceof PrecisionRectangle) { |
| PrecisionRectangle rect = (PrecisionRectangle) o; |
| return super.equals(o) |
| && Math.abs(rect.preciseX() - preciseX()) < 0.000000001 |
| && Math.abs(rect.preciseY() - preciseY()) < 0.000000001 |
| && Math.abs(rect.preciseWidth() - preciseWidth()) < 0.000000001 |
| && Math.abs(rect.preciseHeight() - preciseHeight()) < 0.00000001; |
| } |
| |
| return super.equals(o); |
| } |
| |
| /** |
| * Expands the horizontal and vertical sides of this Rectangle with the |
| * values provided as input, and returns this for convenience. The location |
| * of its center is kept constant. |
| * |
| * @param h |
| * Horizontal increment |
| * @param v |
| * Vertical increment |
| * @return <code>this</code> for convenience |
| * @since 3.4 |
| * @deprecated Use {@link #expandPrecise(double, double)} instead. |
| */ |
| public Rectangle expand(double h, double v) { |
| return shrink(-h, -v); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#expand(org.eclipse.draw2d.geometry.Insets) |
| */ |
| public Rectangle expand(Insets insets) { |
| if (insets == null) |
| return this; |
| setPreciseX(preciseX() - insets.left); |
| setPreciseY(preciseY() - insets.top); |
| setPreciseWidth(preciseWidth() + insets.getWidth()); |
| setPreciseHeight(preciseHeight() + insets.getHeight()); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#expand(int, int) |
| */ |
| public Rectangle expand(int h, int v) { |
| return expandPrecise(h, v); |
| } |
| |
| /** |
| * Expands the horizontal and vertical sides of this Rectangle with the |
| * values provided as input, and returns this for convenience. The location |
| * of its center is kept constant. |
| * |
| * @param h |
| * Horizontal increment |
| * @param v |
| * Vertical increment |
| * @return <code>this</code> for convenience |
| * @since 3.7 |
| */ |
| private PrecisionRectangle expandPrecise(double h, double v) { |
| return shrinkPrecise(-h, -v); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getBottom() |
| */ |
| public Point getBottom() { |
| return new PrecisionPoint(preciseX() + preciseWidth() / 2, bottom()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getBottomLeft() |
| */ |
| public Point getBottomLeft() { |
| return new PrecisionPoint(preciseX(), preciseY() + preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getBottomRight() |
| */ |
| public Point getBottomRight() { |
| return new PrecisionPoint(preciseX() + preciseWidth(), preciseY() |
| + preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getCenter() |
| */ |
| public Point getCenter() { |
| return new PrecisionPoint(preciseX() + preciseWidth() / 2.0, preciseY() |
| + preciseHeight() / 2.0); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getCopy() |
| */ |
| public Rectangle getCopy() { |
| return getPreciseCopy(); |
| } |
| |
| /** |
| * Returns a precise copy of this. |
| * |
| * @return a precise copy |
| */ |
| public PrecisionRectangle getPreciseCopy() { |
| return new PrecisionRectangle(preciseX(), preciseY(), preciseWidth(), |
| preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getTop() |
| */ |
| public Point getTop() { |
| return new PrecisionPoint(preciseX() + preciseWidth() / 2, preciseY()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getTopLeft() |
| */ |
| public Point getTopLeft() { |
| return new PrecisionPoint(preciseX(), preciseY()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#getTopRight() |
| */ |
| public Point getTopRight() { |
| return new PrecisionPoint(preciseX() + preciseWidth(), preciseY()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#intersect(org.eclipse.draw2d.geometry.Rectangle) |
| */ |
| public Rectangle intersect(Rectangle rect) { |
| return intersectPrecise(rect); |
| } |
| |
| /** |
| * Sets the size of this Rectangle to the intersection region with the |
| * Rectangle supplied as input, and returns this for convenience. The |
| * location and dimensions are set to zero if there is no intersection with |
| * the input Rectangle. |
| * |
| * @param rect |
| * Rectangle for the calculating intersection. |
| * @return <code>this</code> for convenience |
| * @since 3.7 |
| */ |
| private PrecisionRectangle intersectPrecise(Rectangle rect) { |
| double x1 = Math.max(preciseX(), rect.preciseX()); |
| double x2 = Math.min(preciseX() + preciseWidth(), rect.preciseX() |
| + rect.preciseWidth()); |
| double y1 = Math.max(preciseY(), rect.preciseY()); |
| double y2 = Math.min(preciseY() + preciseHeight(), rect.preciseY() |
| + rect.preciseHeight()); |
| if (((x2 - x1) < 0) || ((y2 - y1) < 0)) |
| return setPreciseBounds(0, 0, 0, 0); // no intersection |
| else { |
| return setPreciseBounds(x1, y1, x2 - x1, y2 - y1); |
| } |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#performScale(double) |
| */ |
| public void performScale(double factor) { |
| setPreciseX(preciseX() * factor); |
| setPreciseY(preciseY() * factor); |
| setPreciseWidth(preciseWidth() * factor); |
| setPreciseHeight(preciseHeight() * factor); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#performTranslate(int, int) |
| */ |
| public void performTranslate(int dx, int dy) { |
| setPreciseX(preciseX() + dx); |
| setPreciseY(preciseY() + dy); |
| } |
| |
| /** |
| * Returns the bottom coordinte in double precision. |
| * |
| * @return the precise bottom |
| */ |
| public double preciseBottom() { |
| return preciseHeight() + preciseY(); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#preciseHeight() |
| */ |
| public double preciseHeight() { |
| updatePreciseHeightDouble(); |
| return preciseHeight; |
| } |
| |
| /** |
| * Returns the right side in double precision. |
| * |
| * @return the precise right |
| */ |
| public double preciseRight() { |
| return preciseWidth() + preciseX(); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#preciseWidth() |
| */ |
| public double preciseWidth() { |
| updatePreciseWidthDouble(); |
| return preciseWidth; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#preciseX() |
| */ |
| public double preciseX() { |
| updatePreciseXDouble(); |
| return preciseX; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#preciseY() |
| */ |
| public double preciseY() { |
| updatePreciseYDouble(); |
| return preciseY; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#resize(org.eclipse.draw2d.geometry.Dimension) |
| */ |
| public Rectangle resize(Dimension d) { |
| return resizePrecise(d.preciseWidth(), d.preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#resize(int, int) |
| */ |
| public Rectangle resize(int w, int h) { |
| return resizePrecise(w, h); |
| } |
| |
| /** |
| * Resizes this Rectangle by adding the values supplied, returning this for |
| * convenience. |
| * |
| * @param w |
| * Amount by which width is to be resized |
| * @param h |
| * Amount by which height is to be resized |
| * @return <code>this</code> for convenience |
| * @since 3.7 |
| */ |
| private PrecisionRectangle resizePrecise(double w, double h) { |
| setPreciseWidth(preciseWidth() + w); |
| setPreciseHeight(preciseHeight() + h); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setBounds(int, int, int, int) |
| */ |
| public Rectangle setBounds(int x, int y, int width, int height) { |
| return setPreciseBounds(x, y, width, height); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setBounds(org.eclipse.draw2d.geometry.Point, |
| * org.eclipse.draw2d.geometry.Dimension) |
| */ |
| public Rectangle setBounds(Point location, Dimension size) { |
| return setPreciseBounds(location.preciseX(), location.preciseY(), |
| size.preciseWidth(), size.preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setBounds(org.eclipse.draw2d.geometry.Rectangle) |
| */ |
| public Rectangle setBounds(Rectangle rect) { |
| return setPreciseBounds(rect.preciseX(), rect.preciseY(), |
| rect.preciseWidth(), rect.preciseHeight()); |
| } |
| |
| /** |
| * Sets the height. |
| * |
| * @param value |
| * the new height |
| * @deprecated Use {@link #setPreciseHeight(double)} instead. |
| */ |
| public void setHeight(double value) { |
| setPreciseHeight(value); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setHeight(int) |
| */ |
| public Rectangle setHeight(int height) { |
| return setPreciseHeight(height); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setLocation(int, int) |
| */ |
| public Rectangle setLocation(int x, int y) { |
| return setPreciseLocation(x, y); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setLocation(org.eclipse.draw2d.geometry.Point) |
| */ |
| public Rectangle setLocation(Point loc) { |
| return setPreciseLocation(loc.preciseX(), loc.preciseY()); |
| } |
| |
| /** |
| * Sets the preciseX, preciseY, preciseWidth, and preciseHeight values of |
| * this PrecisionRectangle to the provided values and updates the integer |
| * values of x, y, width, and height accordingly. |
| * |
| * @param x |
| * The new x |
| * @param y |
| * The new y |
| * @param width |
| * The new width |
| * @param height |
| * The new height |
| * @return this for convenience |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseBounds(double x, double y, |
| double width, double height) { |
| setPreciseLocation(x, y); |
| setPreciseSize(width, height); |
| return this; |
| } |
| |
| /** |
| * Sets the height of this PrecisionRectangle to the specified value. |
| * |
| * @param value |
| * The new height. |
| * @return this for convenience |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseHeight(double value) { |
| preciseHeight = value; |
| updateHeightInt(); |
| return this; |
| } |
| |
| /** |
| * Sets the preciseX and preciseY values of this PrecisionRectangle to the |
| * provided values and updates the integer values of x and y accordingly. |
| * |
| * @param x |
| * The new x value |
| * @param y |
| * The new y value |
| * @return this for convenience |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseLocation(double x, double y) { |
| setPreciseX(x); |
| setPreciseY(y); |
| return this; |
| } |
| |
| /** |
| * Sets the precise location of this PrecisionRectangle |
| * |
| * @param loc |
| * The new location |
| * @return this for convenience. |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseLocation(PrecisionPoint loc) { |
| return setPreciseLocation(loc.preciseX(), loc.preciseY()); |
| } |
| |
| /** |
| * Sets the preciseWidth and preciseHeight values of this PrecisionRectangle |
| * to the provided values and updates the integer values of width and height |
| * accordingly. |
| * |
| * @param w |
| * The new width |
| * @param h |
| * The new height |
| * @return this for convenience. |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseSize(double w, double h) { |
| setPreciseWidth(w); |
| setPreciseHeight(h); |
| return this; |
| } |
| |
| /** |
| * Set the size of this PrecisionRectangle to the given dimension's width |
| * and height. Returns this for convenience. |
| * |
| * @param size |
| * The new size |
| * @return this for convenience. |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseSize(PrecisionDimension size) { |
| return setPreciseSize(size.preciseWidth(), size.preciseHeight()); |
| } |
| |
| /** |
| * Sets the width of this PrecisionRectangle to the specified one. |
| * |
| * @param value |
| * The new width |
| * @return this for convenience |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseWidth(double value) { |
| preciseWidth = value; |
| updateWidthInt(); |
| return this; |
| } |
| |
| /** |
| * Sets the x value. |
| * |
| * @param value |
| * The new x value |
| * @return this for convenience |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseX(double value) { |
| preciseX = value; |
| updateXInt(); |
| return this; |
| } |
| |
| /** |
| * Sets the y value. |
| * |
| * @param value |
| * the new y value |
| * @return this for convenience |
| * @since 3.7 |
| */ |
| public PrecisionRectangle setPreciseY(double value) { |
| preciseY = value; |
| updateYInt(); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setSize(org.eclipse.draw2d.geometry.Dimension) |
| */ |
| public Rectangle setSize(Dimension d) { |
| return setPreciseSize(d.preciseWidth(), d.preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setSize(int, int) |
| */ |
| public Rectangle setSize(int w, int h) { |
| return setPreciseSize(w, h); |
| } |
| |
| /** |
| * Sets the width. |
| * |
| * @param value |
| * the new width |
| * @deprecated Use {@link #setPreciseWidth(double)} instead. |
| */ |
| public void setWidth(double value) { |
| setPreciseWidth(value); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setWidth(int) |
| */ |
| public Rectangle setWidth(int width) { |
| return setPreciseWidth(width); |
| } |
| |
| /** |
| * Sets the x value. |
| * |
| * @param value |
| * the new x value |
| * @deprecated Use {@link #setPreciseX(double)} instead. |
| */ |
| public void setX(double value) { |
| setPreciseX(value); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setX(int) |
| */ |
| public Rectangle setX(int value) { |
| return setPreciseX(value); |
| } |
| |
| /** |
| * Sets the y value. |
| * |
| * @param value |
| * the new y value |
| * @deprecated Use {@link #setPreciseX(double)} instead. |
| */ |
| public void setY(double value) { |
| setPreciseY(value); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#setY(int) |
| */ |
| public Rectangle setY(int value) { |
| return setPreciseY(value); |
| } |
| |
| /** |
| * Shrinks the sides of this Rectangle by the horizontal and vertical values |
| * provided as input, and returns this Rectangle for convenience. The center |
| * of this Rectangle is kept constant. |
| * |
| * @param h |
| * Horizontal reduction amount |
| * @param v |
| * Vertical reduction amount |
| * @return <code>this</code> for convenience |
| * @since 3.4 |
| * @deprecated Use {@link #shrink(int, int)} or |
| * {@link #shrinkPrecise(double, double)} instead. |
| */ |
| public Rectangle shrink(double h, double v) { |
| return shrinkPrecise(h, v); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#shrink(org.eclipse.draw2d.geometry.Insets) |
| */ |
| public Rectangle shrink(Insets insets) { |
| if (insets == null) |
| return this; |
| setPreciseX(preciseX() + insets.left); |
| setPreciseY(preciseY() + insets.top); |
| setPreciseWidth(preciseWidth() - insets.getWidth()); |
| setPreciseHeight(preciseHeight() - insets.getHeight()); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#shrink(int, int) |
| */ |
| public Rectangle shrink(int h, int v) { |
| return shrinkPrecise(h, v); |
| } |
| |
| /** |
| * Shrinks the sides of this Rectangle by the horizontal and vertical values |
| * provided as input, and returns this Rectangle for convenience. The center |
| * of this Rectangle is kept constant. |
| * |
| * @param h |
| * Horizontal reduction amount |
| * @param v |
| * Vertical reduction amount |
| * @return <code>this</code> for convenience |
| * @since 3.7 |
| */ |
| private PrecisionRectangle shrinkPrecise(double h, double v) { |
| setPreciseX(preciseX() + h); |
| setPreciseWidth(preciseWidth() - (h + h)); |
| setPreciseY(preciseY() + v); |
| setPreciseHeight(preciseHeight() - (v + v)); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#touches(org.eclipse.draw2d.geometry.Rectangle) |
| */ |
| public boolean touches(Rectangle rect) { |
| return rect.preciseX() <= preciseX() + preciseWidth() |
| && rect.preciseY() <= preciseY() + preciseHeight() |
| && rect.preciseX() + rect.preciseWidth() >= preciseX() |
| && rect.preciseY() + rect.preciseHeight() >= preciseY(); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#translate(int, int) |
| */ |
| public Rectangle translate(int dx, int dy) { |
| return translatePrecise(dx, dy); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#translate(org.eclipse.draw2d.geometry.Point) |
| */ |
| public Rectangle translate(Point p) { |
| return translatePrecise(p.preciseX(), p.preciseY()); |
| } |
| |
| /** |
| * Moves this Rectangle horizontally by dx and vertically by dy, then |
| * returns this Rectangle for convenience. |
| * |
| * @param dx |
| * Shift along X axis |
| * @param dy |
| * Shift along Y axis |
| * @return <code>this</code> for convenience |
| * @since 3.7 |
| */ |
| private PrecisionRectangle translatePrecise(double dx, double dy) { |
| setPreciseX(preciseX() + dx); |
| setPreciseY(preciseY() + dy); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#transpose() |
| */ |
| public Rectangle transpose() { |
| double temp = preciseX(); |
| setPreciseX(preciseY()); |
| setPreciseY(temp); |
| temp = preciseWidth(); |
| setPreciseWidth(preciseHeight()); |
| setPreciseHeight(temp); |
| return this; |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#union(int, int) |
| */ |
| public Rectangle union(int x, int y) { |
| return unionPrecise(x, y); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#union(org.eclipse.draw2d.geometry.Point) |
| */ |
| public void union(Point p) { |
| unionPrecise(p.preciseX(), p.preciseY()); |
| } |
| |
| /** |
| * Unions the given PrecisionRectangle with this rectangle and returns |
| * <code>this</code> for convenience. |
| * |
| * @since 3.0 |
| * @param rect |
| * the rectangle being unioned |
| * @return <code>this</code> for convenience |
| * @deprecated Use {@link #union(Rectangle)} instead |
| */ |
| public PrecisionRectangle union(PrecisionRectangle rect) { |
| if (rect == null || rect.isEmpty()) { |
| return this; |
| } |
| return unionPrecise(rect.preciseX(), rect.preciseY(), |
| rect.preciseWidth(), rect.preciseHeight()); |
| } |
| |
| /** |
| * @see org.eclipse.draw2d.geometry.Rectangle#union(org.eclipse.draw2d.geometry.Rectangle) |
| */ |
| public Rectangle union(Rectangle rect) { |
| if (rect == null || rect.isEmpty()) |
| return this; |
| return unionPrecise(rect.preciseX(), rect.preciseY(), |
| rect.preciseWidth(), rect.preciseHeight()); |
| } |
| |
| /** |
| * Updates this Rectangle's bounds to the minimum size which can hold both |
| * this Rectangle and the coordinate (x,y). |
| * |
| * @return <code>this</code> for convenience |
| * @param x |
| * X coordinate |
| * @param y |
| * Y coordinate |
| * @since 3.7 |
| */ |
| private PrecisionRectangle unionPrecise(double x, double y) { |
| if (x < preciseX()) { |
| setPreciseWidth(preciseWidth() + (preciseX() - x)); |
| setPreciseX(x); |
| } else { |
| double right = preciseX() + preciseWidth(); |
| if (x > right) { |
| setPreciseWidth(x - preciseX()); |
| } |
| } |
| if (y < preciseY()) { |
| setPreciseHeight(preciseHeight() + (preciseY() - y)); |
| setPreciseY(y); |
| } else { |
| double bottom = preciseY() + preciseHeight(); |
| if (y > bottom) { |
| setPreciseHeight(y - preciseY()); |
| } |
| } |
| return this; |
| } |
| |
| /** |
| * Updates this Rectangle's dimensions to the minimum size which can hold |
| * both this Rectangle and the rectangle (x, y, w, h). |
| * |
| * @param x |
| * X coordinate of desired union. |
| * @param y |
| * Y coordinate of desired union. |
| * @param w |
| * Width of desired union. |
| * @param h |
| * Height of desired union. |
| * @return <code>this</code> for convenience |
| * @since 3.7 |
| */ |
| private PrecisionRectangle unionPrecise(double x, double y, double w, |
| double h) { |
| double right = Math.max(preciseX() + preciseWidth(), x + w); |
| double bottom = Math.max(preciseY() + preciseHeight(), y + h); |
| setPreciseX(Math.min(preciseX(), x)); |
| setPreciseY(Math.min(preciseY(), y)); |
| setPreciseWidth(right - preciseX()); |
| setPreciseHeight(bottom - preciseY()); |
| return this; |
| } |
| |
| /** |
| * Updates the height integer field using the value of preciseHeight. |
| */ |
| private final void updateHeightInt() { |
| height = PrecisionGeometry.doubleToInteger(preciseHeight + preciseY()) |
| - y; |
| } |
| |
| /** |
| * Updates the integer values based on the current precise values. |
| * |
| * @deprecated This method should not be accessed by clients any more (it |
| * will be made private in future releases). The update of |
| * integer and precision fields is performed automatically if |
| * {@link #preciseX}, {@link #preciseY}, {@link #preciseWidth}, |
| * and {@link #preciseHeight} field values are not manipulated |
| * directly, but only via respective methods offered by this |
| * class. |
| * |
| * @since 3.0 |
| */ |
| public void updateInts() { |
| updateXInt(); |
| updateYInt(); |
| updateWidthInt(); |
| updateHeightInt(); |
| } |
| |
| /** |
| * Updates the preciseHeight double field using the value of height. |
| */ |
| private final void updatePreciseHeightDouble() { |
| if (height != PrecisionGeometry.doubleToInteger(preciseY() |
| + preciseHeight) |
| - y) { |
| preciseHeight = height; |
| } |
| } |
| |
| /** |
| * Updates the preciseWidth double field using the value of width. |
| */ |
| private final void updatePreciseWidthDouble() { |
| if (width != PrecisionGeometry.doubleToInteger(preciseX() |
| + preciseWidth) |
| - x) { |
| preciseWidth = width; |
| } |
| } |
| |
| /** |
| * Updates the preciseX double field using the value of x. |
| */ |
| private final void updatePreciseXDouble() { |
| if (x != PrecisionGeometry.doubleToInteger(preciseX)) { |
| preciseX = x; |
| } |
| } |
| |
| /** |
| * Updates the preciseY double field using the value of y. |
| */ |
| private final void updatePreciseYDouble() { |
| if (y != PrecisionGeometry.doubleToInteger(preciseY)) { |
| preciseY = y; |
| } |
| } |
| |
| /** |
| * Updates the width integer field using the value of preciseWidth. |
| */ |
| private final void updateWidthInt() { |
| width = PrecisionGeometry.doubleToInteger(preciseWidth + preciseX()) |
| - x; |
| } |
| |
| /** |
| * Updates the x integer field using the value of preciseX. |
| */ |
| private final void updateXInt() { |
| x = PrecisionGeometry.doubleToInteger(preciseX); |
| } |
| |
| /** |
| * Updates the y integer field using the value of preciseY. |
| */ |
| private final void updateYInt() { |
| y = PrecisionGeometry.doubleToInteger(preciseY); |
| } |
| |
| } |