Source Code Cross Referenced for GeometryFactory.java in  » GIS » deegree » org » deegree » model » spatialschema » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » GIS » deegree » org.deegree.model.spatialschema 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        //$HeadURL: https://svn.wald.intevation.org/svn/deegree/base/trunk/src/org/deegree/model/spatialschema/GeometryFactory.java $
0002:        /*----------------    FILE HEADER  ------------------------------------------
0003:
0004:         This file is part of deegree.
0005:         Copyright (C) 2001-2008 by:
0006:         EXSE, Department of Geography, University of Bonn
0007:         http://www.giub.uni-bonn.de/deegree/
0008:         lat/lon GmbH
0009:         http://www.lat-lon.de
0010:
0011:         This library is free software; you can redistribute it and/or
0012:         modify it under the terms of the GNU Lesser General Public
0013:         License as published by the Free Software Foundation; either
0014:         version 2.1 of the License, or (at your option) any later version.
0015:
0016:         This library is distributed in the hope that it will be useful,
0017:         but WITHOUT ANY WARRANTY; without even the implied warranty of
0018:         MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0019:         Lesser General Public License for more details.
0020:
0021:         You should have received a copy of the GNU Lesser General Public
0022:         License along with this library; if not, write to the Free Software
0023:         Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
0024:
0025:         Contact:
0026:
0027:         Andreas Poth
0028:         lat/lon GmbH
0029:         Aennchenstr. 19
0030:         53115 Bonn
0031:         Germany
0032:         E-Mail: poth@lat-lon.de
0033:
0034:         Prof. Dr. Klaus Greve
0035:         Department of Geography
0036:         University of Bonn
0037:         Meckenheimer Allee 166
0038:         53115 Bonn
0039:         Germany
0040:         E-Mail: greve@giub.uni-bonn.de
0041:
0042:
0043:         ---------------------------------------------------------------------------*/
0044:        package org.deegree.model.spatialschema;
0045:
0046:        import java.util.ArrayList;
0047:
0048:        import javax.vecmath.Point3d;
0049:
0050:        import org.deegree.framework.util.StringTools;
0051:        import org.deegree.model.crs.CoordinateSystem;
0052:
0053:        /**
0054:         * Factory to create geometry instances.
0055:         * 
0056:         * @author <a href="mailto:poth@lat-lon.de">Andreas Poth</a>
0057:         * @version $Revision: 10278 $, $Date: 2008-02-25 06:53:37 -0800 (Mon, 25 Feb 2008) $
0058:         * 
0059:         */
0060:        public final class GeometryFactory {
0061:
0062:            private GeometryFactory() {
0063:                // Hidden default constructor.
0064:            }
0065:
0066:            /**
0067:             * creates a Envelope object out from two corner coordinates
0068:             * 
0069:             * @param minx
0070:             *            lower x-axis coordinate
0071:             * @param miny
0072:             *            lower y-axis coordinate
0073:             * @param maxx
0074:             *            upper x-axis coordinate
0075:             * @param maxy
0076:             *            upper y-axis coordinate
0077:             * @param crs
0078:             *            The coordinate system
0079:             * @return an Envelope with given parameters
0080:             */
0081:            public static Envelope createEnvelope(double minx, double miny,
0082:                    double maxx, double maxy, CoordinateSystem crs) {
0083:                Position min = createPosition(minx, miny);
0084:                Position max = createPosition(maxx, maxy);
0085:                return new EnvelopeImpl(min, max, crs);
0086:            }
0087:
0088:            /**
0089:             * creates a Envelope object out from two corner coordinates
0090:             * 
0091:             * @param min
0092:             *            lower point
0093:             * @param max
0094:             *            upper point
0095:             * @param crs
0096:             *            The coordinate system
0097:             * @return an Envelope with given parameters
0098:             */
0099:            public static Envelope createEnvelope(Position min, Position max,
0100:                    CoordinateSystem crs) {
0101:                return new EnvelopeImpl(min, max, crs);
0102:            }
0103:
0104:            /**
0105:             * creates an Envelope from a comma seperated String; e.g.: 10,34,15,48
0106:             * 
0107:             * @param bbox
0108:             *            the boundingbox of the created Envelope
0109:             * @param crs
0110:             *            The coordinate system
0111:             * @return an Envelope with given parameters
0112:             */
0113:            public static Envelope createEnvelope(String bbox,
0114:                    CoordinateSystem crs) {
0115:                double[] d = StringTools.toArrayDouble(bbox, ",");
0116:                return createEnvelope(d[0], d[1], d[2], d[3], crs);
0117:            }
0118:
0119:            /**
0120:             * creates a Position from two coordinates.
0121:             * 
0122:             * @param x
0123:             *            coordinate on the x-axis
0124:             * @param y
0125:             *            coordinate on the y-axis
0126:             * @return a Position defining position x, y
0127:             */
0128:            public static Position createPosition(double x, double y) {
0129:                return new PositionImpl(x, y);
0130:            }
0131:
0132:            /**
0133:             * creates a Position from three coordinates.
0134:             * 
0135:             * @param x
0136:             *            coordinate on the x-axis
0137:             * @param y
0138:             *            coordinate on the y-axis
0139:             * @param z
0140:             *            coordinate on the z-axis
0141:             * @return a Position defining position x, y, z
0142:             */
0143:            public static Position createPosition(double x, double y, double z) {
0144:                return new PositionImpl(new double[] { x, y, z });
0145:            }
0146:
0147:            /**
0148:             * creates a Position from a point3d.
0149:             * 
0150:             * @param coordinates
0151:             *            the coordinates to create the position from.
0152:             * @return a Position defining position x, y, z
0153:             */
0154:            public static Position createPosition(Point3d coordinates) {
0155:                return new PositionImpl(coordinates);
0156:            }
0157:
0158:            /**
0159:             * creates a Position from an array of double.
0160:             * 
0161:             * @param p
0162:             *            list of points
0163:             * @return the Position defined by the array.
0164:             */
0165:            public static Position createPosition(double[] p) {
0166:                return new PositionImpl(p);
0167:            }
0168:
0169:            /**
0170:             * creates a Point from two coordinates.
0171:             * 
0172:             * @param x
0173:             *            x coordinate
0174:             * @param y
0175:             *            y coordinate
0176:             * @param crs
0177:             *            spatial reference system of the point geometry
0178:             * @return a Position defining position x, y in the given CRS
0179:             */
0180:            public static Point createPoint(double x, double y,
0181:                    CoordinateSystem crs) {
0182:                return new PointImpl(x, y, crs);
0183:            }
0184:
0185:            /**
0186:             * creates a Point from two coordinates.
0187:             * 
0188:             * @param x
0189:             *            x coordinate
0190:             * @param y
0191:             *            y coordinate
0192:             * @param z
0193:             *            coordinate on the z-axis
0194:             * @param crs
0195:             *            spatial reference system of the point geometry
0196:             * @return a Position defining position x, y, z in the given CRS
0197:             */
0198:            public static Point createPoint(double x, double y, double z,
0199:                    CoordinateSystem crs) {
0200:                return new PointImpl(x, y, z, crs);
0201:            }
0202:
0203:            /**
0204:             * creates a Point from a position.
0205:             * 
0206:             * @param position
0207:             *            position
0208:             * @param crs
0209:             *            spatial reference system of the point geometry
0210:             * @return the Position defined by the array in the given CRS
0211:             */
0212:            public static Point createPoint(Position position,
0213:                    CoordinateSystem crs) {
0214:                return new PointImpl(position, crs);
0215:            }
0216:
0217:            /**
0218:             * creates a Point from a wkb.
0219:             * 
0220:             * @param wkb
0221:             *            geometry in Well-Known Binary (WKB) format
0222:             * @param srs
0223:             *            spatial reference system of the geometry
0224:             * @return the Position defined by the WKB and the given CRS
0225:             * @throws GeometryException
0226:             *             if the wkb is not known or invalid
0227:             */
0228:            public static Point createPoint(byte[] wkb, CoordinateSystem srs)
0229:                    throws GeometryException {
0230:                int wkbType = -1;
0231:                double x = 0;
0232:                double y = 0;
0233:
0234:                byte byteorder = wkb[0];
0235:
0236:                if (byteorder == 0) {
0237:                    wkbType = ByteUtils.readBEInt(wkb, 1);
0238:                } else {
0239:                    wkbType = ByteUtils.readLEInt(wkb, 1);
0240:                }
0241:
0242:                if (wkbType != 1) {
0243:                    throw new GeometryException("invalid byte stream");
0244:                }
0245:
0246:                if (byteorder == 0) {
0247:                    x = ByteUtils.readBEDouble(wkb, 5);
0248:                    y = ByteUtils.readBEDouble(wkb, 13);
0249:                } else {
0250:                    x = ByteUtils.readLEDouble(wkb, 5);
0251:                    y = ByteUtils.readLEDouble(wkb, 13);
0252:                }
0253:
0254:                return new PointImpl(x, y, srs);
0255:            }
0256:
0257:            /**
0258:             * creates a CurveSegment from an array of points.
0259:             * 
0260:             * @param points
0261:             *            array of Point
0262:             * @param crs
0263:             *            CS_CoordinateSystem spatial reference system of the curve
0264:             * @return A curve defined by the given Points in the CRS.
0265:             * @throws GeometryException
0266:             *             if the point array is empty
0267:             */
0268:            public static CurveSegment createCurveSegment(Position[] points,
0269:                    CoordinateSystem crs) throws GeometryException {
0270:                return new LineStringImpl(points, crs);
0271:            }
0272:
0273:            /**
0274:             * creates a Curve from an array of Positions.
0275:             * 
0276:             * @param positions
0277:             *            positions
0278:             * @param crs
0279:             *            spatial reference system of the geometry
0280:             * @return A curve defined by the given Points in the CRS.
0281:             * @throws GeometryException
0282:             *             if the point array is empty
0283:             */
0284:            public static Curve createCurve(Position[] positions,
0285:                    CoordinateSystem crs) throws GeometryException {
0286:                CurveSegment[] cs = new CurveSegment[1];
0287:                cs[0] = createCurveSegment(positions, crs);
0288:                return new CurveImpl(cs);
0289:            }
0290:
0291:            /**
0292:             * creates a Curve from one curve segment.
0293:             * 
0294:             * @param segment
0295:             *            CurveSegments
0296:             * @return a new CurveSegment
0297:             * @throws GeometryException
0298:             *             if the segment is null
0299:             */
0300:            public static Curve createCurve(CurveSegment segment)
0301:                    throws GeometryException {
0302:                return new CurveImpl(new CurveSegment[] { segment });
0303:            }
0304:
0305:            /**
0306:             * creates a Curve from an array of curve segments.
0307:             * 
0308:             * @param segments
0309:             *            array of CurveSegments
0310:             * @return a new CurveSegment
0311:             * @throws GeometryException
0312:             *             if the segment is null or has no values
0313:             * 
0314:             */
0315:            public static Curve createCurve(CurveSegment[] segments)
0316:                    throws GeometryException {
0317:                return new CurveImpl(segments);
0318:            }
0319:
0320:            /**
0321:             * creates a Curve from an array of curve segments.
0322:             * 
0323:             * @param segments
0324:             *            array of CurveSegments
0325:             * @param crs
0326:             * @return a new CurveSegment
0327:             * @throws GeometryException
0328:             *             if the segment is null or has no values
0329:             * 
0330:             */
0331:            public static Curve createCurve(CurveSegment[] segments,
0332:                    CoordinateSystem crs) throws GeometryException {
0333:                return new CurveImpl(segments, crs);
0334:            }
0335:
0336:            /**
0337:             * creates a GM_Curve from an array of ordinates
0338:             * 
0339:             * TODO: If resources are available, think about good programming style.
0340:             * 
0341:             * @param ord
0342:             *            the ordinates
0343:             * @param dim
0344:             *            the dimension of the ordinates
0345:             * @param crs
0346:             *            the spatial reference system of the geometry
0347:             * 
0348:             * @return the Curve defined by the given parameters
0349:             * @throws GeometryException
0350:             *             if the ord array is empty
0351:             */
0352:            public static Curve createCurve(double[] ord, int dim,
0353:                    CoordinateSystem crs) throws GeometryException {
0354:                Position[] pos = new Position[ord.length / dim];
0355:                int i = 0;
0356:                while (i < ord.length) {
0357:                    double[] o = new double[dim];
0358:                    for (int j = 0; j < dim; j++) {
0359:                        o[j] = ord[i++];
0360:                    }
0361:                    pos[i / dim - 1] = GeometryFactory.createPosition(o);
0362:                }
0363:                return GeometryFactory.createCurve(pos, crs);
0364:            }
0365:
0366:            /**
0367:             * creates a SurfacePatch from array(s) of Position
0368:             * 
0369:             * @param exteriorRing
0370:             *            exterior ring of the patch
0371:             * @param interiorRings
0372:             *            interior rings of the patch
0373:             * @param si
0374:             *            SurfaceInterpolation
0375:             * @param crs
0376:             *            CS_CoordinateSystem spatial reference system of the surface patch
0377:             * @return a Surfacepatch defined by the given Parameters
0378:             * @throws GeometryException
0379:             */
0380:            public static SurfacePatch createSurfacePatch(
0381:                    Position[] exteriorRing, Position[][] interiorRings,
0382:                    SurfaceInterpolation si, CoordinateSystem crs)
0383:                    throws GeometryException {
0384:                return new PolygonImpl(si, exteriorRing, interiorRings, crs);
0385:            }
0386:
0387:            /**
0388:             * 
0389:             * @param exteriorRing
0390:             * @param interiorRings
0391:             * @param crs
0392:             * @return
0393:             * @throws GeometryException
0394:             */
0395:            public static SurfacePatch createSurfacePatch(
0396:                    CurveSegment[] exteriorRing,
0397:                    CurveSegment[][] interiorRings, CoordinateSystem crs)
0398:                    throws GeometryException {
0399:                Ring eRing = new RingImpl(exteriorRing, crs, '+');
0400:                Ring[] iRings = null;
0401:                if (interiorRings != null) {
0402:                    iRings = new Ring[interiorRings.length];
0403:                    for (int i = 0; i < iRings.length; i++) {
0404:                        iRings[i] = new RingImpl(interiorRings[i], crs, '+');
0405:                    }
0406:                }
0407:                return new PolygonImpl(eRing, iRings, crs);
0408:            }
0409:
0410:            /**
0411:             * 
0412:             * @param exteriorRing
0413:             * @param interiorRings
0414:             * @param crs
0415:             * @return
0416:             * @throws GeometryException
0417:             */
0418:            public static SurfacePatch createSurfacePatch(Curve exteriorRing,
0419:                    Curve[] interiorRings, CoordinateSystem crs)
0420:                    throws GeometryException {
0421:                CurveSegment[] e = exteriorRing.getCurveSegments();
0422:                CurveSegment[][] i = null;
0423:                if (interiorRings != null) {
0424:                    i = new CurveSegment[interiorRings.length][];
0425:                    for (int j = 0; j < i.length; j++) {
0426:                        i[j] = interiorRings[j].getCurveSegments();
0427:                    }
0428:                }
0429:                return createSurfacePatch(e, i, crs);
0430:            }
0431:
0432:            /**
0433:             * creates a Curve from a wkb.
0434:             * 
0435:             * @param wkb
0436:             *            byte stream that contains the wkb information
0437:             * @param crs
0438:             *            CS_CoordinateSystem spatial reference system of the curve
0439:             * @return the Curve defined by the WKB and the given CRS
0440:             * @throws GeometryException
0441:             *             if the wkb is not known or invalid
0442:             * 
0443:             */
0444:            public static Curve createCurve(byte[] wkb, CoordinateSystem crs)
0445:                    throws GeometryException {
0446:                int wkbType = -1;
0447:                int numPoints = -1;
0448:                Position[] points = null;
0449:                double x = 0;
0450:                double y = 0;
0451:
0452:                byte byteorder = wkb[0];
0453:
0454:                if (byteorder == 0) {
0455:                    wkbType = ByteUtils.readBEInt(wkb, 1);
0456:                } else {
0457:                    wkbType = ByteUtils.readLEInt(wkb, 1);
0458:                }
0459:
0460:                // check if it's realy a linestrin/curve
0461:                if (wkbType != 2) {
0462:                    throw new GeometryException("invalid byte stream for Curve");
0463:                }
0464:
0465:                // read number of points
0466:                if (byteorder == 0) {
0467:                    numPoints = ByteUtils.readBEInt(wkb, 5);
0468:                } else {
0469:                    numPoints = ByteUtils.readLEInt(wkb, 5);
0470:                }
0471:
0472:                int offset = 9;
0473:
0474:                points = new Position[numPoints];
0475:
0476:                // read the i-th point depending on the byteorde
0477:                if (byteorder == 0) {
0478:                    for (int i = 0; i < numPoints; i++) {
0479:                        x = ByteUtils.readBEDouble(wkb, offset);
0480:                        offset += 8;
0481:                        y = ByteUtils.readBEDouble(wkb, offset);
0482:                        offset += 8;
0483:                        points[i] = new PositionImpl(x, y);
0484:                    }
0485:                } else {
0486:                    for (int i = 0; i < numPoints; i++) {
0487:                        x = ByteUtils.readLEDouble(wkb, offset);
0488:                        offset += 8;
0489:                        y = ByteUtils.readLEDouble(wkb, offset);
0490:                        offset += 8;
0491:                        points[i] = new PositionImpl(x, y);
0492:                    }
0493:                }
0494:
0495:                CurveSegment[] segment = new CurveSegment[1];
0496:
0497:                segment[0] = createCurveSegment(points, crs);
0498:
0499:                return createCurve(segment);
0500:            }
0501:
0502:            /**
0503:             * creates a Surface composed of one SurfacePatch from array(s) of Position
0504:             * 
0505:             * @param exteriorRing
0506:             *            exterior ring of the patch
0507:             * @param interiorRings
0508:             *            interior rings of the patch
0509:             * @param si
0510:             *            SurfaceInterpolation
0511:             * @param crs
0512:             *            CS_CoordinateSystem spatial reference system of the surface patch
0513:             * @return a Surface composed of one SurfacePatch from array(s) of Position
0514:             * @throws GeometryException
0515:             *             if the implicite orientation is not '+' or '-', or the rings aren't closed
0516:             */
0517:            public static Surface createSurface(Position[] exteriorRing,
0518:                    Position[][] interiorRings, SurfaceInterpolation si,
0519:                    CoordinateSystem crs) throws GeometryException {
0520:                SurfacePatch sp = new PolygonImpl(si, exteriorRing,
0521:                        interiorRings, crs);
0522:                return createSurface(sp);
0523:            }
0524:
0525:            /**
0526:             * creates a Surface from an array of SurfacePatch.
0527:             * 
0528:             * @param patch
0529:             *            patches that build the surface
0530:             * @return a Surface from an array of SurfacePatch.
0531:             * @throws GeometryException
0532:             *             if implicite the orientation is not '+' or '-'
0533:             */
0534:            public static Surface createSurface(SurfacePatch patch)
0535:                    throws GeometryException {
0536:                return new SurfaceImpl(patch);
0537:            }
0538:
0539:            /**
0540:             * creates a Surface from an array of SurfacePatch.
0541:             * 
0542:             * @param patches
0543:             *            patches that build the surface
0544:             * 
0545:             * @return a Surface from an array of SurfacePatch.
0546:             * @throws GeometryException
0547:             *             if implicite the orientation is not '+' or '-'
0548:             */
0549:            public static Surface createSurface(SurfacePatch[] patches)
0550:                    throws GeometryException {
0551:                return new SurfaceImpl(patches);
0552:            }
0553:
0554:            /**
0555:             * creates a Surface from an array of SurfacePatch.
0556:             * 
0557:             * @param patches
0558:             *            patches that build the surface
0559:             * @param crs
0560:             * 
0561:             * @return a Surface from an array of SurfacePatch.
0562:             * @throws GeometryException
0563:             *             if implicite the orientation is not '+' or '-'
0564:             */
0565:            public static Surface createSurface(SurfacePatch[] patches,
0566:                    CoordinateSystem crs) throws GeometryException {
0567:                return new SurfaceImpl(patches, crs);
0568:            }
0569:
0570:            /**
0571:             * creates a Surface from a wkb.
0572:             * 
0573:             * @param wkb
0574:             *            byte stream that contains the wkb information
0575:             * @param crs
0576:             *            CS_CoordinateSystem spatial reference system of the curve
0577:             * @param si
0578:             *            SurfaceInterpolation
0579:             * @return a Surface from a wkb.
0580:             * @throws GeometryException
0581:             *             if the implicite orientation is not '+' or '-' or the wkb is not known or invalid
0582:             */
0583:            public static Surface createSurface(byte[] wkb,
0584:                    CoordinateSystem crs, SurfaceInterpolation si)
0585:                    throws GeometryException {
0586:                int wkbtype = -1;
0587:                int numRings = 0;
0588:                int numPoints = 0;
0589:                int offset = 0;
0590:                double x = 0;
0591:                double y = 0;
0592:
0593:                Position[] externalBoundary = null;
0594:                Position[][] internalBoundaries = null;
0595:
0596:                byte byteorder = wkb[offset++];
0597:
0598:                if (byteorder == 0) {
0599:                    wkbtype = ByteUtils.readBEInt(wkb, offset);
0600:                } else {
0601:                    wkbtype = ByteUtils.readLEInt(wkb, offset);
0602:                }
0603:
0604:                offset += 4;
0605:
0606:                if (wkbtype == 6) {
0607:                    return null;
0608:                }
0609:
0610:                // is the geometry respresented by wkb a polygon?
0611:                if (wkbtype != 3) {
0612:                    throw new GeometryException(
0613:                            "invalid byte stream for Surface " + wkbtype);
0614:                }
0615:
0616:                // read number of rings of the polygon
0617:                if (byteorder == 0) {
0618:                    numRings = ByteUtils.readBEInt(wkb, offset);
0619:                } else {
0620:                    numRings = ByteUtils.readLEInt(wkb, offset);
0621:                }
0622:
0623:                offset += 4;
0624:
0625:                // read number of points of the external ring
0626:                if (byteorder == 0) {
0627:                    numPoints = ByteUtils.readBEInt(wkb, offset);
0628:                } else {
0629:                    numPoints = ByteUtils.readLEInt(wkb, offset);
0630:                }
0631:
0632:                offset += 4;
0633:
0634:                // allocate memory for the external boundary
0635:                externalBoundary = new Position[numPoints];
0636:
0637:                if (byteorder == 0) {
0638:                    // read points of the external boundary from the byte[]
0639:                    for (int i = 0; i < numPoints; i++) {
0640:                        x = ByteUtils.readBEDouble(wkb, offset);
0641:                        offset += 8;
0642:                        y = ByteUtils.readBEDouble(wkb, offset);
0643:                        offset += 8;
0644:                        externalBoundary[i] = new PositionImpl(x, y);
0645:                    }
0646:                } else {
0647:                    // read points of the external boundary from the byte[]
0648:                    for (int i = 0; i < numPoints; i++) {
0649:                        x = ByteUtils.readLEDouble(wkb, offset);
0650:                        offset += 8;
0651:                        y = ByteUtils.readLEDouble(wkb, offset);
0652:                        offset += 8;
0653:                        externalBoundary[i] = new PositionImpl(x, y);
0654:                    }
0655:                }
0656:
0657:                // only if numRings is larger then one there internal rings
0658:                if (numRings > 1) {
0659:                    internalBoundaries = new Position[numRings - 1][];
0660:                }
0661:
0662:                if (byteorder == 0) {
0663:                    for (int j = 1; j < numRings; j++) {
0664:                        // read number of points of the j-th internal ring
0665:                        numPoints = ByteUtils.readBEInt(wkb, offset);
0666:                        offset += 4;
0667:
0668:                        // allocate memory for the j-th internal boundary
0669:                        internalBoundaries[j - 1] = new Position[numPoints];
0670:
0671:                        // read points of the external boundary from the byte[]
0672:                        for (int i = 0; i < numPoints; i++) {
0673:                            x = ByteUtils.readBEDouble(wkb, offset);
0674:                            offset += 8;
0675:                            y = ByteUtils.readBEDouble(wkb, offset);
0676:                            offset += 8;
0677:                            internalBoundaries[j - 1][i] = new PositionImpl(x,
0678:                                    y);
0679:                        }
0680:                    }
0681:                } else {
0682:                    for (int j = 1; j < numRings; j++) {
0683:                        // read number of points of the j-th internal ring
0684:                        numPoints = ByteUtils.readLEInt(wkb, offset);
0685:                        offset += 4;
0686:
0687:                        // allocate memory for the j-th internal boundary
0688:                        internalBoundaries[j - 1] = new Position[numPoints];
0689:
0690:                        // read points of the external boundary from the byte[]
0691:                        for (int i = 0; i < numPoints; i++) {
0692:                            x = ByteUtils.readLEDouble(wkb, offset);
0693:                            offset += 8;
0694:                            y = ByteUtils.readLEDouble(wkb, offset);
0695:                            offset += 8;
0696:                            internalBoundaries[j - 1][i] = new PositionImpl(x,
0697:                                    y);
0698:                        }
0699:                    }
0700:                }
0701:
0702:                SurfacePatch patch = createSurfacePatch(externalBoundary,
0703:                        internalBoundaries, si, crs);
0704:
0705:                return createSurface(patch);
0706:            }
0707:
0708:            /**
0709:             * Creates a <tt>Surface</tt> from a <tt>Envelope</tt>.
0710:             * <p>
0711:             * 
0712:             * @param bbox
0713:             *            envelope to be converted
0714:             * @param crs
0715:             *            spatial reference system of the surface
0716:             * @return corresponding surface
0717:             * 
0718:             * @throws GeometryException
0719:             *             if the implicite orientation is not '+' or '-'
0720:             */
0721:            public static Surface createSurface(Envelope bbox,
0722:                    CoordinateSystem crs) throws GeometryException {
0723:
0724:                Position min = bbox.getMin();
0725:                Position max = bbox.getMax();
0726:                Position[] exteriorRing = null;
0727:                if (min.getCoordinateDimension() == 2) {
0728:                    exteriorRing = new Position[] { min,
0729:                            new PositionImpl(min.getX(), max.getY()), max,
0730:                            new PositionImpl(max.getX(), min.getY()), min };
0731:                } else {
0732:                    exteriorRing = new Position[] {
0733:                            min,
0734:                            new PositionImpl(min.getX(), max.getY(), min.getZ()
0735:                                    + ((max.getZ() - min.getZ()) * 0.5)),
0736:                            max,
0737:                            new PositionImpl(max.getX(), min.getY(), min.getZ()
0738:                                    + ((max.getZ() - min.getZ()) * 0.5)), min };
0739:                }
0740:
0741:                return createSurface(exteriorRing, null,
0742:                        new SurfaceInterpolationImpl(), crs);
0743:            }
0744:
0745:            /**
0746:             * Creates a <tt>GM_Surface</tt> from the ordinates of the exterior ring and the the interior rings
0747:             * <p>
0748:             * 
0749:             * @param exterior
0750:             *            ring
0751:             * @param interior
0752:             *            ring
0753:             * @param dim
0754:             *            of the surface
0755:             * @param crs
0756:             *            spatial reference system of the surface
0757:             * @return corresponding surface
0758:             * @throws GeometryException
0759:             *             if the implicite orientation is not '+' or '-'
0760:             * 
0761:             */
0762:            public static Surface createSurface(double[] exterior,
0763:                    double[][] interior, int dim, CoordinateSystem crs)
0764:                    throws GeometryException {
0765:
0766:                // get exterior ring
0767:                Position[] ext = new Position[exterior.length / dim];
0768:                int i = 0;
0769:                int k = 0;
0770:                while (i < exterior.length - 1) {
0771:                    double[] o = new double[dim];
0772:                    for (int j = 0; j < dim; j++) {
0773:                        o[j] = exterior[i++];
0774:                    }
0775:                    ext[k++] = GeometryFactory.createPosition(o);
0776:                }
0777:
0778:                // get interior rings if available
0779:                Position[][] in = null;
0780:                if (interior != null && interior.length > 0) {
0781:                    in = new Position[interior.length][];
0782:                    for (int j = 0; j < in.length; j++) {
0783:                        in[j] = new Position[interior[j].length / dim];
0784:                        i = 0;
0785:                        while (i < interior[j].length) {
0786:                            double[] o = new double[dim];
0787:                            for (int z = 0; z < dim; z++) {
0788:                                o[z] = interior[j][i++];
0789:                            }
0790:                            in[j][i / dim - 1] = GeometryFactory
0791:                                    .createPosition(o);
0792:                        }
0793:                    }
0794:                }
0795:
0796:                // default - linear - interpolation
0797:                SurfaceInterpolation si = new SurfaceInterpolationImpl();
0798:                return GeometryFactory.createSurface(ext, in, si, crs);
0799:            }
0800:
0801:            /**
0802:             * creates a MultiPoint from an array of Point.
0803:             * 
0804:             * @param points
0805:             *            array of Points
0806:             * @return a MultiPoint from an array of Point.
0807:             * 
0808:             */
0809:            public static MultiPoint createMultiPoint(Point[] points) {
0810:                return new MultiPointImpl(points);
0811:            }
0812:
0813:            /**
0814:             * creates a MultiPoint from an array of Point.
0815:             * 
0816:             * @param points
0817:             *            array of Points
0818:             * @param crs
0819:             * @return a MultiPoint from an array of Point.
0820:             */
0821:            public static MultiPoint createMultiPoint(Point[] points,
0822:                    CoordinateSystem crs) {
0823:                return new MultiPointImpl(points, crs);
0824:            }
0825:
0826:            /**
0827:             * creates a MultiPoint from a wkb.
0828:             * 
0829:             * @param wkb
0830:             *            byte stream that contains the wkb information
0831:             * @param crs
0832:             *            CS_CoordinateSystem spatial reference system of the curve
0833:             * @return the MultiPoint defined by the WKB and the given CRS
0834:             * @throws GeometryException
0835:             *             if the wkb is not known or invalid
0836:             * 
0837:             */
0838:            public static MultiPoint createMultiPoint(byte[] wkb,
0839:                    CoordinateSystem crs) throws GeometryException {
0840:                Point[] points = null;
0841:                int wkbType = -1;
0842:                int numPoints = -1;
0843:                double x = 0;
0844:                double y = 0;
0845:                byte byteorder = wkb[0];
0846:
0847:                // read wkbType
0848:                if (byteorder == 0) {
0849:                    wkbType = ByteUtils.readBEInt(wkb, 1);
0850:                } else {
0851:                    wkbType = ByteUtils.readLEInt(wkb, 1);
0852:                }
0853:
0854:                // if the geometry isn't a multipoint throw exception
0855:                if (wkbType != 4) {
0856:                    throw new GeometryException(
0857:                            "Invalid byte stream for MultiPoint");
0858:                }
0859:
0860:                // read number of points
0861:                if (byteorder == 0) {
0862:                    numPoints = ByteUtils.readBEInt(wkb, 5);
0863:                } else {
0864:                    numPoints = ByteUtils.readLEInt(wkb, 5);
0865:                }
0866:
0867:                points = new Point[numPoints];
0868:
0869:                int offset = 9;
0870:
0871:                Object[] o = new Object[3];
0872:                o[2] = crs;
0873:
0874:                // read all points
0875:                for (int i = 0; i < numPoints; i++) {
0876:                    // byteorder of the i-th point
0877:                    byteorder = wkb[offset];
0878:
0879:                    // wkbType of the i-th geometry
0880:                    if (byteorder == 0) {
0881:                        wkbType = ByteUtils.readBEInt(wkb, offset + 1);
0882:                    } else {
0883:                        wkbType = ByteUtils.readLEInt(wkb, offset + 1);
0884:                    }
0885:
0886:                    // if the geometry isn't a point throw exception
0887:                    if (wkbType != 1) {
0888:                        throw new GeometryException(
0889:                                "Invalid byte stream for Point as "
0890:                                        + "part of a multi point");
0891:                    }
0892:
0893:                    // read the i-th point depending on the byteorde
0894:                    if (byteorder == 0) {
0895:                        x = ByteUtils.readBEDouble(wkb, offset + 5);
0896:                        y = ByteUtils.readBEDouble(wkb, offset + 13);
0897:                    } else {
0898:                        x = ByteUtils.readLEDouble(wkb, offset + 5);
0899:                        y = ByteUtils.readLEDouble(wkb, offset + 13);
0900:                    }
0901:
0902:                    offset += 21;
0903:
0904:                    points[i] = new PointImpl(x, y, crs);
0905:                }
0906:
0907:                return createMultiPoint(points);
0908:            }
0909:
0910:            /**
0911:             * creates a MultiCurve from an array of Curves.
0912:             * 
0913:             * @param curves
0914:             * @return a MultiCurve from an array of Curves.
0915:             */
0916:            public static MultiCurve createMultiCurve(Curve[] curves) {
0917:                return new MultiCurveImpl(curves);
0918:            }
0919:
0920:            /**
0921:             * creates a MultiCurve from an array of Curves.
0922:             * 
0923:             * @param curves
0924:             * @param crs
0925:             * @return a MultiCurve from an array of Curves.
0926:             */
0927:            public static MultiCurve createMultiCurve(Curve[] curves,
0928:                    CoordinateSystem crs) {
0929:                return new MultiCurveImpl(curves, crs);
0930:            }
0931:
0932:            /**
0933:             * creates a MultiCurve from a wkb.
0934:             * 
0935:             * @param wkb
0936:             *            byte stream that contains the wkb information
0937:             * @param crs
0938:             *            CS_CoordinateSystem spatial reference system of the curve
0939:             * @return the MultiCurve defined by the WKB and the given CRS
0940:             * @throws GeometryException
0941:             *             if the wkb is not known or invalid
0942:             */
0943:            public static MultiCurve createMultiCurve(byte[] wkb,
0944:                    CoordinateSystem crs) throws GeometryException {
0945:                int wkbType = -1;
0946:                int numPoints = -1;
0947:                int numParts = -1;
0948:                double x = 0;
0949:                double y = 0;
0950:                Position[][] points = null;
0951:                int offset = 0;
0952:                byte byteorder = wkb[offset++];
0953:
0954:                if (byteorder == 0) {
0955:                    wkbType = ByteUtils.readBEInt(wkb, offset);
0956:                } else {
0957:                    wkbType = ByteUtils.readLEInt(wkb, offset);
0958:                }
0959:
0960:                offset += 4;
0961:
0962:                // check if it's realy a linestring
0963:                if (wkbType != 5) {
0964:                    throw new GeometryException(
0965:                            "Invalid byte stream for MultiCurve");
0966:                }
0967:
0968:                // read number of linestrings
0969:                if (byteorder == 0) {
0970:                    numParts = ByteUtils.readBEInt(wkb, offset);
0971:                } else {
0972:                    numParts = ByteUtils.readLEInt(wkb, offset);
0973:                }
0974:
0975:                offset += 4;
0976:
0977:                points = new Position[numParts][];
0978:
0979:                // for every linestring
0980:                for (int j = 0; j < numParts; j++) {
0981:                    byteorder = wkb[offset++];
0982:
0983:                    if (byteorder == 0) {
0984:                        wkbType = ByteUtils.readBEInt(wkb, offset);
0985:                    } else {
0986:                        wkbType = ByteUtils.readLEInt(wkb, offset);
0987:                    }
0988:
0989:                    offset += 4;
0990:
0991:                    // check if it's realy a linestring
0992:                    if (wkbType != 2) {
0993:                        throw new GeometryException(
0994:                                "Invalid byte stream for Curve as "
0995:                                        + " part of a MultiCurve.");
0996:                    }
0997:
0998:                    // read number of points
0999:                    if (byteorder == 0) {
1000:                        numPoints = ByteUtils.readBEInt(wkb, offset);
1001:                    } else {
1002:                        numPoints = ByteUtils.readLEInt(wkb, offset);
1003:                    }
1004:
1005:                    offset += 4;
1006:
1007:                    points[j] = new Position[numPoints];
1008:
1009:                    // read the i-th point depending on the byteorde
1010:                    if (byteorder == 0) {
1011:                        for (int i = 0; i < numPoints; i++) {
1012:                            x = ByteUtils.readBEDouble(wkb, offset);
1013:                            offset += 8;
1014:                            y = ByteUtils.readBEDouble(wkb, offset);
1015:                            offset += 8;
1016:                            points[j][i] = new PositionImpl(x, y);
1017:                        }
1018:                    } else {
1019:                        for (int i = 0; i < numPoints; i++) {
1020:                            x = ByteUtils.readLEDouble(wkb, offset);
1021:                            offset += 8;
1022:                            y = ByteUtils.readLEDouble(wkb, offset);
1023:                            offset += 8;
1024:                            points[j][i] = new PositionImpl(x, y);
1025:                        }
1026:                    }
1027:                }
1028:
1029:                CurveSegment[] segment = new CurveSegment[1];
1030:                Curve[] curves = new Curve[numParts];
1031:
1032:                for (int i = 0; i < numParts; i++) {
1033:                    segment[0] = createCurveSegment(points[i], crs);
1034:                    curves[i] = createCurve(segment);
1035:                }
1036:
1037:                return createMultiCurve(curves);
1038:            }
1039:
1040:            /**
1041:             * creates a MultiSurface from an array of surfaces
1042:             * 
1043:             * @param surfaces
1044:             * @return a MultiSurface from an array of surfaces
1045:             */
1046:            public static MultiSurface createMultiSurface(Surface[] surfaces) {
1047:                return new MultiSurfaceImpl(surfaces);
1048:            }
1049:
1050:            /**
1051:             * creates a MultiSurface from an array of surfaces
1052:             * 
1053:             * @param surfaces
1054:             * @param crs
1055:             * @return a MultiSurface from an array of surfaces
1056:             */
1057:            public static MultiSurface createMultiSurface(Surface[] surfaces,
1058:                    CoordinateSystem crs) {
1059:                return new MultiSurfaceImpl(surfaces, crs);
1060:            }
1061:
1062:            /**
1063:             * creates a MultiSurface from a wkb
1064:             * 
1065:             * @param wkb
1066:             *            geometry in Well-Known Binary (WKB) format
1067:             * @param crs
1068:             *            spatial reference system of the geometry
1069:             * @param si
1070:             *            surface interpolation
1071:             * @return the MultiSurface defined by the WKB and the given CRS
1072:             * @throws GeometryException
1073:             *             if the wkb is not known or invalid
1074:             */
1075:            public static MultiSurface createMultiSurface(byte[] wkb,
1076:                    CoordinateSystem crs, SurfaceInterpolation si)
1077:                    throws GeometryException {
1078:                int wkbtype = -1;
1079:                int numPoly = 0;
1080:                int numRings = 0;
1081:                int numPoints = 0;
1082:                int offset = 0;
1083:                double x = 0;
1084:                double y = 0;
1085:                Position[] externalBoundary = null;
1086:                Position[][] internalBoundaries = null;
1087:                byte byteorder = wkb[offset++];
1088:
1089:                if (byteorder == 0) {
1090:                    wkbtype = ByteUtils.readBEInt(wkb, offset);
1091:                } else {
1092:                    wkbtype = ByteUtils.readLEInt(wkb, offset);
1093:                }
1094:
1095:                offset += 4;
1096:
1097:                // is the wkbmetry a multipolygon?
1098:                if (wkbtype != 6) {
1099:                    throw new GeometryException(
1100:                            "Invalid byte stream for MultiSurface");
1101:                }
1102:
1103:                // read number of polygons on the byte[]
1104:                if (byteorder == 0) {
1105:                    numPoly = ByteUtils.readBEInt(wkb, offset);
1106:                } else {
1107:                    numPoly = ByteUtils.readLEInt(wkb, offset);
1108:                }
1109:
1110:                offset += 4;
1111:
1112:                ArrayList<Surface> list = new ArrayList<Surface>(numPoly);
1113:
1114:                for (int ip = 0; ip < numPoly; ip++) {
1115:                    byteorder = wkb[offset];
1116:                    offset++;
1117:
1118:                    if (byteorder == 0) {
1119:                        wkbtype = ByteUtils.readBEInt(wkb, offset);
1120:                    } else {
1121:                        wkbtype = ByteUtils.readLEInt(wkb, offset);
1122:                    }
1123:
1124:                    offset += 4;
1125:
1126:                    // is the geometry respresented by wkb a polygon?
1127:                    if (wkbtype != 3) {
1128:                        throw new GeometryException(
1129:                                "invalid byte stream for Surface " + wkbtype);
1130:                    }
1131:
1132:                    // read number of rings of the polygon
1133:                    if (byteorder == 0) {
1134:                        numRings = ByteUtils.readBEInt(wkb, offset);
1135:                    } else {
1136:                        numRings = ByteUtils.readLEInt(wkb, offset);
1137:                    }
1138:
1139:                    offset += 4;
1140:
1141:                    // read number of points of the external ring
1142:                    if (byteorder == 0) {
1143:                        numPoints = ByteUtils.readBEInt(wkb, offset);
1144:                    } else {
1145:                        numPoints = ByteUtils.readLEInt(wkb, offset);
1146:                    }
1147:
1148:                    offset += 4;
1149:
1150:                    // allocate memory for the external boundary
1151:                    externalBoundary = new Position[numPoints];
1152:
1153:                    if (byteorder == 0) {
1154:                        // read points of the external boundary from the byte[]
1155:                        for (int i = 0; i < numPoints; i++) {
1156:                            x = ByteUtils.readBEDouble(wkb, offset);
1157:                            offset += 8;
1158:                            y = ByteUtils.readBEDouble(wkb, offset);
1159:                            offset += 8;
1160:                            externalBoundary[i] = new PositionImpl(x, y);
1161:                        }
1162:                    } else {
1163:                        // read points of the external boundary from the byte[]
1164:                        for (int i = 0; i < numPoints; i++) {
1165:                            x = ByteUtils.readLEDouble(wkb, offset);
1166:                            offset += 8;
1167:                            y = ByteUtils.readLEDouble(wkb, offset);
1168:                            offset += 8;
1169:                            externalBoundary[i] = new PositionImpl(x, y);
1170:                        }
1171:                    }
1172:
1173:                    // only if numRings is larger then one there internal rings
1174:                    if (numRings > 1) {
1175:                        internalBoundaries = new Position[numRings - 1][];
1176:                    }
1177:
1178:                    if (byteorder == 0) {
1179:                        for (int j = 1; j < numRings; j++) {
1180:                            // read number of points of the j-th internal ring
1181:                            numPoints = ByteUtils.readBEInt(wkb, offset);
1182:                            offset += 4;
1183:
1184:                            // allocate memory for the j-th internal boundary
1185:                            internalBoundaries[j - 1] = new Position[numPoints];
1186:
1187:                            // read points of the external boundary from the byte[]
1188:                            for (int i = 0; i < numPoints; i++) {
1189:                                x = ByteUtils.readBEDouble(wkb, offset);
1190:                                offset += 8;
1191:                                y = ByteUtils.readBEDouble(wkb, offset);
1192:                                offset += 8;
1193:                                internalBoundaries[j - 1][i] = new PositionImpl(
1194:                                        x, y);
1195:                            }
1196:                        }
1197:                    } else {
1198:                        for (int j = 1; j < numRings; j++) {
1199:                            // read number of points of the j-th internal ring
1200:                            numPoints = ByteUtils.readLEInt(wkb, offset);
1201:                            offset += 4;
1202:
1203:                            // allocate memory for the j-th internal boundary
1204:                            internalBoundaries[j - 1] = new Position[numPoints];
1205:
1206:                            // read points of the external boundary from the byte[]
1207:                            for (int i = 0; i < numPoints; i++) {
1208:                                x = ByteUtils.readLEDouble(wkb, offset);
1209:                                offset += 8;
1210:                                y = ByteUtils.readLEDouble(wkb, offset);
1211:                                offset += 8;
1212:                                internalBoundaries[j - 1][i] = new PositionImpl(
1213:                                        x, y);
1214:                            }
1215:                        }
1216:                    }
1217:
1218:                    SurfacePatch patch = createSurfacePatch(externalBoundary,
1219:                            internalBoundaries, si, crs);
1220:
1221:                    list.add(createSurface(patch));
1222:                }
1223:
1224:                MultiSurface multisurface = new MultiSurfaceImpl(crs);
1225:
1226:                for (int i = 0; i < list.size(); i++) {
1227:                    multisurface.addSurface(list.get(i));
1228:                }
1229:
1230:                return multisurface;
1231:            }
1232:
1233:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.