Revision 42377 trunk/org.gvsig.desktop/org.gvsig.desktop.compat.cdc/org.gvsig.fmap.geometry/org.gvsig.fmap.geometry.jts/src/main/java/org/gvsig/fmap/geom/jts/operation/fromwkb/WKBParser3.java

View differences:

WKBParser3.java
3 3
 *
4 4
 * Copyright (C) 2007-2013 gvSIG Association.
5 5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 3
9
 * of the License, or (at your option) any later version.
6
 * This program is free software; you can redistribute it and/or modify it under
7
 * the terms of the GNU General Public License as published by the Free Software
8
 * Foundation; either version 3 of the License, or (at your option) any later
9
 * version.
10 10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
11
 * This program is distributed in the hope that it will be useful, but WITHOUT
12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
13
 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
14
 * details.
15 15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
16
 * You should have received a copy of the GNU General Public License along with
17
 * this program; if not, write to the Free Software Foundation, Inc., 51
18
 * Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20 19
 *
21
 * For any additional information, do not hesitate to contact us
22
 * at info AT gvsig.com, or visit our website www.gvsig.com.
20
 * For any additional information, do not hesitate to contact us at info AT
21
 * gvsig.com, or visit our website www.gvsig.com.
23 22
 */
24 23
package org.gvsig.fmap.geom.jts.operation.fromwkb;
25 24

  
......
29 28
 *
30 29
 * (C) 2005 Markus Schaber, schabios@logi-track.com
31 30
 */
32

  
33 31
import java.nio.ByteBuffer;
34 32
import java.nio.ByteOrder;
35 33

  
......
58 56
/**
59 57
 * Parse binary representation of geometries. Currently, only text rep (hexed)
60 58
 * implementation is tested.
61
 * 
59
 *
62 60
 * It should be easy to add char[] and CharSequence ByteGetter instances,
63 61
 * although the latter one is not compatible with older jdks.
64
 * 
62
 *
65 63
 * I did not implement real unsigned 32-bit integers or emulate them with long,
66 64
 * as both java Arrays and Strings currently can have only 2^31-1 elements
67 65
 * (bytes), so we cannot even get or build Geometries with more than approx.
68 66
 * 2^28 coordinates (8 bytes each).
69
 * 
67
 *
70 68
 * @author markus.schaber@logi-track.com
71
 * 
69
 *
72 70
 */
