Statistics
| Revision:

svn-gvsig-desktop / branches / v2_0_0_prep / libraries / libDwg / src / org / gvsig / dwg / lib / objects / DwgPFacePolyline.java @ 29001

History | View | Annotate | Download (12.9 KB)

1
/*
2
 * Created on 03-feb-2007
3
 *
4
 * gvSIG. Sistema de Informaci�n Geogr�fica de la Generalitat Valenciana
5
 *
6
 * Copyright (C) 2004 IVER T.I. and Generalitat Valenciana.
7
 *
8
 * This program is free software; you can redistribute it and/or
9
 * modify it under the terms of the GNU General Public License
10
 * as published by the Free Software Foundation; either version 2
11
 * of the License, or (at your option) any later version.
12
 *
13
 * This program is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
 * GNU General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU General Public License
19
 * along with this program; if not, write to the Free Software
20
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307,USA.
21
 *
22
 * For more information, contact:
23
 *
24
 *  Generalitat Valenciana
25
 *   Conselleria d'Infraestructures i Transport
26
 *   Av. Blasco Ib��ez, 50
27
 *   46010 VALENCIA
28
 *   SPAIN
29
 *
30
 *      +34 963862235
31
 *   gvsig@gva.es
32
 *      www.gvsig.gva.es
33
 *
34
 *    or
35
 *
36
 *   IVER T.I. S.A
37
 *   Salamanca 50
38
 *   46005 Valencia
39
 *   Spain
40
 *
41
 *   +34 963163400
42
 *   dac@iver.es
43
 */
44
/* CVS MESSAGES:
45
 *
46
 * $Id: DwgPFacePolyline.java 29001 2009-05-26 15:32:46Z jmvivo $
47
 * $Log$
48
 * Revision 1.3.2.1  2007-03-21 19:49:16  azabala
49
 * implementation of dwg 12, 13, 14.
50
 *
51
 * Revision 1.3  2007/03/20 19:57:08  azabala
52
 * source code cleaning
53
 *
54
 * Revision 1.2  2007/03/06 19:39:38  azabala
55
 * Changes to adapt dwg 12 to general architecture
56
 *
57
 * Revision 1.1  2007/03/01 19:58:53  azabala
58
 * refactor of pface and mesh names
59
 *
60
 * Revision 1.2  2007/02/07 12:44:27  fdiaz
61
 * A�adido o modificado el metodo clone para que el DwgObject se encargue de las propiedades comunes a todos los objetos.
62
 * A�adido el metodo fill.
63
 *
64
 * Revision 1.1  2007/02/05 07:03:22  azabala
65
 * *** empty log message ***
66
 *
67
 *
68
 */
69
package org.gvsig.dwg.lib.objects;
70

    
71
import java.awt.geom.Point2D;
72
import java.util.ArrayList;
73
import java.util.List;
74
import java.util.Map;
75

    
76
import org.gvsig.dwg.lib.DwgFile;
77
import org.gvsig.dwg.lib.DwgHandleReference;
78
import org.gvsig.dwg.lib.DwgObject;
79
import org.gvsig.dwg.lib.IDwg2FMap;
80
import org.gvsig.dwg.lib.IDwgBlockMember;
81
import org.gvsig.dwg.lib.IDwgPolyline;
82
import org.gvsig.dwg.lib.IDwgVertex;
83
import org.gvsig.dwg.lib.util.FMapUtil;
84
import org.gvsig.fmap.geom.Geometry;
85
import org.gvsig.fmap.geom.GeometryLocator;
86
import org.gvsig.fmap.geom.GeometryManager;
87
import org.gvsig.fmap.geom.aggregate.MultiSurface;
88
import org.gvsig.fmap.geom.exception.CreateGeometryException;
89
import org.slf4j.Logger;
90
import org.slf4j.LoggerFactory;
91

    
92

    
93
/**
94
 * This DWG entity is a "Polyface Mesh".
95
 *
96
 */
97

    
98
/*
99
 * azabala DXF 12 spec says: "If the Vertex defines a face of the mesh, its
100
 * Vertex flags (70) group has the 128 bit set but not the 64 bit. The 10, 20,
101
 * and 30 (location) groups of the face entity are irrelevant and are always
102
 * written as zero in a DXF file.
103
 *
104
 * The vertex indexes that define the mesh are given by 71, 72, 73, and 74
105
 * groups, the values of which are integers specifying one of the previously
106
 * defined vertices by index.
107
 *
108
 * If the index is negative, the edge that begins with that vertex is invisible.
109
 *
110
 * The first zero vertex marks the end of the vertices of the face.
111
 *
112
 * Since the 71 through 74 groups are optional fields with default values of
113
 * zero, they are present in DXF only if nonzero."
114
 *
115
 * But DWG 12 spec doesnt say anything about 71,72,73 and 74 fields for VERTEX.
116
 */
