]> gerrit.simantics Code Review - simantics/3d.git/blob - org.simantics.proconf.g3d.occ/src/org/simantics/proconf/g3d/occ/geometry/OccTriangulator.java
ca5af06ada670af3202a0b676b902b36f7a5beb2
[simantics/3d.git] / org.simantics.proconf.g3d.occ / src / org / simantics / proconf / g3d / occ / geometry / OccTriangulator.java
1 /*******************************************************************************\r
2  * Copyright (c) 2007 VTT Technical Research Centre of Finland and others.\r
3  * All rights reserved. This program and the accompanying materials\r
4  * are made available under the terms of the Eclipse Public License v1.0\r
5  * which accompanies this distribution, and is available at\r
6  * http://www.eclipse.org/legal/epl-v10.html\r
7  *\r
8  * Contributors:\r
9  *     VTT Technical Research Centre of Finland - initial API and implementation\r
10  *******************************************************************************/\r
11 package org.simantics.proconf.g3d.occ.geometry;\r
12 \r
13 import java.io.IOException;\r
14 import java.util.Collection;\r
15 \r
16 import javax.vecmath.AxisAngle4d;\r
17 import javax.vecmath.Tuple3d;\r
18 import javax.vecmath.Vector2d;\r
19 \r
20 import org.jcae.opencascade.jni.BRepBuilderAPI_MakeEdge;\r
21 import org.jcae.opencascade.jni.BRepBuilderAPI_MakeFace;\r
22 import org.jcae.opencascade.jni.BRepBuilderAPI_MakeWire;\r
23 import org.jcae.opencascade.jni.BRepBuilderAPI_Transform;\r
24 import org.jcae.opencascade.jni.BRepOffsetAPI_ThruSections;\r
25 import org.jcae.opencascade.jni.BRepPrimAPI_MakePrism;\r
26 import org.jcae.opencascade.jni.BRepPrimAPI_MakeRevol;\r
27 import org.jcae.opencascade.jni.BRepPrimAPI_MakeTorus;\r
28 import org.jcae.opencascade.jni.BRep_Builder;\r
29 import org.jcae.opencascade.jni.GC_MakeArcOfCircle;\r
30 import org.jcae.opencascade.jni.GC_MakeSegment;\r
31 import org.jcae.opencascade.jni.GP_Elips;\r
32 import org.jcae.opencascade.jni.GP_Trsf;\r
33 import org.jcae.opencascade.jni.TopoDS_Edge;\r
34 import org.jcae.opencascade.jni.TopoDS_Face;\r
35 import org.jcae.opencascade.jni.TopoDS_Shape;\r
36 import org.jcae.opencascade.jni.TopoDS_Wire;\r
37 import org.simantics.proconf.g3d.csg.stubs.Barrel;\r
38 import org.simantics.proconf.g3d.csg.stubs.BooleanOperation;\r
39 import org.simantics.proconf.g3d.csg.stubs.Box;\r
40 import org.simantics.proconf.g3d.csg.stubs.CSGShape;\r
41 import org.simantics.proconf.g3d.csg.stubs.Cone;\r
42 import org.simantics.proconf.g3d.csg.stubs.Cylinder;\r
43 import org.simantics.proconf.g3d.csg.stubs.EllipticCylinder;\r
44 import org.simantics.proconf.g3d.csg.stubs.RectangularSolid;\r
45 import org.simantics.proconf.g3d.csg.stubs.RegularPrism;\r
46 import org.simantics.proconf.g3d.csg.stubs.Sphere;\r
47 import org.simantics.proconf.g3d.csg.stubs.Torus;\r
48 import org.simantics.layer0.utils.IEntity;\r
49 import org.simantics.proconf.g3d.base.G3DTools;\r
50 import org.simantics.proconf.g3d.base.GeometryProvider;\r
51 import org.simantics.proconf.g3d.occ.OccResources;\r
52 import org.simantics.utils.ErrorLogger;\r
53 \r
54 import com.jme.eclipse.test.ply.PLY_Loader;\r
55 import com.jme.scene.Geometry;\r
56 import com.jme.scene.Line;\r
57 import com.jme.scene.TriMesh;\r
58 import com.jme.util.geom.BufferUtils;\r
59 \r
60 public class OccTriangulator implements GeometryProvider{\r
61 \r
62     \r
63     public static final double MIN_VALUE = 0.001;\r
64     \r
65     public OccTriangulator() {\r
66         \r
67     }\r
68     \r
69     \r
70     \r
71     public boolean canHandle(IEntity instance) {\r
72         if (instance.isInstanceOf(OccResources.csgResource.CSGShape)) {\r
73             return true;\r
74         }\r
75         return false;\r
76     }\r
77     \r
78     public Geometry[] getGeometryFromResource(IEntity resource, boolean transform) {\r
79         if (resource.isInstanceOf(OccResources.csgResource.CSGShape)) {\r
80             TopoDS_Shape shape = OccTriangulator.getShapeFromResource(resource, transform);\r
81             Geometry[] g = OccTriangulator.getGeometry(shape);\r
82             shape.delete();\r
83             return g;\r
84         } \r
85         return null;\r
86     }\r
87     \r
88     public boolean reconstructGeometry(IEntity instance, boolean transform, Geometry[] geometry) {\r
89         if (instance.isInstanceOf(OccResources.csgResource.CSGShape)) {\r
90             TopoDS_Shape shape = OccTriangulator.getShapeFromResource(instance, transform);\r
91             boolean b = OccTriangulator.getGeometry(shape,geometry);\r
92             shape.delete();\r
93             return b;\r
94         } \r
95         return false;\r
96         \r
97     }\r
98 \r
99     public static Geometry[] getGeometry(TopoDS_Shape tds_shape) {\r
100         Geometry g[] = new Geometry[]{new TriMesh(),new Line()};\r
101         if (getGeometry(tds_shape, g))\r
102                 return g;\r
103         return null;\r
104         \r
105     }\r
106     \r
107     public static boolean getGeometry(TopoDS_Shape tds_shape, Geometry[] geometry) {\r
108         ViewableShapeImpl shape = new ViewableShapeImpl(tds_shape);\r
109         //System.out.println("Geometries in shape " + shape.numGeometries());\r
110         if (shape.numGeometries() > 0) {\r
111             int totalIndicesCount = 0;\r
112             int totalVerticesCount = 0;\r
113             boolean hasTCoords = true;\r
114             for (int geometryIndex = 0; geometryIndex < shape.numGeometries(); geometryIndex++) {\r
115                 IndexedGeometry geom = shape.getGeometry(geometryIndex);\r
116                 totalIndicesCount += geom.getIndices().length;\r
117                 totalVerticesCount += (geom.getCoordinates().length / 3);\r
118                 if (geom.getTCoordinates() == null || geom.getTCoordinates().length == 0)\r
119                         hasTCoords = false;\r
120             }\r
121             int currentVertex = 0;\r
122             int currentIndex = 0;\r
123             int indices[] = new int[totalIndicesCount];\r
124             \r
125             \r
126             \r
127             //TriMesh mesh = new TriMesh();\r
128             TriMesh mesh = (TriMesh)geometry[0];\r
129             float data[] = new float[totalVerticesCount*3];\r
130             float normals[] = new float[totalVerticesCount*3];\r
131             float tcoords[] = null;\r
132             if (hasTCoords)\r
133                 tcoords = new float[totalVerticesCount*2];\r
134             for (int geometryIndex = 0; geometryIndex < shape.numGeometries(); geometryIndex++) {\r
135                 IndexedGeometry geom = shape.getGeometry(geometryIndex);         \r
136                 System.arraycopy(geom.getCoordinates(), 0, data, currentVertex*3, geom.getCoordinates().length);\r
137                 System.arraycopy(geom.getNormals(), 0, normals, currentVertex*3, geom.getCoordinates().length);\r
138                 if (hasTCoords)\r
139                         System.arraycopy(geom.getTCoordinates(), 0, tcoords, currentVertex*2, geom.getTCoordinates().length - 1);\r
140                 \r
141                  for (int i = 0; i < geom.getIndices().length; i++) {\r
142                      indices[currentIndex + i] = geom.getIndices()[i] + currentVertex;\r
143                  }\r
144                \r
145                  currentVertex += geom.getCoordinates().length/3;\r
146                  currentIndex += geom.getIndices().length;\r
147                \r
148             }\r
149             mesh.reconstruct(BufferUtils.createFloatBuffer(data),BufferUtils.createFloatBuffer(normals) , null, hasTCoords ? BufferUtils.createFloatBuffer(tcoords) : null, BufferUtils.createIntBuffer(indices));\r
150             \r
151             int numEdgeVertices = 0;\r
152             int currentEdgeVertex = 0;\r
153             for (int i = 0; i < shape.getNumEdges(); i++) {\r
154                 numEdgeVertices += shape.getEdge(i).length/3;\r
155             }\r
156 \r
157             Line lines = (Line)geometry[1];\r
158             data = new float[numEdgeVertices*3];\r
159             for (int i = 0; i < shape.getNumEdges(); i++) {\r
160                 int index = currentEdgeVertex *3;\r
161                 System.arraycopy(shape.getEdge(i), 0,data, index, shape.getEdge(i).length);\r
162                 currentEdgeVertex+= shape.getEdge(i).length/3;\r
163             }\r
164             lines.reconstruct(BufferUtils.createFloatBuffer(data), null, null, null);\r
165             \r
166             tds_shape.delete();\r
167             return true;\r
168         } else {\r
169                 tds_shape.delete();\r
170                 return false;\r
171         }\r
172     }\r
173     /*\r
174     public static Geometry[] getGeometry(TopoDS_Shape tds_shape) {\r
175         return getGeometry(tds_shape,true);\r
176     }\r
177     */\r
178     /*\r
179     public static boolean getGeometry(TopoDS_Shape tds_shape, Geometry[] geometry) {\r
180         return getGeometry(tds_shape,true, geometry);\r
181     }\r
182     */\r
183     \r
184     private static TopoDS_Shape getPrimitiveFromResource(IEntity thing) {\r
185         if (!thing.isInstanceOf(OccResources.csgResource.Primitive)) \r
186             throw new IllegalArgumentException("Resource is not a primitive");\r
187         TopoDS_Shape shape = null;\r
188         if (thing.isInstanceOf(OccResources.csgResource.Box)) {\r
189             Box box = new Box(thing);\r
190             double sx = box.getXAxisSize()[0];\r
191             double sy = box.getYAxisSize()[0];\r
192             double sz = box.getZAxisSize()[0];\r
193             if (sx <= MIN_VALUE)\r
194                 sx = MIN_VALUE;\r
195             if (sy <= MIN_VALUE)\r
196                 sy = MIN_VALUE;\r
197             if (sz <= MIN_VALUE)\r
198                 sz = MIN_VALUE;\r
199             \r
200             shape = makeBox(-sx * 0.5, -sy * 0.5, -sz * 0.5, sx * 0.5, sy * 0.5, sz * 0.5);\r
201         } else if (thing.isInstanceOf(OccResources.csgResource.Cone)) {\r
202             Cone cone = new Cone(thing);\r
203             double h = cone.getHeight()[0];\r
204             double r1 = cone.getBottomRadius()[0];\r
205             double r2 = cone.getTopRadius()[0];\r
206             if (Math.abs(r1 - r2) > MIN_VALUE) { // OpenCASCADE won't work,\r
207                                             // if r1 == r2\r
208                 shape = makeCone(new double[] { 0.0, -h * 0.5, 0.0 }, new double[] { 0.0, 1.0, 0.0 }, r1,\r
209                         r2, h);\r
210             } else {\r
211                 shape = makeCylinder(new double[] { 0.0, -h * 0.5, 0.0 }, new double[] { 0.0, 1.0, 0.0 },\r
212                         r1, h);\r
213             }\r
214         } else if (thing.isInstanceOf(OccResources.csgResource.Sphere)) {\r
215             Sphere sphere = new Sphere(thing);\r
216             double r = sphere.getRadius()[0];\r
217             if (r <= MIN_VALUE)\r
218                 r = MIN_VALUE;\r
219             shape = makeSphere(0.0, 0.0, 0.0, r);\r
220         } else if (thing.isInstanceOf(OccResources.csgResource.Torus)) {\r
221             Torus torus = new Torus(thing);\r
222             double r1 = torus.getMajorRadius()[0];\r
223             double r2 = torus.getMinorRadius()[0];\r
224             if (r1 <= MIN_VALUE)\r
225                 r1 = MIN_VALUE;\r
226             if (r2 <= MIN_VALUE)\r
227                 r2 = MIN_VALUE;\r
228             shape = makeTorus(new double[] { 0.0, 0.0, 0.0 }, new double[] { 0.0, 1.0, 0.0 }, r1, r2);\r
229         } else if (thing.isInstanceOf(OccResources.csgResource.Cylinder)) {\r
230             Cylinder cylinder = new Cylinder(thing);\r
231             double h = cylinder.getHeight()[0];\r
232             double r = cylinder.getRadius()[0];\r
233             if (r <= MIN_VALUE)\r
234                 r = MIN_VALUE;\r
235             if (h <= MIN_VALUE)\r
236                 h = MIN_VALUE;\r
237             shape = makeCylinder(new double[] { 0.0, -h * 0.5, 0.0 }, new double[] { 0.0, 1.0, 0.0 }, r, h);\r
238                 } else if (thing.isInstanceOf(OccResources.csgResource.Barrel)) {\r
239                         Barrel barrel = new Barrel(thing);\r
240                         double h = barrel.getHeight()[0];\r
241                         if (h <= 0.0)\r
242                                 h = 0.01;\r
243                         double r1 = barrel.getMinorRadius()[0];\r
244                         if (r1 <= MIN_VALUE)\r
245                                 r1 = MIN_VALUE;\r
246                         double r2 = barrel.getMajorRadius()[0];\r
247                         if (r2 <= MIN_VALUE)\r
248                                 r2 = MIN_VALUE;\r
249                         if (Math.abs(r1 -r2)< MIN_VALUE)\r
250                                 r2 = r1 + MIN_VALUE;\r
251                         double p0[] = new double[]{0.0,-h*0.5,0.0};\r
252                         double p1[] = new double[]{0.0,-h*0.5,r1};\r
253                         double p2[] = new double[]{0.0, 0.0  ,r2};\r
254                         double p3[] = new double[]{0.0, h*0.5,r1};\r
255                         double p4[] = new double[]{0.0, h*0.5,0.0};\r
256                         GC_MakeArcOfCircle m = new GC_MakeArcOfCircle(p1,p2,p3);\r
257                         GC_MakeSegment s1 = new GC_MakeSegment(p0,p1);\r
258                         GC_MakeSegment s2 = new GC_MakeSegment(p3,p4);\r
259                         TopoDS_Edge e1 = (TopoDS_Edge)new BRepBuilderAPI_MakeEdge(s1.value()).shape();\r
260                         TopoDS_Edge e2 = (TopoDS_Edge)new BRepBuilderAPI_MakeEdge(m.value()).shape();\r
261                         TopoDS_Edge e3 = (TopoDS_Edge)new BRepBuilderAPI_MakeEdge(s2.value()).shape();\r
262                         TopoDS_Wire w = (TopoDS_Wire) new BRepBuilderAPI_MakeWire(e1,e2,e3).shape();\r
263                         TopoDS_Face F = (TopoDS_Face) new BRepBuilderAPI_MakeFace(w).shape();\r
264             shape = new BRepPrimAPI_MakeRevol(F,new double[]{0.0,0.0,0.0,0.0,1.0,0.0}).shape();\r
265             m.delete();\r
266             s1.delete();\r
267             s2.delete();\r
268             e1.delete();\r
269             e2.delete();\r
270             e3.delete();\r
271             w.delete();\r
272             F.delete();\r
273                 } else if (thing.isInstanceOf(OccResources.csgResource.EllipticCylinder)) {\r
274                         EllipticCylinder cylinder = new EllipticCylinder(thing);\r
275                         double h = cylinder.getHeight()[0];\r
276                         if (h < MIN_VALUE)\r
277                                 h = MIN_VALUE;\r
278                         double r2 = cylinder.getMinorRadius()[0];\r
279                         if (r2 < MIN_VALUE)\r
280                                 r2 = MIN_VALUE;\r
281                         double r1 = cylinder.getMajorRadius()[0];\r
282                         if (r1 < MIN_VALUE)\r
283                                 r1 = MIN_VALUE;\r
284                         GP_Elips ellipse;\r
285                         if (r1 < r2) {\r
286                                 // FIXME : ellipse should be rotated, but current JNI won't allow it since Ax2 is not separate object\r
287                                 ellipse = new GP_Elips(new double[]{0.0,-h*0.5,0.0,0.0,1.0,0.0},r2,r1);\r
288                         } else {\r
289                                 ellipse = new GP_Elips(new double[]{0.0,-h*0.5,0.0,0.0,1.0,0.0},r1,r2);\r
290                         }\r
291                         TopoDS_Edge ed = (TopoDS_Edge) new BRepBuilderAPI_MakeEdge(ellipse).shape();\r
292                         TopoDS_Wire w = (TopoDS_Wire) new BRepBuilderAPI_MakeWire(ed).shape();\r
293             TopoDS_Face F = (TopoDS_Face) new BRepBuilderAPI_MakeFace(w).shape();\r
294             shape = new BRepPrimAPI_MakePrism(F, new double[] { 0.0, h, 0.0 }).shape();\r
295             ellipse.delete();\r
296             ed.delete();\r
297             w.delete();\r
298             F.delete();\r
299                 } else if (thing.isInstanceOf(OccResources.csgResource.RegularPrism)) {\r
300                         RegularPrism prism = new RegularPrism(thing);\r
301                         int n = prism.getCorners()[0];\r
302                         if (n < 3)\r
303                                 n = 3;\r
304                         double h = prism.getHeight()[0];\r
305                         if (h < MIN_VALUE)\r
306                                 h = MIN_VALUE;\r
307                         double r = prism.getRadius()[0];\r
308                         if (r < MIN_VALUE)\r
309                                 r = MIN_VALUE;\r
310                         Vector2d vertices[] = new Vector2d[n];\r
311                         for (int i = 0; i < n; i++) {\r
312                                 vertices[i] = new Vector2d(Math.sin(Math.PI * 2.0 * i / n)*r,Math.cos(Math.PI * 2.0 * i / n)*r);\r
313                         }\r
314                         BRepBuilderAPI_MakeWire wire = new BRepBuilderAPI_MakeWire();\r
315                         for (int i = 0; i < n; i++) {\r
316                                 Vector2d v1 = vertices[i];\r
317                                 Vector2d v2 = vertices[(i+1)%n];\r
318                                 wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{v1.x,-h*0.5,v1.y},new double[]{v2.x,-h*0.5,v2.y}).shape());\r
319                         }\r
320                         TopoDS_Wire w = (TopoDS_Wire)wire.shape();\r
321                         TopoDS_Face F = (TopoDS_Face) new BRepBuilderAPI_MakeFace(w).shape();\r
322             shape = new BRepPrimAPI_MakePrism(F, new double[] { 0.0, h, 0.0 }).shape(); \r
323             wire.delete();\r
324             w.delete();\r
325             F.delete();\r
326                 } else if (thing.isInstanceOf(OccResources.csgResource.RectangularSolid)) {\r
327                         RectangularSolid solid = new RectangularSolid(thing);\r
328                         double x1 = solid.getXAxisMinimumSize()[0];\r
329                         double x2 = solid.getXAxisMaximumSize()[0];\r
330                         double y = solid.getYAxisSize()[0];\r
331                         double z1 = solid.getZAxisMinimumSize()[0];\r
332                         double z2 = solid.getZAxisMaximumSize()[0];\r
333                         if (x1 < MIN_VALUE)\r
334                                 x1 = MIN_VALUE;\r
335                         if (x2 < MIN_VALUE)\r
336                                 x2 = MIN_VALUE;\r
337                         if (y < MIN_VALUE)\r
338                                 y = MIN_VALUE;\r
339                         if (z1 < MIN_VALUE)\r
340                                 z1 = MIN_VALUE;\r
341                         if (z2 < MIN_VALUE)\r
342                                 z2 = MIN_VALUE;\r
343                         x1 *= 0.5;\r
344                         x2 *= 0.5;\r
345                         y *= 0.5;\r
346                         z1 *= 0.5;\r
347                         z2 *= 0.5;\r
348                         \r
349                         BRepBuilderAPI_MakeWire wire = new BRepBuilderAPI_MakeWire();\r
350                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{x1,-y,z1},new double[]{x1,-y,-z1}).shape());\r
351                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{x1,-y,-z1},new double[]{-x1,-y,-z1}).shape());\r
352                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{-x1,-y,-z1},new double[]{-x1,-y,z1}).shape());\r
353                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{-x1,-y,z1},new double[]{x1,-y,z1}).shape());\r
354                         TopoDS_Wire w1 = (TopoDS_Wire)wire.shape();\r
355                         wire.delete();\r
356                         wire = new BRepBuilderAPI_MakeWire();\r
357                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{x2, y,z2},new double[]{x2, y,-z2}).shape());\r
358                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{x2, y,-z2},new double[]{-x2, y,-z2}).shape());\r
359                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{-x2, y,-z2},new double[]{-x2, y,z2}).shape());\r
360                         wire.add((TopoDS_Edge)new BRepBuilderAPI_MakeEdge(new double[]{-x2, y,z2},new double[]{x2, y,z2}).shape());\r
361                         TopoDS_Wire w2 = (TopoDS_Wire)wire.shape();\r
362                         BRepOffsetAPI_ThruSections generatorb = new BRepOffsetAPI_ThruSections(true, true);\r
363                         generatorb.addWire(w1);\r
364                         generatorb.addWire(w2);\r
365                         generatorb.build();\r
366                         shape = generatorb.shape();\r
367                         wire.delete();\r
368                         w1.delete();\r
369                         w2.delete();\r
370                 } else {\r
371                         throw new UnsupportedOperationException("Unsupported primitive");\r
372 \r
373                 }\r
374         return shape;\r
375     }\r
376     \r
377     private static TopoDS_Shape getBooleanOp(IEntity thing, TopoDS_Shape topoDSshape1, TopoDS_Shape topoDSshape2) {\r
378         if (!thing.isInstanceOf(OccResources.csgResource.BooleanOperation))\r
379             throw new IllegalArgumentException("Resource is not a boolean operation");\r
380         TopoDS_Shape shape = null;\r
381         int type;\r
382         if (thing.isInstanceOf(OccResources.csgResource.Difference)) {\r
383             type = 0;\r
384         } else if (thing.isInstanceOf(OccResources.csgResource.Union)) {\r
385             type = 1;\r
386         } else if (thing.isInstanceOf(OccResources.csgResource.Intersection)) {\r
387             type = 2;\r
388         } else {\r
389             throw new UnsupportedOperationException("Unsupported boolean operation");\r
390         }\r
391        \r
392         switch (type) {\r
393         case 0:\r
394             shape = makeCut(topoDSshape1, topoDSshape2);\r
395             break;\r
396         case 1:\r
397             shape = makeFuse(topoDSshape1, topoDSshape2);\r
398             break;\r
399         case 2:\r
400             shape = makeCommon(topoDSshape1, topoDSshape2);\r
401             break;\r
402         }\r
403         topoDSshape1.delete();\r
404         topoDSshape2.delete();\r
405         return shape;\r
406     }\r
407     \r
408     private static TopoDS_Shape getBooleanOpFromResource(IEntity thing) {\r
409         if (!thing.isInstanceOf(OccResources.csgResource.BooleanOperation))\r
410                 throw new IllegalArgumentException("Resource is not a boolean operation");\r
411         \r
412         TopoDS_Shape shape = null;\r
413         TopoDS_Shape topoDSshape1 = null;\r
414         TopoDS_Shape topoDSshape2 = null;\r
415         BooleanOperation op = new BooleanOperation(thing);\r
416         CSGShape mainShape = op.getMainShape();\r
417         Collection<CSGShape> secondaryShapes = op.getSecondaryShape();\r
418         if (mainShape == null || secondaryShapes.size() < 1) {\r
419             throw new RuntimeException("Cannot find requested Shapes for boolean operation");\r
420         }\r
421         topoDSshape1 = getShapeFromResource(mainShape);\r
422         for (CSGShape shape2 : secondaryShapes) {\r
423             topoDSshape2 = getShapeFromResource(shape2);\r
424             shape = getBooleanOp(thing,topoDSshape1,topoDSshape2);\r
425             topoDSshape1.delete();\r
426             topoDSshape1 = shape;\r
427         }\r
428         \r
429         topoDSshape2.delete();\r
430         return shape;\r
431     }\r
432 \r
433     private static TopoDS_Shape getShapeFromResource(IEntity thing) {\r
434         return getShapeFromResource(thing, true);\r
435     }\r
436     \r
437     private static TopoDS_Shape getShapeFromResource(IEntity thing, boolean transform) {\r
438         if (thing.isInstanceOf(OccResources.csgResource.CSGShape)) {\r
439             TopoDS_Shape shape = null;\r
440             \r
441             if (thing.isInstanceOf(OccResources.csgResource.Primitive)) {\r
442                 shape = getPrimitiveFromResource(thing);\r
443 \r
444             } else if (thing.isInstanceOf(OccResources.csgResource.BooleanOperation)) {\r
445                 shape = getBooleanOpFromResource(thing);\r
446 \r
447             } else {\r
448                 throw new UnsupportedOperationException("Shape must be a primitive or a boolean operation");\r
449             }\r
450             Tuple3d c = null;\r
451             CSGShape shapeType = new CSGShape(thing);\r
452             \r
453             if (shapeType.getCenter() != null)\r
454                 c = G3DTools.getVector(shapeType.getCenter());\r
455             \r
456             TopoDS_Shape tShape = null;\r
457             if(c != null) {\r
458                 tShape = makeTranslation(shape, c.x, c.y, c.z);\r
459                 shape.delete();\r
460                 shape = tShape;\r
461             }\r
462             if (transform) {\r
463                 //CSGShape shapeType = CSGShapeFactory.create(resource);\r
464                 Tuple3d p = G3DTools.getVector(shapeType.getLocalPosition());\r
465                 AxisAngle4d r = G3DTools.getOrientation(shapeType.getLocalOrientation());\r
466                \r
467                 if (Math.abs(r.angle) > 0.01) {\r
468                     tShape = makeRotation(shape, new double[] { 0.0, 0.0, 0.0, r.x, r.y, r.z }, r.angle);\r
469                     shape.delete();\r
470                     shape = tShape;\r
471                 }\r
472                 tShape = makeTranslation(shape, p.x, p.y, p.z);\r
473                 shape.delete();\r
474                 shape = tShape;\r
475             }\r
476 \r
477             return shape;\r
478 \r
479         }\r
480         throw new UnsupportedOperationException("Resource is not a shape");\r
481     }\r
482 \r
483     private static TopoDS_Shape getShapeFromFile(String filename) {\r
484         assert (filename != null);\r
485         if (filename.endsWith("stp")) {\r
486             TopoDS_Shape shape = importSTEP(filename);\r
487             return shape;\r
488         } else if (filename.endsWith("step")) {\r
489             TopoDS_Shape shape = importSTEP(filename);\r
490             return shape;\r
491         } else if (filename.endsWith("iges")) {\r
492             TopoDS_Shape shape = importIGES(filename);\r
493             return shape;\r
494         } else if (filename.endsWith("brep")) {\r
495             TopoDS_Shape shape = importBREP(filename);\r
496             return shape;\r
497         } else {\r
498             throw new UnsupportedOperationException("Unsupported format " + filename);\r
499         }\r
500 \r
501     }\r
502 \r
503    \r
504 \r
505     public static Geometry[] getGeometryFromFile(String filename) {\r
506         if (filename.endsWith("ply")) {\r
507             try {\r
508                 return new Geometry[]{PLY_Loader.loadPLY(filename)};\r
509             } catch (IOException e) {\r
510                 ErrorLogger.defaultLogError(e);\r
511                 return null;\r
512             }\r
513         }\r
514         TopoDS_Shape shape = OccTriangulator.getShapeFromFile(filename);\r
515         Geometry g[] = OccTriangulator.getGeometry(shape);\r
516         shape.delete();\r
517         return g;\r
518     }\r
519     \r
520     public static TopoDS_Shape importBREP(String filename) {\r
521         org.jcae.opencascade.jni.BRep_Builder aBuilder = new org.jcae.opencascade.jni.BRep_Builder();\r
522         org.jcae.opencascade.jni.TopoDS_Shape myShape = org.jcae.opencascade.jni.BRepTools.read(filename, aBuilder);\r
523         aBuilder.delete();\r
524         return myShape;\r
525     }\r
526 \r
527     public static TopoDS_Shape importIGES(String filename) {\r
528         org.jcae.opencascade.jni.IGESControl_Reader aReader = new org.jcae.opencascade.jni.IGESControl_Reader();\r
529         aReader.readFile(filename);\r
530         aReader.clearShapes();\r
531         aReader.transferRoots();\r
532         TopoDS_Shape result = aReader.oneShape();\r
533         aReader.delete();\r
534         return result;\r
535     }\r
536     \r
537     public static TopoDS_Shape importSTEP(String filename) {\r
538         org.jcae.opencascade.jni.STEPControl_Reader aReader = new org.jcae.opencascade.jni.STEPControl_Reader();\r
539         aReader.readFile(filename);\r
540         aReader.clearShapes();\r
541         aReader.transferRoots();\r
542         TopoDS_Shape result = aReader.oneShape();\r
543         aReader.delete();\r
544         return result;\r
545     }\r
546 \r
547     public static TopoDS_Shape archimede(TopoDS_Shape topoDS_Shape, double param, double param2, double param3) {\r
548         throw new UnsupportedOperationException();\r
549     }\r
550 \r
551     public static TopoDS_Shape suppressHolesInFaceOrShell(TopoDS_Shape topoDS_Shape, TopoDS_Shape[] topoDS_Shape1) {\r
552         throw new UnsupportedOperationException();\r
553     }\r
554 \r
555     public static TopoDS_Shape suppressHole(TopoDS_Shape topoDS_Shape, TopoDS_Shape[] topoDS_Shape1,\r
556             TopoDS_Shape[] topoDS_Shape2, TopoDS_Shape[] topoDS_Shape3) {\r
557         throw new UnsupportedOperationException();\r
558     }\r
559 \r
560     public static TopoDS_Shape[] suppressFaces(TopoDS_Shape topoDS_Shape, TopoDS_Shape[] topoDS_Shape1) {\r
561         throw new UnsupportedOperationException();\r
562     }\r
563 \r
564     public static TopoDS_Shape[] subShapeAll(TopoDS_Shape topoDS_Shape, short param) {\r
565         throw new UnsupportedOperationException();\r
566     }\r
567 \r
568     public static TopoDS_Shape subShape(TopoDS_Shape topoDS_Shape, short param, TopoDS_Shape[] topoDS_Shape2) {\r
569         throw new UnsupportedOperationException();\r
570     }\r
571 \r
572     public static boolean setBlock(TopoDS_Shape topoDS_Shape) {\r
573         throw new UnsupportedOperationException();\r
574     }\r
575 \r
576     public static TopoDS_Shape partitionKeepFaces(TopoDS_Shape[] topoDS_Shape, TopoDS_Shape topoDS_Shape1, boolean param) {\r
577         throw new UnsupportedOperationException();\r
578     }\r
579 \r
580     public static TopoDS_Shape orientationChange(TopoDS_Shape topoDS_Shape) {\r
581         throw new UnsupportedOperationException();\r
582     }\r
583 \r
584     public static short nbLabels() {\r
585         throw new UnsupportedOperationException();\r
586     }\r
587 \r
588     public static TopoDS_Shape makeWire(TopoDS_Shape[] topoDS_Shape) {\r
589         throw new UnsupportedOperationException();\r
590     }\r
591 \r
592     public static TopoDS_Shape makeVertex(double param, double param1, double param2) {\r
593         throw new UnsupportedOperationException();\r
594     }\r
595 \r
596     public static TopoDS_Shape makeVector(double[] pointStruct, double[] pointStruct1) {\r
597         throw new UnsupportedOperationException();\r
598     }\r
599 \r
600     public static TopoDS_Shape makeTranslation(TopoDS_Shape aShape, double x, double y, double z) {\r
601         GP_Trsf theTransformation = new GP_Trsf();\r
602         theTransformation.setTranslation(new double[] { x, y, z });\r
603         BRepBuilderAPI_Transform bt = new BRepBuilderAPI_Transform(aShape, theTransformation, true);\r
604 \r
605         TopoDS_Shape shape = bt.shape();\r
606         bt.delete();\r
607         theTransformation.delete();\r
608         return shape;\r
609     }\r
610 \r
611     public static TopoDS_Shape makeTorus(double[] pointStruct, double[] dirStruct, double r1, double r2) {\r
612         double[] axe = new double[6];\r
613         System.arraycopy(pointStruct, 0, axe, 0, 3);\r
614         System.arraycopy(dirStruct, 0, axe, 3, 3);\r
615         org.jcae.opencascade.jni.TopoDS_Shape tds = new BRepPrimAPI_MakeTorus(axe, r1, r2).shape();\r
616         return tds;\r
617     }\r
618 \r
619     public static TopoDS_Shape makeSphere(double x, double y, double z, double radius) {\r
620         double[] c = new double[] { x, y, z };\r
621         org.jcae.opencascade.jni.TopoDS_Shape tds = new org.jcae.opencascade.jni.BRepPrimAPI_MakeSphere(c, radius)\r
622                 .shape();\r
623         return tds;\r
624     }\r
625 \r
626     public static TopoDS_Shape makeSewingShape(TopoDS_Shape topoDS_Shape, double param) {\r
627         throw new UnsupportedOperationException();\r
628     }\r
629 \r
630     public static TopoDS_Shape makeSewing(TopoDS_Shape[] topoDS_Shape, double param) {\r
631         throw new UnsupportedOperationException();\r
632     }\r
633 \r
634     public static TopoDS_Shape makeScaleTransform(TopoDS_Shape topoDS_Shape, double[] pointStruct, double param) {\r
635         throw new UnsupportedOperationException();\r
636     }\r
637 \r
638     public static TopoDS_Shape makeRotation(TopoDS_Shape aShape, double[] axisStruct, double angle) {\r
639 \r
640         GP_Trsf theTransformation = new GP_Trsf();\r
641         theTransformation.setRotation(axisStruct, angle);\r
642         BRepBuilderAPI_Transform bt = new BRepBuilderAPI_Transform(aShape, theTransformation, true);\r
643         TopoDS_Shape shape = bt.shape();\r
644         bt.delete();\r
645         theTransformation.delete();\r
646         return shape;\r
647     }\r
648 \r
649     public static TopoDS_Shape makeRevolution(TopoDS_Shape topoDS_Shape, double[] axisStruct, double param) {\r
650         throw new UnsupportedOperationException();\r
651     }\r
652 \r
653     public static TopoDS_Shape makePrism(TopoDS_Shape topoDS_Shape, double[] pointStruct, double[] pointStruct2) {\r
654         throw new UnsupportedOperationException();\r
655     }\r
656 \r
657     public static TopoDS_Shape makePlane(double[] pointStruct, double[] dirStruct, double param) {\r
658         throw new UnsupportedOperationException();\r
659     }\r
660 \r
661     public static TopoDS_Shape makePlacedBox(double param, double param1, double param2, double param3, double param4,\r
662             double param5) {\r
663         throw new UnsupportedOperationException();\r
664     }\r
665 \r
666     public static TopoDS_Shape makePipe(TopoDS_Shape topoDS_Shape, TopoDS_Shape topoDS_Shape1) {\r
667         throw new UnsupportedOperationException();\r
668     }\r
669 \r
670     public static TopoDS_Shape makePanel(TopoDS_Shape topoDS_Shape, short param, double param2) {\r
671         throw new UnsupportedOperationException();\r
672     }\r
673 \r
674     public static TopoDS_Shape makeMultiTranslation2D(TopoDS_Shape topoDS_Shape, double[] dirStruct, double param,\r
675             short param3, double[] dirStruct4, double param5, short param6) {\r
676         throw new UnsupportedOperationException();\r
677     }\r
678 \r
679     public static TopoDS_Shape makeMultiTranslation1D(TopoDS_Shape topoDS_Shape, double[] dirStruct, double param, short param3) {\r
680         throw new UnsupportedOperationException();\r
681     }\r
682 \r
683     public static TopoDS_Shape makeMultiRotation2D(TopoDS_Shape topoDS_Shape, double[] dirStruct, double[] pointStruct,\r
684             double param, short param4, double param5, short param6) {\r
685         throw new UnsupportedOperationException();\r
686     }\r
687 \r
688     public static TopoDS_Shape makeMultiRotation1D(TopoDS_Shape topoDS_Shape, double[] dirStruct, double[] pointStruct,\r
689             short param) {\r
690         throw new UnsupportedOperationException();\r
691     }\r
692 \r
693     public static TopoDS_Shape makeMirrorByPlane(TopoDS_Shape topoDS_Shape, TopoDS_Shape topoDS_Shape1) {\r
694         throw new UnsupportedOperationException();\r
695     }\r
696 \r
697     public static TopoDS_Shape makeLine(double[] pointStruct, double[] dirStruct) {\r
698         throw new UnsupportedOperationException();\r
699     }\r
700 \r
701     public static TopoDS_Shape makeFilling(TopoDS_Shape topoDS_Shape, short param, short param2, double param3, double param4,\r
702             short param5) {\r
703         throw new UnsupportedOperationException();\r
704     }\r
705 \r
706     public static TopoDS_Shape makeFillet(TopoDS_Shape topoDS_Shape, double param, short param2, TopoDS_Shape[] topoDS_Shape3) {\r
707         throw new UnsupportedOperationException();\r
708     }\r
709 \r
710     public static TopoDS_Shape makeFace(TopoDS_Shape topoDS_Shape, boolean param) {\r
711         throw new UnsupportedOperationException();\r
712     }\r
713 \r
714     public static TopoDS_Shape makeEdge(double[] pointStruct, double[] pointStruct1) {\r
715         throw new UnsupportedOperationException();\r
716     }\r
717 \r
718     public static TopoDS_Shape makeCylinder(double[] pointStruct, double[] dirStruct, double radius, double height) {\r
719         double[] axe = new double[6];\r
720         System.arraycopy(pointStruct, 0, axe, 0, 3);\r
721         System.arraycopy(dirStruct, 0, axe, 3, 3);\r
722         org.jcae.opencascade.jni.TopoDS_Shape tds = new org.jcae.opencascade.jni.BRepPrimAPI_MakeCylinder(axe, radius,\r
723                 height, 2 * Math.PI).shape();\r
724         return tds;\r
725     }\r
726 \r
727     public static TopoDS_Shape makeCopy(TopoDS_Shape topoDS_Shape) {\r
728         throw new UnsupportedOperationException();\r
729     }\r
730 \r
731     public static TopoDS_Shape makeCone(double[] pointStruct, double[] dirStruct, double radius1, double radius2, double height) {\r
732         double[] axe = new double[6];\r
733         System.arraycopy(pointStruct, 0, axe, 0, 3);\r
734         System.arraycopy(dirStruct, 0, axe, 3, 3);\r
735         org.jcae.opencascade.jni.TopoDS_Shape tds = new org.jcae.opencascade.jni.BRepPrimAPI_MakeCone(axe, radius1,\r
736                 radius2, height, 2 * Math.PI).shape();\r
737         return tds;\r
738     }\r
739 \r
740     public static TopoDS_Shape makeCompound(TopoDS_Shape[] shapes) {\r
741         BRep_Builder builder = new BRep_Builder();\r
742         org.jcae.opencascade.jni.TopoDS_Compound comp = new org.jcae.opencascade.jni.TopoDS_Compound();\r
743         builder.makeCompound(comp);\r
744         for (int i = 0; i < shapes.length; i++) {\r
745 \r
746             builder.add(comp, shapes[i]);\r
747         }\r
748         builder.delete();\r
749         return comp;\r
750     }\r
751 \r
752     public static TopoDS_Shape makeCircle(double[] pointStruct, double[] dirStruct, double param) {\r
753         throw new UnsupportedOperationException();\r
754     }\r
755 \r
756     public static TopoDS_Shape makeChamfer(TopoDS_Shape topoDS_Shape, double param, double param2, short param3,\r
757             TopoDS_Shape[] topoDS_Shape4) {\r
758         throw new UnsupportedOperationException();\r
759     }\r
760 \r
761     public static TopoDS_Shape makeCDG(TopoDS_Shape topoDS_Shape) {\r
762         throw new UnsupportedOperationException();\r
763     }\r
764 \r
765     public static TopoDS_Shape makeBox(double x1, double y1, double z1, double x2, double y2, double z2) {\r
766         double[] p1 = new double[] { x1, y1, z1 };\r
767         double[] p2 = new double[] { x2, y2, z2 };\r
768         org.jcae.opencascade.jni.TopoDS_Shape tds = new org.jcae.opencascade.jni.BRepPrimAPI_MakeBox(p1, p2).shape();\r
769         return tds;\r
770     }\r
771 \r
772     public static TopoDS_Shape makeCut(TopoDS_Shape shape1, TopoDS_Shape shape2) {\r
773 \r
774         org.jcae.opencascade.jni.TopoDS_Shape s = new org.jcae.opencascade.jni.BRepAlgoAPI_Cut(shape1, shape2).shape();\r
775         return s;\r
776     }\r
777     \r
778     public static TopoDS_Shape makeCommon(TopoDS_Shape shape1, TopoDS_Shape shape2) {\r
779 \r
780         org.jcae.opencascade.jni.TopoDS_Shape s = new org.jcae.opencascade.jni.BRepAlgoAPI_Common(shape1, shape2).shape();\r
781         return s;\r
782     }\r
783     \r
784     public static TopoDS_Shape makeFuse(TopoDS_Shape shape1, TopoDS_Shape shape2) {\r
785 \r
786         org.jcae.opencascade.jni.TopoDS_Shape s = new org.jcae.opencascade.jni.BRepAlgoAPI_Fuse(shape1, shape2).shape();\r
787         return s;\r
788     }\r
789 \r
790     public static TopoDS_Shape makeArc(double[] pointStruct, double[] pointStruct1, double[] pointStruct2) {\r
791         throw new UnsupportedOperationException();\r
792     }\r
793     \r
794     public static TopoDS_Shape makeWedge(double[] pointStruct, double[] dirStruct,double dx, double dy, double dz, double xmin, double zmin, double xmax, double zmax) {\r
795         double[] axe = new double[6];\r
796         System.arraycopy(pointStruct, 0, axe, 0, 3);\r
797         System.arraycopy(dirStruct, 0, axe, 3, 3);\r
798         org.jcae.opencascade.jni.TopoDS_Shape s = new org.jcae.opencascade.jni.BRepPrimAPI_MakeWedge(axe,  dx,  dy,  dz,  xmin,  zmin, xmax, zmax).shape();\r
799         return s;\r
800     }\r
801 \r
802  \r
803 \r
804     public static void exportBREP(TopoDS_Shape shape, String filename) {\r
805         org.jcae.opencascade.jni.BRepTools.write(shape, filename);\r
806     }\r
807 \r
808     public static void exportIGES(TopoDS_Shape shape, String filename) {\r
809         throw new UnsupportedOperationException();\r
810         \r
811 //          IGESControl_Writer writer=new IGESControl_Writer();\r
812 //          writer.addShape(shape); writer.write(filename,false);\r
813          \r
814     }\r
815 \r
816 \r
817 \r
818 \r
819     \r
820 }\r