73

  
74 71
public class WKBParser3 {
75 72

  
76
	private boolean gHaveM, gHaveZ, gHaveS; // M, Z y SRID
73
    private boolean gHaveM, gHaveZ, gHaveS; // M, Z y SRID
77 74

  
78
	private static final Logger LOG = LoggerFactory.getLogger(WKBParser2.class);
79
	private GeometryManager geomManager = GeometryLocator.getGeometryManager();
80
	private GeometryType[] pointGeometryTypes;
75
    private static final Logger LOG = LoggerFactory.getLogger(WKBParser2.class);
76
    private GeometryManager geomManager = GeometryLocator.getGeometryManager();
77
    private GeometryType[] pointGeometryTypes;
81 78

  
82
	/**
83
	 * @throws GeometryTypeNotValidException
84
	 * @throws GeometryTypeNotSupportedException
85
	 * 
86
	 */
87
	public WKBParser3() {
88
		pointGeometryTypes =
89
			new GeometryType[] {
90
				loadPointGeometryType(Geometry.SUBTYPES.GEOM2D, "2D"),
91
				loadPointGeometryType(Geometry.SUBTYPES.GEOM3D, "3D"),
92
				loadPointGeometryType(Geometry.SUBTYPES.GEOM2DM, "2DM"),
93
				loadPointGeometryType(Geometry.SUBTYPES.GEOM3DM, "3DM") };
94
	}
79
    /**
80
     * @throws GeometryTypeNotValidException
81
     * @throws GeometryTypeNotSupportedException
82
     *
83
     */
84
    public WKBParser3() {
85
        pointGeometryTypes
86
                = new GeometryType[]{
87
                    loadPointGeometryType(Geometry.SUBTYPES.GEOM2D, "2D"),
88
                    loadPointGeometryType(Geometry.SUBTYPES.GEOM3D, "3D"),
89
                    loadPointGeometryType(Geometry.SUBTYPES.GEOM2DM, "2DM"),
90
                    loadPointGeometryType(Geometry.SUBTYPES.GEOM3DM, "3DM")};
91
    }
95 92

  
96
	private GeometryType loadPointGeometryType(int subtype, String subTypeName) {
97
		try {
98
			return geomManager.getGeometryType(Geometry.TYPES.POINT, subtype);
99
		} catch (Exception e) {
100
			LOG.info("Unable to get a reference to the geometry "
101
					+ "type Point{}, to be cached", subTypeName);
102
			return null;
103
		}
104
	}
93
    private GeometryType loadPointGeometryType(int subtype, String subTypeName) {
94
        try {
95
            return geomManager.getGeometryType(Geometry.TYPES.POINT, subtype);
96
        } catch (Exception e) {
97
            LOG.info("Unable to get a reference to the geometry "
98
                    + "type Point{}, to be cached", subTypeName);
99
            return null;
100
        }
101
    }
105 102

  
106
	/**
107
	 * Parse a binary encoded geometry.
108
	 * 
109
	 * Is synchronized to protect offset counter. (Unfortunately, Java does not
110
	 * have neither call by reference nor multiple return values.)
111
	 * @throws CreateGeometryException 
112
	 */
113
	public synchronized Geometry parse(byte[] value) throws CreateGeometryException {
114
		// BinaryByteGetter bytes = new ByteGetter.BinaryByteGetter(value);
115
		ByteBuffer buf = ByteBuffer.wrap(value);
116
		return parseGeometry(buf);
117
	}
103
    /**
104
     * Parse a binary encoded geometry.
105
     *
106
     * Is synchronized to protect offset counter. (Unfortunately, Java does not
107
     * have neither call by reference nor multiple return values.)
108
     *
109
     * @throws CreateGeometryException
110
     */
111
    public synchronized Geometry parse(byte[] value) throws CreateGeometryException {
112
        // BinaryByteGetter bytes = new ByteGetter.BinaryByteGetter(value);
113
        ByteBuffer buf = ByteBuffer.wrap(value);
114
        return parseGeometry(buf);
115
    }
118 116

  
117
    /**
118
     * Parse a geometry starting at offset.
119
     *
120
     * @throws CreateGeometryException
121
     */
122
    protected Geometry parseGeometry(ByteBuffer data) throws CreateGeometryException {
123
        int realtype = parseTypeAndSRID(data);
119 124

  
120
	/** Parse a geometry starting at offset. 
121
	 * @throws CreateGeometryException */
122
	protected Geometry parseGeometry(ByteBuffer data) throws CreateGeometryException {
123
		int realtype = parseTypeAndSRID(data);
125
        Geometry result1 = null;
126
        switch (realtype) {
127
            case WKBConstants.wkbPoint:
128
                result1 = parsePoint(data, gHaveZ, gHaveM);
129
                break;
130
            case WKBConstants.wkbLineString:
131
                result1 = parseLineString(data, gHaveZ, gHaveM);
132
                break;
133
            case WKBConstants.wkbPolygon:
134
                result1 = parsePolygon(data, gHaveZ, gHaveM);
135
                break;
136
            case WKBConstants.wkbMultiPoint:
137
                result1 = parseMultiPoint(data);
138
                break;
139
            case WKBConstants.wkbMultiLineString:
140
                result1 = parseMultiLineString(data);
141
                return result1;
142
            case WKBConstants.wkbMultiPolygon:
143
                result1 = parseMultiPolygon(data);
144
                break;
145
            case WKBConstants.wkbGeometryCollection:
146
                result1 = parseCollection(data);
147
                break;
148
            default:
149
            //throw new IllegalArgumentException("Unknown Geometry Type!");
150
        }
124 151

  
125
		Geometry result1 = null;
126
		switch (realtype) {
127
		case WKBConstants.wkbPoint:
128
			result1 = parsePoint(data, gHaveZ, gHaveM);
129
			break;
130
		case WKBConstants.wkbLineString:
131
			result1 = parseLineString(data, gHaveZ, gHaveM);
132
			break;
133
		case WKBConstants.wkbPolygon:
134
			result1 = parsePolygon(data, gHaveZ, gHaveM);
135
			break;
136
		case WKBConstants.wkbMultiPoint:
137
			result1 = parseMultiPoint(data);
138
			break;
139
		case WKBConstants.wkbMultiLineString:
140
			result1 = parseMultiLineString(data);
141
			return result1;
142
		case WKBConstants.wkbMultiPolygon:
143
			result1 = parseMultiPolygon(data);
144
			break;
145
		case WKBConstants.wkbGeometryCollection:
146
			result1 = parseCollection(data);
147
			break;
148
		default:
149
			//throw new IllegalArgumentException("Unknown Geometry Type!");
150
		}
152
        return result1;
153
    }
151 154

  
152
		return result1;
153
	}
155
    protected int parseTypeAndSRID(ByteBuffer data) {
156
        byte endian = data.get(); // skip and test endian flag
157
        if (endian == 1) {
158
            data.order(ByteOrder.LITTLE_ENDIAN);
159
        }
160
        int typeword = data.getInt();
154 161

  
155
	protected int parseTypeAndSRID(ByteBuffer data) {
156
		byte endian = data.get(); // skip and test endian flag
157
		if (endian == 1) {
158
			data.order(ByteOrder.LITTLE_ENDIAN);
159
		}
160
		int typeword = data.getInt();
162
        int realtype = typeword & 0x1FFFFFFF; // cut off high flag bits
161 163

  
162
		int realtype = typeword & 0x1FFFFFFF; // cut off high flag bits
164
        gHaveZ = (typeword & 0x80000000) != 0;
165
        gHaveM = (typeword & 0x40000000) != 0;
166
        gHaveS = (typeword & 0x20000000) != 0;
163 167

  
164
		gHaveZ = (typeword & 0x80000000) != 0;
165
		gHaveM = (typeword & 0x40000000) != 0;
166
		gHaveS = (typeword & 0x20000000) != 0;
167
		
168
		// not used
169
		int srid = -1;
168
        // not used
169
        int srid = -1;
170 170

  
171
		if (gHaveS) {
172
			srid = data.getInt();
173
		}
171
        if (gHaveS) {
172
            srid = data.getInt();
173
        }
174 174

  
175
		return realtype;
175
        return realtype;
176 176

  
177
	}
177
    }
178 178

  
179
	private Point parsePoint(ByteBuffer data, boolean haveZ, boolean haveM) 
180
	throws CreateGeometryException {
181
		double x = data.getDouble();
182
		double y = data.getDouble();
183
		Point point;
179
    private Point parsePoint(ByteBuffer data, boolean haveZ, boolean haveM)
180
            throws CreateGeometryException {
181
        double x = data.getDouble();
182
        double y = data.getDouble();
183
        Point point;
184 184

  
185
		int subtype = getSubType(haveZ, haveM);
185
        int subtype = getSubType(haveZ, haveM);
186 186

  
187
		// If we have a cached GeometryType use it, otherwise call the manager
188
                if( pointGeometryTypes[subtype] == null ) {
189
                    point = (Point) geomManager.create(Geometry.TYPES.POINT, subtype);
190
                } else {
191
                    point = (Point) pointGeometryTypes[subtype].create();
192
                }
193
                point.setX(x);
194
		point.setY(y);
187
        // If we have a cached GeometryType use it, otherwise call the manager
188
        if (pointGeometryTypes[subtype] == null) {
189
            point = (Point) geomManager.create(Geometry.TYPES.POINT, subtype);
190
        } else {
191
            point = (Point) pointGeometryTypes[subtype].create();
192
        }
193
        point.setX(x);
194
        point.setY(y);
195 195

  
196
		// Other dimensions
197
		if (haveZ) {
198
			point.setCoordinateAt(Geometry.DIMENSIONS.Z, data.getDouble());
199
			if (haveM) {
200
				/*point.setCoordinateAt(Geometry.DIMENSIONS.Z + 1,
201
						data.getDouble());*/
202
				data.getDouble();
203
			}
204
		} else {
205
			if (haveM) {
206
				/*point.setCoordinateAt(Geometry.DIMENSIONS.Y + 1,
207
						data.getDouble());*/
208
				data.getDouble();
209
			}
210
		}
196
        // Other dimensions
197
        if (haveZ) {
198
            point.setCoordinateAt(Geometry.DIMENSIONS.Z, data.getDouble());
199
            if (haveM) {
200
                /*point.setCoordinateAt(Geometry.DIMENSIONS.Z + 1,
201
                 data.getDouble());*/
202
                data.getDouble();
203
            }
204
        } else {
205
            if (haveM) {
206
                /*point.setCoordinateAt(Geometry.DIMENSIONS.Y + 1,
207
                 data.getDouble());*/
208
                data.getDouble();
209
            }
210
        }
211 211

  
212
		return point;
213
	}
212
        return point;
213
    }
214 214

  
215
	/**
216
	 * @param haveZ
217
	 * @param haveM
218
	 * @return
219
	 */
220
	private int getSubType(boolean haveZ, boolean haveM) {
221
		/*int subtype =
222
			haveZ ? (haveM ? Geometry.SUBTYPES.GEOM3DM
223
					: Geometry.SUBTYPES.GEOM3D) : (haveM
224
							? Geometry.SUBTYPES.GEOM2DM : Geometry.SUBTYPES.GEOM2D);*/
225
		//TODO: No hay soporte para M
226
		int subtype = haveZ ? Geometry.SUBTYPES.GEOM3D : Geometry.SUBTYPES.GEOM2D;
227
		return subtype;
228
	}
215
    /**
216
     * @param haveZ
217
     * @param haveM
218
     * @return
219
     */
220
    private int getSubType(boolean haveZ, boolean haveM) {
221
        /*int subtype =
222
         haveZ ? (haveM ? Geometry.SUBTYPES.GEOM3DM
223
         : Geometry.SUBTYPES.GEOM3D) : (haveM
224
         ? Geometry.SUBTYPES.GEOM2DM : Geometry.SUBTYPES.GEOM2D);*/
225
        //TODO: No hay soporte para M
226
        int subtype = haveZ ? Geometry.SUBTYPES.GEOM3D : Geometry.SUBTYPES.GEOM2D;
227
        return subtype;
228
    }
229 229

  
230
	private Curve parseMultiLineString(ByteBuffer data) throws CreateGeometryException {
231
		Curve curve = (Curve) geomManager.create(TYPES.CURVE, getSubType(gHaveZ, gHaveM));
232
		fillOrientablePrimitive(data, curve);
233
		return curve;
234
	}
230
    private Curve parseMultiLineString(ByteBuffer data) throws CreateGeometryException {
231
        Curve curve = (Curve) geomManager.create(TYPES.CURVE, getSubType(gHaveZ, gHaveM));
232
        fillOrientablePrimitive(data, curve);
233
        return curve;
234
    }
235 235

  
236
	/**
237
	 * @param data
238
	 * @return
239
	 * @throws CreateGeometryException
240
	 */
241
	private void fillOrientablePrimitive(ByteBuffer data, OrientablePrimitive orientablePrimitive)
242
	throws CreateGeometryException {
243
		int count = data.getInt();
236
    /**
237
     * @param data
238
     * @return
239
     * @throws CreateGeometryException
240
     */
241
    private void fillOrientablePrimitive(ByteBuffer data, OrientablePrimitive orientablePrimitive)
242
            throws CreateGeometryException {
243
        int count = data.getInt();
244 244

  
245
		for (int i=0; i < count; i++)
246
		{
247
			parseTypeAndSRID(data);
248
			Point[] points = parsePointArray(data, gHaveZ, gHaveM);
245
        for (int i = 0; i < count; i++) {
246
            parseTypeAndSRID(data);
247
            Point[] points = parsePointArray(data, gHaveZ, gHaveM);
249 248

  
250
			orientablePrimitive.addMoveToVertex(points[0]);
251
			for (int j = 1; j < points.length; j++) {
252
				orientablePrimitive.addVertex(points[j]);
253
			}           
254
		}		
255
	}
249
            orientablePrimitive.addMoveToVertex(points[0]);
250
            for (int j = 1; j < points.length; j++) {
251
                orientablePrimitive.addVertex(points[j]);
252
            }
253
        }
254
    }
256 255

  
257
	private MultiSurface parseMultiPolygon(ByteBuffer data)
258
	throws CreateGeometryException {
259
		int count = data.getInt();
260
		
261
		int subType = getSubType(gHaveZ, gHaveM);        
262
		MultiSurface multiSurface = (MultiSurface)geomManager.create(TYPES.MULTISURFACE, subType);        
256
    private MultiSurface parseMultiPolygon(ByteBuffer data)
257
            throws CreateGeometryException {
258
        int count = data.getInt();
263 259

  
264
		Point point;
265
		for (int i = 0; i < count; i++) {
266
			Surface surface = (Surface)geomManager.create(TYPES.SURFACE, subType); 
267
			parseTypeAndSRID(data);
268
			int countRings = data.getInt();            
269
			for (int j = 0; j < countRings; j++) {
270
				double[][] points = parsePointsAsDoubleArray(data, gHaveZ, gHaveM);
260
        int subType = getSubType(gHaveZ, gHaveM);
261
        MultiSurface multiSurface = (MultiSurface) geomManager.create(TYPES.MULTISURFACE, subType);
271 262

  
272
				//Add the initial point
273
				point = geomManager.createPoint(points[0][0], points[0][1], subType);
274
				if(gHaveZ)
275
					point.setCoordinateAt(Geometry.DIMENSIONS.Z, points[0][2]);
276
				surface.addMoveToVertex(point);
277
				
263
        Point point;
264
        for (int i = 0; i < count; i++) {
265
            Surface surface = (Surface) geomManager.create(TYPES.SURFACE, subType);
266
            parseTypeAndSRID(data);
267
            int countRings = data.getInt();
268
            for (int j = 0; j < countRings; j++) {
269
                double[][] points = parsePointsAsDoubleArray(data, gHaveZ, gHaveM);
278 270

  
279
				//Add the other points
280
				int lastPoint = points.length - 1;
281
				for (int k = 1; k < lastPoint; k++){                    
282
					point = geomManager.createPoint(points[k][0], points[k][1], subType);
283
					if(gHaveZ)
284
						point.setCoordinateAt(Geometry.DIMENSIONS.Z, points[0][2]);
285
					/*for (int l = 2; l < points[k].length; i++){
286
						point.setCoordinateAt(l, points[k][l]);
287
					}*/
288
					surface.addVertex(point);
289
				}   
290
				surface.closePrimitive();
291
			}
292
			multiSurface.addSurface(surface);
293
		}
294
		return multiSurface;
295
	}
271
                //Add the initial point
272
                point = geomManager.createPoint(points[0][0], points[0][1], subType);
273
                if (gHaveZ) {
274
                    point.setCoordinateAt(Geometry.DIMENSIONS.Z, points[0][2]);
275
                }
276
                surface.addMoveToVertex(point);
296 277

  
297
	private double[][] parsePointsAsDoubleArray(ByteBuffer data, boolean haveZ,
298
			boolean haveM) throws CreateGeometryException {
299
		int count = data.getInt();
300
		double points[][] = null;
301
		int subtype = getSubType(haveZ, haveM);
278
                //Add the other points
279
                int lastPoint = points.length - 1;
280
                for (int k = 1; k < lastPoint; k++) {
281
                    point = geomManager.createPoint(points[k][0], points[k][1], subType);
282
                    if (gHaveZ) {
283
                        point.setCoordinateAt(Geometry.DIMENSIONS.Z, points[0][2]);
284
                    }
285
                    /*for (int l = 2; l < points[k].length; i++){
286
                     point.setCoordinateAt(l, points[k][l]);
287
                     }*/
288
                    surface.addVertex(point);
289
                }
290
                surface.closePrimitive();
291
            }
292
            multiSurface.addSurface(surface);
293
        }
294
        return multiSurface;
295
    }
302 296

  
303
		switch (subtype) {
304
		case Geometry.SUBTYPES.GEOM2D:
305
			points = new double[count][2];
306
			break;
307
		case Geometry.SUBTYPES.GEOM3D:
308
		case Geometry.SUBTYPES.GEOM2DM:
309
			points = new double[count][3];
310
			break;
311
		case Geometry.SUBTYPES.GEOM3DM:
312
			points = new double[count][4];
313
			break;
314
		default:
315
			break;
316
		}
297
    private double[][] parsePointsAsDoubleArray(ByteBuffer data, boolean haveZ,
298
            boolean haveM) throws CreateGeometryException {
299
        int count = data.getInt();
300
        double points[][] = null;
301
        int subtype = getSubType(haveZ, haveM);
317 302

  
318
		for (int i = 0; i < count; i++) {
319
			points[i][0] = data.getDouble(); // x
320
			points[i][1] = data.getDouble(); // y
321
			switch (subtype) {
322
			case Geometry.SUBTYPES.GEOM3D:
323
			case Geometry.SUBTYPES.GEOM2DM:
324
				points[i][2] = data.getDouble(); // z or m
325
				break;
326
			case Geometry.SUBTYPES.GEOM3DM:
327
				points[i][2] = data.getDouble(); // z
328
				points[i][3] = data.getDouble(); // m
329
				break;
330
			default:
331
				break;
332
			}
333
			//TODO: Remove when M be supported
334
			if(haveZ && haveM)
335
				data.getDouble();
336
		}
337
		return points;
338
	}
303
        switch (subtype) {
304
            case Geometry.SUBTYPES.GEOM2D:
305
                points = new double[count][2];
306
                break;
307
            case Geometry.SUBTYPES.GEOM3D:
308
            case Geometry.SUBTYPES.GEOM2DM:
309
                points = new double[count][3];
310
                break;
311
            case Geometry.SUBTYPES.GEOM3DM:
312
                points = new double[count][4];
313
                break;
314
            default:
315
                break;
316
        }
339 317

  
340
	private MultiPrimitive parseCollection(ByteBuffer data) throws CreateGeometryException {
341
		int count = data.getInt();
342
		Geometry[] geoms = new Geometry[count];
343
		parseGeometryArray(data, geoms);
344
		MultiPrimitive multiPrimitive = (MultiPrimitive) geomManager.create(TYPES.AGGREGATE, SUBTYPES.GEOM2D);
345
		for (int i = 0 ; i < geoms.length ; i++){
346
			multiPrimitive.addPrimitive((Primitive) geoms[i]);
347
		}
348
		return multiPrimitive;
349
	}	
318
        for (int i = 0; i < count; i++) {
319
            points[i][0] = data.getDouble(); // x
320
            points[i][1] = data.getDouble(); // y
321
            switch (subtype) {
322
                case Geometry.SUBTYPES.GEOM3D:
323
                case Geometry.SUBTYPES.GEOM2DM:
324
                    points[i][2] = data.getDouble(); // z or m
325
                    break;
326
                case Geometry.SUBTYPES.GEOM3DM:
327
                    points[i][2] = data.getDouble(); // z
328
                    points[i][3] = data.getDouble(); // m
329
                    break;
330
                default:
331
                    break;
332
            }
333
            //TODO: Remove when M be supported
334
            if (haveZ && haveM) {
335
                data.getDouble();
336
            }
337
        }
338
        return points;
339
    }
350 340

  
351
	/** Parse an Array of "full" Geometries 
352
	 * @throws CreateGeometryException */
353
	private void parseGeometryArray(ByteBuffer data, Geometry[] container) throws CreateGeometryException {
354
		for (int i = 0; i < container.length; i++) {
355
			container[i] = parseGeometry(data);
356
		}
357
	}
341
    private MultiPrimitive parseCollection(ByteBuffer data) throws CreateGeometryException {
342
        int count = data.getInt();
343
        Geometry[] geoms = new Geometry[count];
344
        parseGeometryArray(data, geoms);
345
        MultiPrimitive multiPrimitive = (MultiPrimitive) geomManager.create(TYPES.AGGREGATE, SUBTYPES.GEOM2D);
346
        for (int i = 0; i < geoms.length; i++) {
347
            multiPrimitive.addPrimitive((Primitive) geoms[i]);
348
        }
349
        return multiPrimitive;
350
    }
358 351

  
359
	private Curve parseLineString(ByteBuffer data, boolean haveZ, boolean haveM) throws CreateGeometryException {
360
		Point[] points = parsePointArray(data, haveZ, haveM);
361
		Curve curve = (Curve) geomManager.create(TYPES.CURVE, getSubType(haveZ, haveM));    
362
		curve.addMoveToVertex(points[0]);
363
		for (int i = 1; i< points.length; i++) {
364
			curve.addVertex(points[i]);
365
		}
366
		return curve;
367
	}
352
    /**
353
     * Parse an Array of "full" Geometries
354
     *
355
     * @throws CreateGeometryException
356
     */
357
    private void parseGeometryArray(ByteBuffer data, Geometry[] container) throws CreateGeometryException {
358
        for (int i = 0; i < container.length; i++) {
359
            container[i] = parseGeometry(data);
360
        }
361
    }
368 362

  
369
	/**
370
	 * Parse an Array of "slim" Points (without endianness and type, part of
371
	 * LinearRing and Linestring, but not MultiPoint!
372
	 * 
373
	 * @param haveZ
374
	 * @param haveM
375
	 * @throws CreateGeometryException
376
	 */
377
	private Point[] parsePointArray(ByteBuffer data, boolean haveZ, boolean haveM) 
378
	throws CreateGeometryException {
379
		int count = data.getInt();
380
		Point[] result = new Point[count];
381
		for (int i = 0; i < count; i++) {
382
			result[i] = parsePoint(data, haveZ, haveM);
383
		}
384
		return result;
385
	}
363
    private Curve parseLineString(ByteBuffer data, boolean haveZ, boolean haveM) throws CreateGeometryException {
364
        Point[] points = parsePointArray(data, haveZ, haveM);
365
        Curve curve = (Curve) geomManager.create(TYPES.CURVE, getSubType(haveZ, haveM));
366
        curve.addMoveToVertex(points[0]);
367
        for (int i = 1; i < points.length; i++) {
368
            curve.addVertex(points[i]);
369
        }
370
        return curve;
371
    }
386 372

  
373
    /**
374
     * Parse an Array of "slim" Points (without endianness and type, part of
375
     * LinearRing and Linestring, but not MultiPoint!
376
     *
377
     * @param haveZ
378
     * @param haveM
379
     * @throws CreateGeometryException
380
     */
381
    private Point[] parsePointArray(ByteBuffer data, boolean haveZ, boolean haveM)
382
            throws CreateGeometryException {
383
        int count = data.getInt();
384
        Point[] result = new Point[count];
385
        for (int i = 0; i < count; i++) {
386
            result[i] = parsePoint(data, haveZ, haveM);
387
        }
388
        return result;
389
    }
387 390

  
388
	private Surface parsePolygon(ByteBuffer data, boolean haveZ, boolean haveM) throws CreateGeometryException {
389
		int count = data.getInt();
390
		int subType = getSubType(haveZ, haveM);        
391
    private Surface parsePolygon(ByteBuffer data, boolean haveZ, boolean haveM) throws CreateGeometryException {
392
        int count = data.getInt();
393
        int subType = getSubType(haveZ, haveM);
391 394

  
392
		Surface surface = (Surface) geomManager.create(TYPES.SURFACE, subType);
395
        Surface surface = (Surface) geomManager.create(TYPES.SURFACE, subType);
393 396

  
394
		for (int i = 0; i < count; i++) {
395
			fillLinearRing(data, surface, haveZ, haveM); 
396
		}
397
        for (int i = 0; i < count; i++) {
398
            fillLinearRing(data, surface, haveZ, haveM);
399
        }
397 400

  
398
		surface.closePrimitive();	        
401
        surface.closePrimitive();
399 402

  
400
		return surface;
401
	}
403
        return surface;
404
    }
402 405

  
403
	private void fillLinearRing(ByteBuffer data, OrientablePrimitive orientablePrimitive, boolean haveZ, boolean haveM) throws CreateGeometryException {
404
		Point[] points = parsePointArray(data, haveZ, haveM);
406
    private void fillLinearRing(ByteBuffer data, OrientablePrimitive orientablePrimitive, boolean haveZ, boolean haveM) throws CreateGeometryException {
407
        Point[] points = parsePointArray(data, haveZ, haveM);
405 408

  
406
		orientablePrimitive.addMoveToVertex(points[0]);
407
		int lastPoint = points.length - 1;
408
		for (int i = 1; i< lastPoint; i++) {
409
			orientablePrimitive.addVertex(points[i]);
410
		}        
411
	}
409
        orientablePrimitive.addMoveToVertex(points[0]);
410
        int lastPoint = points.length - 1;
411
        for (int i = 1; i < lastPoint; i++) {
412
            orientablePrimitive.addVertex(points[i]);
413
        }
414
    }
412 415

  
413
	private MultiPoint parseMultiPoint(ByteBuffer data) throws CreateGeometryException {
414
		MultiPoint multipoint = (MultiPoint) geomManager.create(TYPES.MULTIPOINT, SUBTYPES.GEOM2D);
415
                int points = data.getInt();
416
                multipoint.ensureCapacity(points);
417
                for (int i=0; i < points; i++) {
418
			parseTypeAndSRID(data);
419
			multipoint.addPrimitive(parsePoint(data, gHaveZ, gHaveM));
420
		}
421
		return multipoint;
422
	}
416
    private MultiPoint parseMultiPoint(ByteBuffer data) throws CreateGeometryException {
417
        MultiPoint multipoint = (MultiPoint) geomManager.create(TYPES.MULTIPOINT, SUBTYPES.GEOM2D);
418
        int points = data.getInt();
419
        multipoint.ensureCapacity(points);
420
        for (int i = 0; i < points; i++) {
421
            parseTypeAndSRID(data);
422
            multipoint.addPrimitive(parsePoint(data, gHaveZ, gHaveM));
423
        }
424
        return multipoint;
425
    }
423 426

  
424 427
}

Also available in: Unified diff