117
public class DwgPFacePolyline extends DwgObject
118
        implements IDwgPolyline, IDwg2FMap, IDwgBlockMember{
119

    
120
        private static Logger logger = LoggerFactory.getLogger(DwgPFacePolyline.class.getName());
121

    
122
        public static final int NUM_VERTEX_OF_FACE = 4;
123

    
124

    
125
        /**
126
         * number of vertices in the mesh (as it is readed from the dwg file... very
127
         * often is wrong)
128
         */
129
        private int vertexCount;
130
        /**
131
         * number of faces of the mesh (as it is readed from the dwg file... very
132
         * often is wrong)
133
         */
134
        private int faceCount;
135

    
136

    
137
        private DwgHandleReference firstVertexHandle;
138
        private DwgHandleReference lastVertexHandle;
139
        private DwgHandleReference seqendHandle;
140

    
141
        /**
142
         * Collection of all the vertices of the polyface mesh
143
         */
144
        private List vertices;
145
        /**
146
         * Collection of all the faces of the polyface mesh, whose vertices are in
147
         * vertices List.
148
         */
149
        private List faces;
150

    
151
        private ArrayList ownedObjectsHandles; //For R2004+
152

    
153

    
154
        /**
155
         * Constructor
156
         */
157
        public DwgPFacePolyline(int index) {
158
                super(index);
159
                vertices = new ArrayList();
160
                faces = new ArrayList();
161
                ownedObjectsHandles = new ArrayList();
162
        }
163

    
164
        public void setVertexCount(int vertexCount) {
165
                this.vertexCount = vertexCount;
166
        }
167

    
168
        public void setFaceCount(int faceCount) {
169
                this.faceCount = faceCount;
170
        }
171

    
172
        public void setFirstVertexHandle(DwgHandleReference handle) {
173
                this.firstVertexHandle = handle;
174
        }
175

    
176
        public void setLastVertexHandle(DwgHandleReference handle) {
177
                this.lastVertexHandle = handle;
178
        }
179

    
180
        public void setSeqendHandle(DwgHandleReference handle) {
181
                this.seqendHandle = handle;
182
        }
183

    
184
        public int getFaceCount() {
185
                return faceCount;
186
        }
187

    
188
        public DwgHandleReference getFirstVertexHandle() {
189
                return firstVertexHandle;
190
        }
191

    
192
        public DwgHandleReference getLastVertexHandle() {
193
                return lastVertexHandle;
194
        }
195

    
196
        public DwgHandleReference getSeqendHandle() {
197
                return seqendHandle;
198
        }
199

    
200
        public int getVertexCount() {
201
                return vertexCount;
202
        }
203

    
204
        public Object clone(){
205
                DwgPFacePolyline obj = new DwgPFacePolyline(index);
206
                this.fill(obj);
207
                return obj;
208
        }
209

    
210
        protected void fill(DwgObject obj){
211
                super.fill(obj);
212
                DwgPFacePolyline myObj = (DwgPFacePolyline)obj;
213
                myObj.setFaceCount(faceCount);
214
                myObj.setFirstVertexHandle(firstVertexHandle);
215
                myObj.setLastVertexHandle(lastVertexHandle);
216
                myObj.setSeqendHandle(seqendHandle);
217
                myObj.setVertexCount(vertexCount);
218
                myObj.setVertices(this.vertices);
219
                myObj.setFaces(this.faces);
220

    
221
        }
222

    
223
        public void setFaces(List faces) {
224
                this.faces = faces;
225
        }
226

    
227
        public List getFaces(){
228
                return this.faces;
229
        }
230

    
231
        public List getVertices() {
232
                return vertices;
233
        }
234

    
235
        public void setVertices(List vertices) {
236
                this.vertices = vertices;
237
        }
238

    
239
        /**
240
         * @return Returns the owned objects handles.
241
         */
242
        public ArrayList getOwnedObjectsHandles() {
243
                return ownedObjectsHandles;
244
        }
245
        /**
246
         * @param objects The owned objects handles to set.
247
         */
248
        public void setOwnedObjectsHandles(ArrayList handles) {
249
                this.ownedObjectsHandles = handles;
250
        }
251
        /**
252
         * Add a handle to the ownedBbjectsHandle vector
253
         *
254
         * @param handle handle
255
         */
256
        public void addOwnedObjectHandle(DwgHandleReference handle) {
257
                this.ownedObjectsHandles.add(handle);
258
        }
259

    
260
        public void calculateGisModel(DwgFile dwgFile) {
261
        // In DWG 13, 14 and 2000 version, a Polyface mesh has
262
    // handles references to its vertices.
263
        // In DWG 12 vertices are after the entity
264
         if(firstVertexHandle != null && lastVertexHandle != null){
265
                         DwgObject first = dwgFile.getDwgObjectFromHandle(firstVertexHandle.getOffset());
266
                        DwgObject last = dwgFile.getDwgObjectFromHandle(lastVertexHandle.getOffset());
267
                        if(first == null || last == null){
268
                                logger.warn("DwgPFacePolyline con vertices inicial o final a null");
269
                                return;
270
                        }
271

    
272
                        if(!(first instanceof IDwgVertex)){
273
                                logger.warn("El primer vertice de PFacePolyline es "+
274
                                                                first.getClass().getName());
275
                                return;
276
                        }
277

    
278
                        if(!(last instanceof IDwgVertex)){
279
                                logger.warn("El ultimo vertice de PFacePolyline es "+
280
                                                last.getClass().getName());
281
                                return;
282
                        }
283

    
284
                         int firstObjIdx = dwgFile.getIndexOf(first);
285
                         int lastObjIdx =  dwgFile.getIndexOf(last);
286
                         if(firstObjIdx == -1 || lastObjIdx == -1){
287
                                 logger.warn("Calculate GIS Model: Problemas en "+
288
                                                 "la localizacion de vertices: primero ="
289
                                                         +firstObjIdx+
290
                                                         ",Ultimo ="+lastObjIdx);
291
                                 return;
292
                         }
293
                         for(int i = firstObjIdx; i <= lastObjIdx; i++){
294
                                 DwgObject obj = dwgFile.getDwgObject(i);
295
                                 if(obj instanceof IDwgVertex){
296
                                         this.addVertex((IDwgVertex)obj);
297
                                 }else if(obj instanceof DwgSeqend){
298
                                         // TODO SEE IF BREAK THE ITERATION
299
                                         break;
300
                                 }else{
301
                                         logger.warn("Encontrado "+obj.getClass().getName()+" en la lista de vertices de Polyline3D");
302
                                 }
303
                         }// for
304

    
305
                } else {
306
                        logger.warn("Encontrada polilínea sin puntos ...");
307
                        // TODO: No se debe mandar nunca una polil�nea sin puntos, si
308
                        // esto
309
                        // ocurre es porque existe un error que hay que corregir ...
310
                }
311

    
312
        }
313

    
314

    
315
        public Geometry toFMapGeometry(boolean is3DFile) throws CreateGeometryException {
316
                GeometryManager gMan = GeometryLocator.getGeometryManager();
317

    
318
                int subType = getGeometrySubType(is3DFile);
319
                MultiSurface solution = (MultiSurface) gMan.create(getGeometryType(),
320
                                subType);
321
                if(vertices != null && faces != null){
322
                        if(vertices.size() == 0 || faces.size() == 0){
323
                                return gMan.createNullGeometry(subType);
324
                        }
325
                        int numFaces = faces.size();
326
                        for(int i = 0; i < numFaces; i++){
327
                                DwgVertexPFaceFace face = (DwgVertexPFaceFace) faces.get(i);
328
                                int[] verticesId = face.getVerticesidx();
329
                                ArrayList pts = new ArrayList();
330
                                boolean lastWasInvisible = true;
331
                                for(int j = 0; j < NUM_VERTEX_OF_FACE; j++){
332
                                        if(verticesId[j] > 0){
333
                            if(lastWasInvisible){
334
                                pts.clear();
335
                                lastWasInvisible = false;
336
                            }
337
                            // the index is 1-based
338
                            try{
339
                            pts.add(vertices.get(verticesId[j] -1));
340
                            }catch(Throwable t){
341
                                    t.printStackTrace();
342
                            }
343

    
344
                        } else if(verticesId[j] < 0 && !lastWasInvisible){
345
                            lastWasInvisible = true;
346
                            pts.add(vertices.get( (verticesId[j] * -1) -1));
347
                        }
348
                                }// for j
349

    
350
                                solution.addSurface(FMapUtil.ptsToPolygon(pts, subType));
351

    
352

    
353
// if(!lastWasInvisible){
354
// if(vertex[nrV] < 0){
355
// line.addPoint(knot[-vertex[nrV] - 1]);
356
// } else{
357
// line.addPoint(knot[vertex[nrV] - 1]);
358
// }
359
// set.addDrawable(line);
360
// }
361

    
362
                        }// for i
363
                }
364
                return solution;
365

    
366
        }
367
        /*
368
         * (non-Javadoc)
369
         *
370
         * @see com.iver.cit.jdwglib.dwg.IDwg2FMap#toFMapString(boolean)
371
         */
372
        public String toFMapString(boolean is3DFile) {
373
                if(is3DFile) {
374
                        return "FPolyline3D";
375
                } else {
376
                        return "FPolyline2D";
377
                }
378
        }
379

    
380
        public String toString(){
381
                return "PFacePolyline";
382
        }
383

    
384
        public void addVertex(IDwgVertex vertex) {
385
                // here we save the vertex (not the coordinate) because
386
                // this Polyline could have two kind of vertex (pface and pfaceface)
387
                if(vertex instanceof DwgVertexPFaceFace) {
388
                        faces.add(vertex);
389
                } else {
390
                        vertices.add(vertex);
391
                }
392
        }
393

    
394
        public void dump(){
395
                System.out.println("<PFacePolyline vertexCount="+vertexCount+" faceCount"+faceCount+">");
396
                int numRealVertex = 1;
397
                for(int i = 0; i < vertices.size(); i++){
398
                        IDwgVertex vertex = (IDwgVertex) vertices.get(i);
399
                        double[] point = vertex.getPoint();
400
                        System.out.println("<Vertex idx="+numRealVertex+" class="+vertex.getClass().getName()+" x="+point[0]+" y="+point[1]+" z="+point[2]+" >");
401
                        numRealVertex++;
402
                }
403

    
404
                for(int i = 0; i < faces.size(); i++){
405
                        IDwgVertex vertex = (IDwgVertex) faces.get(i);
406
                        if(vertex instanceof DwgVertexPFaceFace){
407
                                int[] point = ((DwgVertexPFaceFace)vertex).getVerticesidx();
408
                                System.out.println("<Vertex class="+vertex.getClass().getName()+" 1="+point[0]+" 2="+point[1]+" 3="+point[2]+" 4="+ point[3]+">");
409
                        }
410
                }
411
                System.out.println("</PFacePolyline>");
412
        }
413

    
414
        public void transform2Block(double[] bPoint, Point2D insPoint, double[] scale, double rot, List dwgObjectsWithoutBlocks, Map handle_objectsWithoutBlocks, DwgFile callBack) {
415
                DwgPFacePolyline transformedEntity = null;
416
                List vertices = this.getVertices();
417
                if (vertices != null) {
418
                        if(vertices.size() == 0) {
419
                                return;
420
                        }
421
                    List transformedVertices = new ArrayList();
422
                        for (int i=0;i < vertices.size();i++) {
423
                                double[] pointAux = null;
424
                                IDwgVertex vertex = (IDwgVertex) vertices.get(i);
425
                            if(!(vertex instanceof DwgVertexPFaceFace)){
426
                                    // DwgVertexPFaceFace hasnt coordinates, instead
427
                                    // it has indices in the vertex array
428
                                        double[] point = vertex.getPoint();
429
                                    pointAux = new double[]{point[0] - bPoint[0],
430
                                                    point[1] - bPoint[1], point[2] - bPoint[2]};
431

    
432
                                        double laX = insPoint.getX() + ((pointAux[0] * scale[0])*Math.cos(rot) + (pointAux[1]*scale[1])*(-1)*Math.sin(rot));
433
                                        double laY = insPoint.getY() + ((pointAux[0]*scale[0])*Math.sin(rot) + (pointAux[1]*scale[1])*Math.cos(rot));
434
                                        double laZ = pointAux[2];
435
                                        vertex.setPoint(new double[]{laX, laY, laZ});
436
                                        transformedVertices.add(vertex);
437
                                }
438
                        }// for
439
                        transformedEntity = (DwgPFacePolyline)this.clone();
440
                        fill(transformedEntity);
441
                        dwgObjectsWithoutBlocks.add(transformedEntity);
442
                        handle_objectsWithoutBlocks.put(new Integer(transformedEntity.getHandle().getOffset()), transformedEntity);
443
                }// if
444
        }
445

    
446
        public int getGeometrySubType(boolean is3DFile) {
447
                if (is3DFile) {
448
                        return Geometry.SUBTYPES.GEOM3D;
449
                } else {
450
                        return Geometry.SUBTYPES.GEOM2D;
451
                }
452
        }
453

    
454
        public int getGeometryType() {
455
                return Geometry.TYPES.MULTISURFACE;
456
        }
457

    
458
}
459