Select Git revision
GModelIO_OCC.h
Forked from
gmsh / gmsh
Source project has a limited visibility.
GModelIO_OCC.h 18.50 KiB
// Gmsh - Copyright (C) 1997-2017 C. Geuzaine, J.-F. Remacle
//
// See the LICENSE.txt file for license information. Please report all
// bugs and problems to the public mailing list <gmsh@onelab.info>.
#ifndef _GMODELIO_OCC_H_
#define _GMODELIO_OCC_H_
#include <vector>
#include <map>
#include "GmshConfig.h"
#include "GmshMessage.h"
#include "GModel.h"
class ExtrudeParams;
#if defined(HAVE_OCC)
#include <TopoDS_Shape.hxx>
#include <TopoDS_Vertex.hxx>
#include <TopoDS_Edge.hxx>
#include <TopoDS_Wire.hxx>
#include <TopoDS_Face.hxx>
#include <TopoDS_Shell.hxx>
#include <TopoDS_Solid.hxx>
#include <TopoDS_Compound.hxx>
#include <TopTools_IndexedMapOfShape.hxx>
#include <TopTools_DataMapOfShapeInteger.hxx>
#include <TopTools_DataMapOfIntegerShape.hxx>
#include <TopTools_ShapeMapHasher.hxx>
#include <NCollection_DataMap.hxx>
class BRepSweep_Prism;
class BRepSweep_Revol;
class BRepBuilderAPI_Transform;
class BRepBuilderAPI_GTransform;
class OCC_Internals {
public:
enum BooleanOperator { Union, Intersection, Difference, Section, Fragments };
private :
// have the internals changed since the last synchronisation
bool _changed;
// maximum tags for each bound entity (shell, wire, vertex, edge, face, solid)
int _maxTag[6];
// all the (sub)shapes, updated dynamically when shapes need to be imported
// into a GModel
TopTools_IndexedMapOfShape _vmap, _emap, _wmap, _fmap, _shmap, _somap;
// cache mapping TopoDS_Shapes to their corresponding (future) GEntity tags
TopTools_DataMapOfShapeInteger _vertexTag, _edgeTag, _faceTag, _solidTag;
TopTools_DataMapOfIntegerShape _tagVertex, _tagEdge, _tagFace, _tagSolid;
// cache mapping TopoDS_Shapes to tags for internal use during geometry
// construction
TopTools_DataMapOfShapeInteger _wireTag, _shellTag;
TopTools_DataMapOfIntegerShape _tagWire, _tagShell;
// internal mesh attributes
class meshAttr {
public:
meshAttr() : size(MAX_LC), extrude(0) {}
meshAttr(double s) : size(s), extrude(0) {}
meshAttr(ExtrudeParams *e) : size(MAX_LC), extrude(e) {}
double size;
ExtrudeParams *extrude;
TopoDS_Shape source;
};
NCollection_DataMap<TopoDS_Shape, meshAttr, TopTools_ShapeMapHasher> _meshAttr;
// iterate on all bound entities and recompute the maximum tag
void _recomputeMaxTag(int dim);
// add a shape and all its subshapes to _vmap, _emap, ..., _somap
void _addShapeToMaps(TopoDS_Shape shape);
// apply various healing algorithms to try to fix the shape
void _healShape(TopoDS_Shape &myshape, double tolerance, bool fixdegenerated,
bool fixsmalledges, bool fixspotstripfaces, bool sewfaces,
bool makesolids=false, double scaling=0.0);
// apply a geometrical transformation (does not modify Shape)
bool _transform(const std::vector<std::pair<int, int> > &inDimTags,
BRepBuilderAPI_Transform *tfo);
// apply a G geometrical transformation (modifies Shape : affinity...)
bool _gtransform(const std::vector<std::pair<int, int> > &inDimTags,
BRepBuilderAPI_GTransform *gtfo);
// add circle or ellipse arc
bool _addArc(int tag, int startTag, int centerTag, int endTag, int mode);
// add bezier or bspline
bool _addSpline(int tag, const std::vector<int> &vertexTags, int mode);
// apply extrusion-like operations
bool _extrude(int mode, const std::vector<std::pair<int, int> > &inDimTags,
double x, double y, double z, double dx, double dy, double dz,
double ax, double ay, double az, double angle, int wireTag,
std::vector<std::pair<int, int> > &outDimTags,
ExtrudeParams *e=0);
// set mesh attributes for extruded meshes
void _setMeshAttr(const TopoDS_Compound &c, BRepSweep_Prism *p,
BRepSweep_Revol *r, ExtrudeParams *e,
double x, double y, double z,
double dx, double dy, double dz,
double ax, double ay, double az, double angle);
void _copyMeshAttr(TopoDS_Edge edge, GEdge *ge);
void _copyMeshAttr(TopoDS_Face face, GFace *gf);
void _copyMeshAttr(TopoDS_Solid solid, GRegion *gr);
public:
OCC_Internals();
// have the internals changed since the last synchronisation?
bool getChanged() const { return _changed; }
// reset all maps
void reset();
// bind and unbind OpenCASCADE shapes to tags
void bind(TopoDS_Vertex vertex, int tag);
void bind(TopoDS_Edge edge, int tag);
void bind(TopoDS_Wire wire, int tag);
void bind(TopoDS_Face face, int tag);
void bind(TopoDS_Shell shell, int tag);
void bind(TopoDS_Solid solid, int tag);
void bind(TopoDS_Shape shape, int dim, int tag);
void unbind(TopoDS_Vertex vertex, int tag, bool recursive=false);
void unbind(TopoDS_Edge edge, int tag, bool recursive=false);
void unbind(TopoDS_Wire wire, int tag, bool recursive=false);
void unbind(TopoDS_Face face, int tag, bool recursive=false);
void unbind(TopoDS_Shell shell, int tag, bool recursive=false);
void unbind(TopoDS_Solid solid, int tag, bool recursive=false);
void unbind(TopoDS_Shape shape, int dim, int tag, bool recursive=false);
// bind (potentially) mutliple entities in shape and return the tags in
// outTags. If tag > 0 and a single entity if found, use that; if
// highestDimOnly is true, only bind the entities of the highest
// dimension
void bind(TopoDS_Shape shape, bool highestDimOnly, int tag,
std::vector<std::pair<int, int> > &outDimTags);
// is the entity of a given dimension and tag bound?
bool isBound(int dim, int tag);
// get the entity of a given dimension and tag
TopoDS_Shape find(int dim, int tag);
// set/get max tag of entity for each dimension (0, 1, 2, 3), as well as
// -2 for shells and -1 for wires
void setMaxTag(int dim, int val);
int getMaxTag(int dim) const;
// add shapes
bool addVertex(int tag, double x, double y, double z, double meshSize=MAX_LC);
bool addLine(int tag, int startTag, int endTag);
bool addLine(int tag, const std::vector<int> &vertexTags);
bool addCircleArc(int tag, int startTag, int centerTag, int endTag);
bool addCircle(int tag, double x, double y, double z, double r, double angle1,
double angle2);
bool addEllipseArc(int tag, int startTag, int centerTag, int endTag);
bool addEllipse(int tag, double x, double y, double z, double r1, double r2,
double angle1, double angle2);
bool addBezier(int tag, const std::vector<int> &vertexTags);
bool addBSpline(int tag, const std::vector<int> &vertexTags);
bool addWire(int tag, const std::vector<int> &edgeTags, bool checkClosed);
bool addLineLoop(int tag, const std::vector<int> &edgeTags);
bool addRectangle(int tag, double x1, double y1, double z1,
double x2, double y2, double z2, double roundedRadius=0.);
bool addDisk(int tag, double xc, double yc, double zc, double rx, double ry);
bool addPlaneSurface(int tag, const std::vector<int> &wireTags);
bool addSurfaceFilling(int tag, int wireTag);
bool addSurfaceLoop(int tag, const std::vector<int> &faceTags);
bool addVolume(int tag, const std::vector<int> &shellTags);
bool addSphere(int tag, double xc, double yc, double zc, double radius,
double angle1, double angle2, double angle3);
bool addBlock(int tag, double x1, double y1, double z1,
double x2, double y2, double z2);
bool addCylinder(int tag, double x1, double y1, double z1, double x2, double y2,
double z2, double r, double angle);
bool addCone(int tag, double x1, double y1, double z1, double x2, double y2,
double z2, double r1, double r2, double angle);
bool addWedge(int tag, double x, double y, double z, double dx, double dy,
double dz, double ltx);
bool addTorus(int tag, double x, double y, double z, double r1, double r2,
double angle);
bool addThruSections(int tag, const std::vector<int> &wireTags,
std::vector<std::pair<int, int> > &outDimTags,
bool makeSolid, bool makeRuled);
bool addThickSolid(int tag, int solidTag, const std::vector<int> &excludeFaceTags,
double offset);
// extrude and revolve
bool extrude(const std::vector<std::pair<int, int> > &inDimTags,
double dx, double dy, double dz,
std::vector<std::pair<int, int> > &outDimTags,
ExtrudeParams *e=0);
bool revolve(const std::vector<std::pair<int, int> > &inDimTags,
double x, double y, double z, double ax, double ay, double az,
double angle, std::vector<std::pair<int, int> > &outDimTags,
ExtrudeParams *e=0);
bool addPipe(const std::vector<std::pair<int, int> > &inDimTags, int wireTag,
std::vector<std::pair<int, int> > &outDimTags);
// fillet
bool fillet(const std::vector<int> ®ionTags, const std::vector<int> &edgeTags,
double radius, std::vector<std::pair<int, int> > &ouDimTags);
// apply boolean operator
bool applyBooleanOperator(int tag, BooleanOperator op,
const std::vector<std::pair<int, int> > &objectDimTags,
const std::vector<std::pair<int, int> > &toolDimTags,
std::vector<std::pair<int, int> > &outDimTags,
bool removeObject, bool removeTool);
// apply transformations
bool translate(const std::vector<std::pair<int, int> > &inDimTags,
double dx, double dy, double dz);
bool rotate(const std::vector<std::pair<int, int> > &inDimTags,
double x, double y, double z, double ax, double ay, double az,
double angle);
// apply gtransformations
bool dilate(const std::vector<std::pair<int, int> > &inDimTags,
double a, double b, double c);
// copy and remove
bool copy(const std::vector<std::pair<int, int> > &inDimTags,
std::vector<std::pair<int, int> > &outDimTags);
bool remove(int dim, int tag, bool recursive=false);
bool remove(const std::vector<std::pair<int, int> > &dimTags, bool recursive=false);
// import shapes from file
bool importShapes(const std::string &fileName, bool highestDimOnly,
std::vector<std::pair<int, int> > &outDimTags,
const std::string &format="");
// import shapes from TopoDS_Shape
bool importShapes(const TopoDS_Shape *shape, bool highestDimOnly,
std::vector<std::pair<int, int> > &outDimTags);
// export all bound shapes to file
bool exportShapes(const std::string &fileName, const std::string &format="");
// set meshing constraints
void setMeshSize(int dim, int tag, double size);
// synchronize internal CAD data with the given GModel
void synchronize(GModel *model);
// queries
bool getVertex(int tag, double &x, double &y, double &z);
GVertex *getOCCVertexByNativePtr(GModel *model, TopoDS_Vertex toFind);
GEdge *getOCCEdgeByNativePtr(GModel *model, TopoDS_Edge toFind);
GFace *getOCCFaceByNativePtr(GModel *model, TopoDS_Face toFind);
GRegion *getOCCRegionByNativePtr(GModel *model, TopoDS_Solid toFind);
// *** FIXME what follows will be removed ***
private:
TopoDS_Shape _shape;
public:
void _addShapeToLists(TopoDS_Shape shape){ _addShapeToMaps(shape); }
void _healGeometry(double tolerance, bool fixdegenerated,
bool fixsmalledges, bool fixspotstripfaces, bool sewfaces,
bool makesolids=false, double scaling=0.0)
{
_healShape(_shape, tolerance, fixdegenerated, fixsmalledges,
fixspotstripfaces, sewfaces, makesolids, scaling);
}
void applyBooleanOperator(TopoDS_Shape tool, const BooleanOperator &op);
TopoDS_Shape getShape () { return _shape; }
void buildLists();
void buildShapeFromLists(TopoDS_Shape shape);
void fillet(std::vector<TopoDS_Edge> &shapes, double radius);
void buildShapeFromGModel(GModel*);
void buildGModel(GModel *gm);
void loadShape(const TopoDS_Shape *s)
{
std::vector<std::pair<int, int> > outDimTags;
importShapes(s, false, outDimTags);
}
GVertex *addVertexToModel(GModel *model, TopoDS_Vertex v);
GEdge *addEdgeToModel(GModel *model, TopoDS_Edge e);
GFace *addFaceToModel(GModel *model, TopoDS_Face f);
GRegion *addRegionToModel(GModel *model, TopoDS_Solid r);
// *** FIXME end of stuff that will be removed ***
};
#else
class OCC_Internals {
private:
bool _error(std::string what)
{
Msg::Error("Gmsh requires OpenCASCADE to %s", what.c_str());
return false;
}
public:
enum BooleanOperator { Union, Intersection, Difference, Section, Fragments };
OCC_Internals(){}
bool getChanged() const { return false; }
void reset(){}
void setMaxTag(int dim, int val){}
int getMaxTag(int dim) const { return 0; }
bool addVertex(int tag, double x, double y, double z, double meshSize=MAX_LC)
{
return _error("add vertex");
}
bool addLine(int tag, int startTag, int endTag)
{
return _error("add line");
}
bool addLine(int tag, const std::vector<int> &vertexTags)
{
return _error("add line");
}
bool addCircleArc(int tag, int startTag, int centerTag, int endTag)
{
return _error("add circle arc");
}
bool addCircle(int tag, double x, double y, double z, double r, double angle1,
double angle2)
{
return _error("add circle");
}
bool addEllipseArc(int tag, int startTag, int centerTag, int endTag)
{
return _error("add ellipse arc");
}
bool addEllipse(int tag, double x, double y, double z, double r1, double r2,
double angle1, double angle2)
{
return _error("add ellipse");
}
bool addBezier(int tag, const std::vector<int> &vertexTags)
{
return _error("add Bezier");
}
bool addBSpline(int tag, const std::vector<int> &vertexTags)
{
return _error("add BSpline");
}
bool addWire(int tag, const std::vector<int> &edgeTags, bool closed)
{
return _error("add wire");
}
bool addLineLoop(int tag, const std::vector<int> &edgeTags)
{
return _error("add line loop");
}
bool addRectangle(int tag, double x1, double y1, double z1,
double x2, double y2, double z2, double roundedRadius=0.)
{
return _error("add rectangle");
}
bool addDisk(int tag, double xc, double yc, double zc, double rx, double ry)
{
return _error("add disk");
}
bool addPlaneSurface(int tag, const std::vector<int> &wireTags)
{
return _error("add plane surface");
}
bool addSurfaceFilling(int tag, int wireTag)
{
return _error("add surface filling");
}
bool addSurfaceLoop(int tag, const std::vector<int> &faceTags)
{
return _error("add surface loop");
}
bool addVolume(int tag, const std::vector<int> &shellTags)
{
return _error("add volume");
}
bool addSphere(int tag, double xc, double yc, double zc, double radius,
double angle1, double angle2, double angle3)
{
return _error("add sphere");
}
bool addBlock(int tag, double x1, double y1, double z1,
double x2, double y2, double z2)
{
return _error("add block");
}
bool addCylinder(int tag, double x1, double y1, double z1, double x2, double y2,
double z2, double r, double angle)
{
return _error("add cylinder");
}
bool addCone(int tag, double x1, double y1, double z1, double x2, double y2,
double z2, double r1, double r2, double angle)
{
return _error("add cone");
}
bool addWedge(int tag, double x, double y, double z, double dx, double dy,
double dz, double ltx)
{ return _error("add wedge");
}
bool addTorus(int tag, double x, double y, double z, double r1, double r2,
double angle)
{
return _error("add torus");
}
bool addThruSections(int tag, const std::vector<int> &wireTags,
std::vector<std::pair<int, int> > &outDimTags,
bool makeSolid, bool makeRuled)
{
return _error("add thrusection");
}
bool addThickSolid(int tag, int solidTag, const std::vector<int> &excludeFaceTags,
double offset)
{
return _error("add thick solid");
}
bool extrude(const std::vector<std::pair<int, int> > &inDimTags,
double dx, double dy, double dz,
std::vector<std::pair<int, int> > &outDimTags,
ExtrudeParams *e=0)
{
return _error("extrude");
}
bool revolve(const std::vector<std::pair<int, int> > &inDimTags,
double x, double y, double z, double ax, double ay, double az,
double angle, std::vector<std::pair<int, int> > &outDimTags,
ExtrudeParams *e=0)
{
return _error("revolve");
}
bool addPipe(const std::vector<std::pair<int, int> > &inDimTags, int wireTag,
std::vector<std::pair<int, int> > &outDimTags)
{
return _error("add pipe");
}
bool fillet(const std::vector<int> ®ionTags, const std::vector<int> &edgeTags,
double radius, std::vector<std::pair<int, int> > &outDimTags)
{
return _error("create fillet");
}
bool applyBooleanOperator(int tag, BooleanOperator op,
const std::vector<std::pair<int, int> > &objectDimTags,
const std::vector<std::pair<int, int> > &toolDimTags,
std::vector<std::pair<int, int> > &outDimTags,
bool removeObject, bool removeTool)
{
return _error("apply boolean operator");
}
bool translate(const std::vector<std::pair<int, int> > &inDimTags,
double dx, double dy, double dz)
{
return _error("apply translation");
}
bool rotate(const std::vector<std::pair<int, int> > &inDimTags,
double x, double y, double z, double ax, double ay, double az,
double angle)
{
return _error("apply rotation");
}
bool copy(const std::vector<std::pair<int, int> > &inDimTags,
std::vector<std::pair<int, int> > &outDimTags)
{
return _error("copy shape");
}
bool remove(int dim, int tag, bool recursive=false)
{
return false;
}
bool remove(const std::vector<std::pair<int, int> > &dimTags, bool recursive=false)
{
return false;
}
bool importShapes(const std::string &fileName, bool highestDimOnly,
std::vector<std::pair<int, int> > &outDimTags,
const std::string &format="")
{
return _error("import shape");
}
bool exportShapes(const std::string &fileName, const std::string &format="")
{
return _error("export shape");
}
void setMeshSize(int dim, int tag, double size){}
void synchronize(GModel *model){}
bool getVertex(int tag, double &x, double &y, double &z){ return false; }
};
#endif
#endif