All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.geolatte.geom.Box Maven / Gradle / Ivy

Go to download

This geoLatte-geom library offers a geometry model that conforms to the OGC Simple Features for SQL specification.

The newest version!
package org.geolatte.geom;

import org.geolatte.geom.crs.CoordinateReferenceSystem;

import static java.lang.String.format;

/**
 * An multi-dimensional axis-aligned bounding box. 
 *
 * 

A Box determines a sub characterised by a lower-left and an upper-right coordinate.

*

An Box is empty if the set of enclosed points are emptym, and has Double.NaN for its lowerleft/upperright coordinates.

* * @author Karel Maesen, Geovise BVBA, 2011 */ public class Box

{ private final CoordinateReferenceSystem

crs; private final P lowerLeft; private final P upperRight; /** * Creates an empty Box */ public Box(CoordinateReferenceSystem

crs) { this.crs = crs; lowerLeft = Positions.mkPosition(crs); upperRight = lowerLeft; } /** * Creates an instance from specified lower-left and upper-right Points. * * * @param lowerLeft the Point designating the lower-left coordinates * @param upperRight the Point designating the upper-right coordinates * of the envelope. */ public Box(P lowerLeft, P upperRight, CoordinateReferenceSystem

crs) { if (crs == null) { throw new IllegalArgumentException("Null CRS argument not allowed"); } for (int i = 0; i < lowerLeft.getCoordinateDimension(); i++) { if (lowerLeft.getCoordinate(i) > upperRight.getCoordinate(i)) { throw new IllegalArgumentException("Lowerleft needs to be smaller than upperRight"); } } this.crs = crs; this.lowerLeft = lowerLeft; this.upperRight = upperRight; } /** * Returns the CoordinateReferenceSystem for this Box * * @return */ public CoordinateReferenceSystem

getCoordinateReferenceSystem() { return this.crs; } /** * Returns the lower-left point of this Box. * * @return the lower-left point */ public P lowerLeft() { return this.lowerLeft; } /** * Returns the upper-right point of this Box. * * @return the upper-right point */ public P upperRight() { return this.upperRight; } public String toString() { StringBuilder builder = new StringBuilder(getCoordinateReferenceSystem().getCrsId().toString()); builder.append("Box LL: ") .append(this.lowerLeft.toString()) .append(" - UR: ") .append(this.upperRight.toString()); return builder.toString(); } /** * Creates an Box that is the set-theoretic union of this {@code Box} with the specified {@code Box} * * @param other other Box * @return an Box that encompasses both operands. * @throws IllegalArgumentException when the operand Boxs don't have the same coordinate reference system. */ public Box

union(Box

other) { if (other == null || other.isEmpty()) return this; if (!this.getCoordinateReferenceSystem().equals(other.getCoordinateReferenceSystem())) throw new IllegalArgumentException("Boxs have different CRS."); double[] lowerLeft = new double[getCoordinateDimension()]; double[] upperRight = new double[getCoordinateDimension()]; for (int i = 0; i < getCoordinateDimension(); i++){ lowerLeft[i] = Math.min(this.lowerLeft.getCoordinate(i), other.lowerLeft.getCoordinate(i)); upperRight[i] = Math.max(this.upperRight.getCoordinate(i), other.upperRight.getCoordinate(i)); } return new Box

(Positions.mkPosition(crs, lowerLeft), Positions.mkPosition(crs, upperRight) , crs); } /** * Intersects the specified Box with this Box and returns the result. * * @param other the Box to intersect with this instance * @return the set-theoretic intersection of this Box and the specified Box. * @throws IllegalArgumentException when the specified Box doesn't have the same coordinate reference system as this instance. */ public Box

intersect(Box

other) { if (other == null || other.isEmpty()) return this; if (!this.getCoordinateReferenceSystem().equals(other.getCoordinateReferenceSystem())) throw new IllegalArgumentException("Boxs have different CRS."); double[] lowerLeft = new double[getCoordinateDimension()]; double[] upperRight = new double[getCoordinateDimension()]; for (int i = 0; i < getCoordinateDimension(); i++){ if (this.lowerLeft.getCoordinate(i) > other.upperRight.getCoordinate(i) || this.upperRight.getCoordinate(i) < other.lowerLeft.getCoordinate(i)) { return mkEmpty(); } lowerLeft[i] = Math.max(this.lowerLeft.getCoordinate(i), other.lowerLeft.getCoordinate(i)); upperRight[i] = Math.min(this.upperRight.getCoordinate(i), other.upperRight.getCoordinate(i)); } return new Box

(Positions.mkPosition(crs, lowerLeft), Positions.mkPosition(crs, upperRight) , crs); } private Box

mkEmpty() { P pos = Positions.mkPosition(crs); return new Box

(pos, pos, crs); } static public

Box

mkEmpty(CoordinateReferenceSystem

crs) { P pos = Positions.mkPosition(crs); return new Box

(pos, pos, crs); } public int getCoordinateDimension(){ return crs.getCoordinateDimension(); } /** * Checks whether this Box is empty. * * @return true iff this instance is empty (the empty set). */ public boolean isEmpty() { return this.lowerLeft.isEmpty() && this.upperRight.isEmpty() ; } /** * Checks whether this Box is contained within the specified Box * * @param other the other Box * @return true iff this instance is contained within the specified Box * @throws IllegalArgumentException when the specified Box doesn't have the same coordinate reference system as this instance. */ public boolean within(Box

other) { if (other == null || other.isEmpty()) return false; if (!this.getCoordinateReferenceSystem().equals(other.getCoordinateReferenceSystem())) throw new IllegalArgumentException("Boxs have different CRS."); for (int i = 0; i < getCoordinateDimension(); i++){ if (this.lowerLeft.getCoordinate(i) < other.lowerLeft.getCoordinate(i) || this.upperRight.getCoordinate(i) > other.upperRight.getCoordinate(i)) { return false; } } return true; } /** * Checks whether this Box contains the specifies Box. * * @param other the other Box * @return true iff this instance contains the specified Box * @throws IllegalArgumentException when the specified Box doesn't have the same coordinate reference system as this instance. */ public boolean contains(Box other) { return other.within(this); } /** * Checks whether this Box contains the specifies Position. * * @param p the Position * @return true iff this instance contains the specified Position * @throws IllegalArgumentException when the specified Point doesn't have the same coordinate reference system as this instance. */ public boolean contains(P p) { if (!p.getClass().equals(this.getCoordinateReferenceSystem().getPositionClass())) throw new IllegalArgumentException("Position and envelope of different types"); if (isEmpty()) return false; for(int i = 0; i < getCoordinateDimension(); i++) { if (p.getCoordinate(i) < lowerLeft.getCoordinate(i) || p.getCoordinate(i) > upperRight.getCoordinate(i)) { return false; } } return true; } /** * Checks whether this Box intersects the specifies Box. * *

Two instances intersect when their set-theoretic intersection is non-empty.

* * @param other the other Box * @return true iff this instance intersects with the other Box * @throws IllegalArgumentException when the specified Box doesn't have the same coordinate reference system as this instance. */ public boolean intersects(Box

other) { if (isEmpty() || other.isEmpty()) return false; for(int i = 0; i < getCoordinateDimension(); i++){ if (this.lowerLeft.getCoordinate(i) > other.upperRight.getCoordinate(i) || this.upperRight.getCoordinate(i) < other.lowerLeft.getCoordinate(i)) { return false; } } return true; } @SuppressWarnings("unchecked") public Box as(Class castToType){ if (! castToType.isAssignableFrom(this.crs.getPositionClass()) ) { throw new ClassCastException(format("Can't cast a %s to a %s", this.crs.getPositionClass().getName(), castToType.getName())); } return (Box)this; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; Box envelope = (Box) o; if (crs != null ? !crs.equals(envelope.crs) : envelope.crs != null) return false; if (this.isEmpty() && envelope.isEmpty()) return true; if (lowerLeft != null ? !lowerLeft.equals(envelope.lowerLeft) : envelope.lowerLeft != null) return false; if (upperRight != null ? !upperRight.equals(envelope.upperRight) : envelope.upperRight != null) return false; return true; } @Override public int hashCode() { int result = crs != null ? crs.hashCode() : 0; result = 31 * result + (lowerLeft != null ? lowerLeft.hashCode() : 0); result = 31 * result + (upperRight != null ? upperRight.hashCode() : 0); return result; } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy