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

nz.co.gregs.dbvolution.internal.sqlite.Polygon2DFunctions Maven / Gradle / Ivy

/*
 * Copyright 2015 gregorygraham.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package nz.co.gregs.dbvolution.internal.sqlite;

import com.vividsolutions.jts.geom.Coordinate;
import com.vividsolutions.jts.geom.Geometry;
import com.vividsolutions.jts.geom.GeometryFactory;
import com.vividsolutions.jts.geom.LineString;
import com.vividsolutions.jts.geom.Point;
import com.vividsolutions.jts.geom.Polygon;
import com.vividsolutions.jts.io.WKTReader;
import java.sql.SQLException;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import nz.co.gregs.dbvolution.databases.SQLiteDB;
import org.sqlite.Function;

/**
 *
 * 

Support DBvolution at * Patreon

* * @author gregorygraham */ public class Polygon2DFunctions { /** * */ public final static String CREATE_FROM_WKTPOLYGON2D = "DBV_CREATE_POLYGON2D_FROM_WKTPOLYGON"; /** * */ public final static String CREATE_FROM_POINT2DS = "DBV_CREATE_POLYGON2D_FROM_POINTS2D"; /** * */ public final static String EQUALS = "DBV_POLYGON2D_EQUALS"; /** * */ public final static String AREA = "DBV_POLYGON2D_AREA"; /** * */ public final static String DIMENSION = "DBV_POLYGON2D_DIMENSION"; /** * */ public final static String MIN_Y = "DBV_POLYGON2D_MIN_Y2D_COORD"; /** * */ public final static String MAX_Y = "DBV_POLYGON2D_MAX_Y2D_COORD"; /** * */ public final static String MAX_X = "DBV_POLYGON2D_MAX_X2D_COORD"; /** * */ public final static String MIN_X = "DBV_POLYGON2D_MIN_X2D_COORD"; /** * */ public final static String BOUNDINGBOX = "DBV_POLYGON2D_BOUNDINGBOX2D"; /** * */ public final static String TOUCHES = "DBV_POLYGON2D_TOUCHES"; /** * */ public final static String EXTERIORRING = "DBV_POLYGON2D_EXTERIORRING"; /** * */ public final static String CONTAINS_POLYGON2D = "DBV_POLYGON2D_CONTAINS"; /** * */ public final static String WITHIN = "DBV_POLYGON2D_WITHIN"; /** * */ public final static String OVERLAPS = "DBV_POLYGON2D_OVERLAPS"; /** * */ public final static String INTERSECTS = "DBV_POLYGON2D_INTERSECTS"; /** * */ public final static String DISJOINT = "DBV_POLYGON2D_DISJOINT"; /** * */ public final static String CONTAINS_POINT2D = "DBV_POLYGON2D_CONTAINS_POINT2D"; public final static String ASTEXT_FUNCTION = "DBV_POLYGON2D_ASTEXT"; private Polygon2DFunctions() { } /** * * @param connection * @throws SQLException */ public static void addFunctions(java.sql.Connection connection) throws SQLException { add(connection, DIMENSION, new SpatialDimension()); add(connection, EQUALS, new Equals()); add(connection, AREA, new Area()); add(connection, TOUCHES, new Touches()); add(connection, EXTERIORRING, new ExteriorRing()); add(connection, CONTAINS_POLYGON2D, new Contains()); add(connection, WITHIN, new Within()); add(connection, OVERLAPS, new Overlaps()); add(connection, INTERSECTS, new Intersects()); add(connection, DISJOINT, new Disjoint()); add(connection, CREATE_FROM_WKTPOLYGON2D, new CreatePolygonFromWKTPolygon2D()); add(connection, CREATE_FROM_POINT2DS, new CreatePolygonFromPoint2Ds()); add(connection, MAX_X, new MaxX()); add(connection, MIN_X, new MinX()); add(connection, MAX_Y, new MaxY()); add(connection, MIN_Y, new MinY()); add(connection, BOUNDINGBOX, new BoundingBox()); add(connection, CONTAINS_POINT2D, new ContainsPoint2D()); add(connection, ASTEXT_FUNCTION, new AsText()); } private static void add(java.sql.Connection connection, String functionName, Function function) throws SQLException { Function.destroy(connection, functionName); Function.create(connection, functionName, function); } /** * Implements Polygon2D DIMENSION for SQLite * */ private static class SpatialDimension extends Function { @Override protected void xFunc() throws SQLException { result(2); } } /** * Implements Polygon2D AsText for SQLite * */ private static class AsText extends Function { @Override protected void xFunc() throws SQLException { String point = value_text(0); result(point); } } /** * Implements Polygon2D CREATE for SQLite * */ private static class CreatePolygonFromWKTPolygon2D extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon polygon = getPolygon(value_text(0)); // polygon.normalize(); result(polygon.toText()); } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(Polygon2DFunctions.class.getName()).log(Level.SEVERE, null, ex); } } } /** * Implements Polygon2D CREATE for SQLite * */ private static class CreatePolygonFromPoint2Ds extends Function { @Override protected void xFunc() throws SQLException { try { WKTReader wktReader = new WKTReader(); GeometryFactory factory = new GeometryFactory(); List coords = new ArrayList(); String originalStr; int numberOfPoints = args(); for (int index = 0; index < numberOfPoints; index++) { originalStr = value_text(index); if (originalStr == null) { result((String) null); } else { Point point = null; Geometry geometry; geometry = wktReader.read(originalStr); if (geometry instanceof Point) { point = (Point) geometry; coords.add(point.getCoordinate()); } else { throw new ParseException(originalStr, 0); } } } Polygon createPolygon = factory.createPolygon(coords.toArray(new Coordinate[]{})); createPolygon.normalize(); result(createPolygon.toText()); } catch (ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class MaxX extends Function { @Override protected void xFunc() throws SQLException { try { // SQLiteDefinition defn = new SQLiteDefinition(); WKTReader wktReader = new WKTReader(); // GeometryFactory factory = new GeometryFactory(); // List coords = new ArrayList(); String originalStr; originalStr = value_text(0); if (originalStr == null) { result((String) null); } else { Geometry geometry; geometry = wktReader.read(originalStr); if (geometry instanceof Polygon) { Polygon polygon = (Polygon) geometry; Double maxX = null; Coordinate[] coordinates = polygon.getCoordinates(); for (Coordinate coordinate : coordinates) { if (maxX == null || coordinate.x > maxX) { maxX = coordinate.x; } } result(maxX); } else { throw new ParseException(originalStr, 0); } } } catch (ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class MinX extends Function { @Override protected void xFunc() throws SQLException { try { WKTReader wktReader = new WKTReader(); String originalStr = value_text(0); if (originalStr == null) { result((String) null); } else { Polygon polygon; Geometry geometry; geometry = wktReader.read(originalStr); if (geometry instanceof Polygon) { polygon = (Polygon) geometry; Double minX = null; Coordinate[] coordinates = polygon.getCoordinates(); for (Coordinate coordinate : coordinates) { if (minX == null || coordinate.x < minX) { minX = coordinate.x; } } result(minX); } else { throw new ParseException(originalStr, 0); } } } catch (ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class MaxY extends Function { @Override protected void xFunc() throws SQLException { try { // SQLiteDefinition defn = new SQLiteDefinition(); WKTReader wktReader = new WKTReader(); // GeometryFactory factory = new GeometryFactory(); // List coords = new ArrayList(); String originalStr = value_text(0); if (originalStr == null) { result((String) null); } else { Polygon polygon; Geometry geometry; geometry = wktReader.read(originalStr); if (geometry instanceof Polygon) { polygon = (Polygon) geometry; Double maxY = null; Coordinate[] coordinates = polygon.getCoordinates(); for (Coordinate coordinate : coordinates) { if (maxY == null || coordinate.y > maxY) { maxY = coordinate.y; } } result(maxY); } else { throw new ParseException(originalStr, 0); } } // Polygon createPolygon = factory.createPolygon(coords.toArray(new Coordinate[]{})); // result(createPolygon.toText()); } catch (ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class MinY extends Function { @Override protected void xFunc() throws SQLException { try { WKTReader wktReader = new WKTReader(); String originalStr = value_text(0); if (originalStr == null) { result((String) null); } else { Polygon polygon; Geometry geometry; geometry = wktReader.read(originalStr); if (geometry instanceof Polygon) { polygon = (Polygon) geometry; Double minY = null; Coordinate[] coordinates = polygon.getCoordinates(); for (Coordinate coordinate : coordinates) { if (minY == null || coordinate.y < minY) { minY = coordinate.y; } } result(minY); } else { throw new ParseException(originalStr, 0); } } } catch (Exception ex) { throw new RuntimeException("Failed To Parse Polygon", ex); } } } private static class BoundingBox extends Function { @Override protected void xFunc() throws SQLException { try { WKTReader wktReader = new WKTReader(); GeometryFactory factory = new GeometryFactory(); String originalStr = value_text(0); if (originalStr == null) { result((String) null); } else { Polygon polygon; Geometry geometry; geometry = wktReader.read(originalStr); if (geometry instanceof Polygon) { polygon = (Polygon) geometry; Double minX = null; Double minY = null; Double maxX = null; Double maxY = null; Coordinate[] coordinates = polygon.getCoordinates(); for (Coordinate coordinate : coordinates) { if (minX == null || coordinate.x < minX) { minX = coordinate.x; } if (minY == null || coordinate.y < minY) { minY = coordinate.y; } if (maxX == null || coordinate.x > maxX) { maxX = coordinate.x; } if (maxY == null || coordinate.y > minY) { maxY = coordinate.y; } } Polygon createPolygon = factory.createPolygon(new Coordinate[]{ new Coordinate(minX, minY), new Coordinate(maxX, minY), new Coordinate(maxX, maxY), new Coordinate(minX, maxY), new Coordinate(minX, minY),}); createPolygon.normalize(); result(createPolygon.toText()); } else { throw new ParseException(originalStr, 0); } } } catch (ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Equals extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon firstPoly = getPolygon(value_text(0)); Polygon secondPoly = getPolygon(value_text(1)); if (firstPoly == null || secondPoly == null) { result(); } else { firstPoly.normalize(); secondPoly.normalize(); result(firstPoly.toText().equals(secondPoly.toText()) ? 1 : 0); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Area extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly = getPolygon(value_text(0)); if (poly == null) { result(); } else { result(poly.getArea()); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Touches extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Polygon poly2 = getPolygon(value_text(1)); if (poly1 == null || poly2 == null) { result(); } else { result(poly1.touches(poly2) ? 1 : 0); } } catch (Exception ex) { throw new RuntimeException("Failed To Parse Polygon", ex); } } } private static class ExteriorRing extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); if (poly1 == null) { result(); } else { final LineString exteriorRing = poly1.getExteriorRing(); exteriorRing.normalize(); // Polygon exteriorPolygon = (new GeometryFactory()).createPolygon(exteriorRing.getCoordinateSequence()); // result(exteriorPolygon.toText()); LineString createLineString = (new GeometryFactory()).createLineString(exteriorRing.getCoordinates()); Geometry reverse = createLineString.reverse(); result(reverse.toText()); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Contains extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Polygon poly2 = getPolygon(value_text(1)); if (poly1 == null || poly2 == null) { result(); } else { result(poly1.contains(poly2) ? 1 : 0); } } catch (Exception ex) { throw new RuntimeException("Failed To Parse Polygon", ex); } } } private static class ContainsPoint2D extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Point point = getPoint(value_text(1)); if (poly1 == null || point == null) { result(); } else { result(poly1.contains(point) ? 1 : 0); } } catch (Exception ex) { throw new RuntimeException("Failed To Parse Polygon or Point", ex); } } } private static class Within extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Polygon poly2 = getPolygon(value_text(1)); if (poly1 == null || poly2 == null) { result(); } else { result(poly1.within(poly2) ? 1 : 0); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Overlaps extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Polygon poly2 = getPolygon(value_text(1)); if (poly1 == null || poly2 == null) { result(); } else { result(poly1.overlaps(poly2) ? 1 : 0); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Intersects extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Polygon poly2 = getPolygon(value_text(1)); if (poly1 == null || poly2 == null) { result(); } else { result(poly1.intersects(poly2) ? 1 : 0); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(SQLiteDB.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static class Disjoint extends PolygonFunction { @Override protected void xFunc() throws SQLException { try { Polygon poly1 = getPolygon(value_text(0)); Polygon poly2 = getPolygon(value_text(1)); if (poly1 == null || poly2 == null) { result(); } else { result(poly1.disjoint(poly2) ? 1 : 0); } } catch (com.vividsolutions.jts.io.ParseException ex) { Logger.getLogger(Polygon2DFunctions.class.getName()).log(Level.SEVERE, null, ex); throw new RuntimeException("Failed To Parse SQLite Polygon", ex); } } } private static abstract class PolygonFunction extends Function { Polygon getPolygon(String possiblePoly) throws com.vividsolutions.jts.io.ParseException { WKTReader wktReader = new WKTReader(); Geometry firstGeom = wktReader.read(possiblePoly); if (firstGeom instanceof Polygon) { return (Polygon) firstGeom; } return null; } Point getPoint(String possiblePoly) throws com.vividsolutions.jts.io.ParseException { WKTReader wktReader = new WKTReader(); Geometry firstGeom = wktReader.read(possiblePoly); if (firstGeom instanceof Point) { return (Point) firstGeom; } return null; } } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy