netgen/libsrc/meshing/meshclass.hpp

935 lines
28 KiB
C++
Raw Normal View History

2009-01-13 04:40:13 +05:00
#ifndef MESHCLASS
#define MESHCLASS
/**************************************************************************/
/* File: meshclass.hpp */
/* Author: Joachim Schoeberl */
/* Date: 20. Nov. 99 */
/**************************************************************************/
/*
The mesh class
*/
2011-03-03 01:50:39 +05:00
namespace netgen
{
enum resthtype { RESTRICTH_FACE, RESTRICTH_EDGE,
RESTRICTH_SURFACEELEMENT, RESTRICTH_POINT, RESTRICTH_SEGMENT };
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
class HPRefElement;
2019-08-09 12:02:50 +05:00
class CurvedElements;
class AnisotropicClusters;
class ParallelMeshTopology;
2011-03-03 01:50:39 +05:00
/// 2d/3d mesh
class Mesh
{
public:
typedef ::netgen::T_POINTS T_POINTS;
// typedef NgArray<Element, 0, size_t> T_VOLELEMENTS;
2019-07-09 13:39:16 +05:00
// typedef NgArray<Element2d, 0, SurfaceElementIndex> T_SURFELEMENTS;
// typedef NgArray<Element2d, 0, size_t> T_SURFELEMENTS;
2011-03-03 01:50:39 +05:00
private:
/// point coordinates
T_POINTS points;
// The communicator for this mesh. Just a dummy if compiled without MPI.
2019-02-12 19:01:34 +05:00
NgMPI_Comm comm;
2011-03-03 01:50:39 +05:00
/// line-segments at edges
2019-08-09 03:23:12 +05:00
Array<Segment> segments;
2011-03-03 01:50:39 +05:00
/// surface elements, 2d-inner elements
2019-08-18 16:10:58 +05:00
Array<Element2d, SurfaceElementIndex> surfelements;
2011-03-03 01:50:39 +05:00
/// volume elements
2019-08-09 03:23:12 +05:00
Array<Element> volelements;
2011-03-03 01:50:39 +05:00
/// points will be fixed forever
2019-08-09 03:23:12 +05:00
Array<PointIndex> lockedpoints;
2011-03-03 01:50:39 +05:00
/// surface indices at boundary nodes
// TABLE<int,PointIndex::BASE> surfacesonnode;
2011-03-03 01:50:39 +05:00
/// boundary edges (1..normal bedge, 2..segment)
2019-08-09 12:02:50 +05:00
unique_ptr<INDEX_2_CLOSED_HASHTABLE<int>> boundaryedges;
2011-03-03 01:50:39 +05:00
///
2019-08-09 12:02:50 +05:00
unique_ptr<INDEX_2_CLOSED_HASHTABLE<int>> segmentht;
2011-03-03 01:50:39 +05:00
///
2019-08-09 12:02:50 +05:00
unique_ptr<INDEX_3_CLOSED_HASHTABLE<int>> surfelementht;
2019-09-27 23:49:12 +05:00
unique_ptr<INDEX_3_CLOSED_HASHTABLE<int>> illegal_trigs;
2011-03-03 01:50:39 +05:00
/// faces of rest-solid
2019-07-09 13:39:16 +05:00
NgArray<Element2d> openelements;
2011-03-03 01:50:39 +05:00
/// open segmenets for surface meshing
2019-07-09 13:39:16 +05:00
NgArray<Segment> opensegments;
2011-03-03 01:50:39 +05:00
2019-10-04 15:25:14 +05:00
Array<int> tets_in_qualclass;
2011-03-03 01:50:39 +05:00
/**
Representation of local mesh-size h
*/
2019-08-09 12:02:50 +05:00
unique_ptr<LocalH> lochfunc;
2011-03-03 01:50:39 +05:00
///
double hglob;
///
double hmin;
///
2019-07-09 13:39:16 +05:00
NgArray<double> maxhdomain;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/**
the face-index of the surface element maps into
this table.
*/
2019-07-09 13:39:16 +05:00
NgArray<FaceDescriptor> facedecoding;
2009-01-13 04:40:13 +05:00
2009-09-22 13:12:00 +06:00
2011-03-03 01:50:39 +05:00
/**
the edge-index of the line element maps into
this table.
*/
2019-07-09 13:39:16 +05:00
NgArray<EdgeDescriptor> edgedecoding;
2009-09-22 13:12:00 +06:00
2011-03-03 01:50:39 +05:00
/// sub-domain materials
2019-07-09 13:39:16 +05:00
NgArray<string*> materials;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// labels for boundary conditions
2019-07-09 13:39:16 +05:00
NgArray<string*> bcnames;
2009-01-13 04:40:13 +05:00
2016-10-04 22:30:57 +05:00
/// labels for co dim 2 bboundary conditions
2019-07-09 13:39:16 +05:00
NgArray<string*> cd2names;
2016-10-04 22:30:57 +05:00
2018-08-06 20:09:03 +05:00
/// labels for co dim 3 bbboundary conditions
2019-07-09 13:39:16 +05:00
NgArray<string*> cd3names;
2018-08-06 20:09:03 +05:00
2011-03-03 01:50:39 +05:00
/// Periodic surface, close surface, etc. identifications
2019-08-09 12:02:50 +05:00
unique_ptr<Identifications> ident;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// number of vertices (if < 0, use np)
int numvertices;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// geometric search tree for interval intersection search
2019-08-09 12:02:50 +05:00
unique_ptr<BoxTree<3>> elementsearchtree;
2011-03-03 01:50:39 +05:00
/// time stamp for tree
2013-04-03 02:29:53 +06:00
mutable int elementsearchtreets;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// element -> face, element -> edge etc ...
MeshTopology topology;
2011-03-03 01:50:39 +05:00
/// methods for high order elements
2019-08-09 12:02:50 +05:00
unique_ptr<CurvedElements> curvedelems;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// nodes identified by close points
2019-08-09 12:02:50 +05:00
unique_ptr<AnisotropicClusters> clusters;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// space dimension (2 or 3)
int dimension;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// changed by every minor modification (addpoint, ...)
int timestamp;
/// changed after finishing global algorithm (improve, ...)
int majortimestamp;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// mesh access semaphors.
NgMutex mutex;
/// mesh access semaphors.
NgMutex majormutex;
2009-01-13 04:40:13 +05:00
2019-07-09 13:39:16 +05:00
SymbolTable< NgArray<int>* > userdata_int;
SymbolTable< NgArray<double>* > userdata_double;
2009-01-13 04:40:13 +05:00
2019-07-09 13:39:16 +05:00
mutable NgArray< Point3d > pointcurves;
mutable NgArray<int> pointcurves_startpoint;
mutable NgArray<double> pointcurves_red,pointcurves_green,pointcurves_blue;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// start element for point search (GetElementOfPoint)
mutable int ps_startelement;
2009-01-13 04:40:13 +05:00
#ifdef PARALLEL
2011-03-03 01:50:39 +05:00
/// connection to parallel meshes
2019-08-09 12:02:50 +05:00
unique_ptr<ParallelMeshTopology> paralleltop;
2009-01-13 04:40:13 +05:00
#endif
2015-08-08 22:10:48 +05:00
shared_ptr<NetgenGeometry> geometry;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
private:
void BuildBoundaryEdges(void);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
public:
bool PointContainedIn2DElement(const Point3d & p,
double lami[3],
const int element,
bool consider3D = false) const;
bool PointContainedIn3DElement(const Point3d & p,
double lami[3],
const int element) const;
bool PointContainedIn3DElementOld(const Point3d & p,
double lami[3],
const int element) const;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
public:
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
// store coarse mesh before hp-refinement
2019-08-09 12:02:50 +05:00
unique_ptr<NgArray<HPRefElement>> hpelements;
unique_ptr<Mesh> coarsemesh;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// number of refinement levels
// int mglevels;
// number of vertices on each refinement level:
NgArray<size_t> level_nv;
2011-03-03 01:50:39 +05:00
/// refinement hierarchy
2019-07-09 13:39:16 +05:00
NgArray<PointIndices<2>,PointIndex::BASE> mlbetweennodes;
2011-03-03 01:50:39 +05:00
/// parent element of volume element
2019-07-09 13:39:16 +05:00
NgArray<int> mlparentelement;
2011-03-03 01:50:39 +05:00
/// parent element of surface element
2019-07-09 13:39:16 +05:00
NgArray<int> mlparentsurfaceelement;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
DLL_HEADER Mesh();
2011-03-03 01:50:39 +05:00
///
DLL_HEADER ~Mesh();
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
Mesh & operator= (const Mesh & mesh2);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
2011-09-02 18:37:54 +06:00
DLL_HEADER void DeleteMesh();
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
void ClearSurfaceElements();
///
2016-12-12 00:17:07 +05:00
DLL_HEADER void ClearVolumeElements()
2011-03-03 01:50:39 +05:00
{
volelements.SetSize(0);
timestamp = NextTimeStamp();
}
///
2016-12-12 00:17:07 +05:00
DLL_HEADER void ClearSegments()
2011-03-03 01:50:39 +05:00
{
segments.SetSize(0);
timestamp = NextTimeStamp();
}
2016-12-12 00:17:07 +05:00
2011-03-03 01:50:39 +05:00
///
bool TestOk () const;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
void SetAllocSize(int nnodes, int nsegs, int nsel, int nel);
2016-12-12 00:17:07 +05:00
2009-01-13 04:40:13 +05:00
DLL_HEADER PointIndex AddPoint (const Point3d & p, int layer = 1);
DLL_HEADER PointIndex AddPoint (const Point3d & p, int layer, POINTTYPE type);
2013-04-03 02:29:53 +06:00
2019-01-31 22:41:20 +05:00
auto GetNP () const { return points.Size(); }
2009-01-13 04:40:13 +05:00
2016-12-11 16:12:05 +05:00
// [[deprecated("Use Point(PointIndex) instead of int !")]]
MeshPoint & Point(int i)
{
// return points.Elem(i);
return Point (PointIndex(i+PointIndex::BASE-1));
}
2011-03-03 01:50:39 +05:00
MeshPoint & Point(PointIndex pi) { return points[pi]; }
2016-12-11 16:12:05 +05:00
// [[deprecated("Use Point(PointIndex) instead of int !")]]
const MeshPoint & Point(int i) const
{
// return points.Get(i);
return Point (PointIndex(i+PointIndex::BASE-1));
}
2011-03-03 01:50:39 +05:00
const MeshPoint & Point(PointIndex pi) const { return points[pi]; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
const MeshPoint & operator[] (PointIndex pi) const { return points[pi]; }
MeshPoint & operator[] (PointIndex pi) { return points[pi]; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
const T_POINTS & Points() const { return points; }
T_POINTS & Points() { return points; }
2009-01-13 04:40:13 +05:00
DLL_HEADER SegmentIndex AddSegment (const Segment & s);
2011-03-03 01:50:39 +05:00
void DeleteSegment (int segnr)
{
2019-08-09 03:23:12 +05:00
segments[segnr-1][0].Invalidate();
segments[segnr-1][1].Invalidate();
2011-03-03 01:50:39 +05:00
}
2016-12-12 00:17:07 +05:00
/*
2011-03-03 01:50:39 +05:00
void FullDeleteSegment (int segnr) // von wem ist das ???
{
segments.Delete(segnr-PointIndex::BASE);
}
2016-12-12 00:17:07 +05:00
*/
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
int GetNSeg () const { return segments.Size(); }
2016-12-13 03:08:22 +05:00
// [[deprecated("Use LineSegment(SegmentIndex) instead of int !")]]
2019-08-09 03:23:12 +05:00
Segment & LineSegment(int i) { return segments[i-1]; }
2016-12-13 03:08:22 +05:00
// [[deprecated("Use LineSegment(SegmentIndex) instead of int !")]]
2019-08-09 03:23:12 +05:00
const Segment & LineSegment(int i) const { return segments[i-1]; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
Segment & LineSegment(SegmentIndex si) { return segments[si]; }
const Segment & LineSegment(SegmentIndex si) const { return segments[si]; }
const Segment & operator[] (SegmentIndex si) const { return segments[si]; }
Segment & operator[] (SegmentIndex si) { return segments[si]; }
2009-01-13 04:40:13 +05:00
2017-10-29 15:31:23 +05:00
const auto & LineSegments() const { return segments; }
auto & LineSegments() { return segments; }
2015-11-11 22:46:18 +05:00
2019-08-09 03:23:12 +05:00
Array<Element0d> pointelements; // only via python interface
2009-01-13 04:40:13 +05:00
DLL_HEADER SurfaceElementIndex AddSurfaceElement (const Element2d & el);
// write to pre-allocated container, thread-safe
DLL_HEADER void SetSurfaceElement (SurfaceElementIndex sei, const Element2d & el);
2016-12-12 00:17:07 +05:00
[[deprecated("Use Delete(SurfaceElementIndex) instead of int !")]]
2011-03-03 01:50:39 +05:00
void DeleteSurfaceElement (int eli)
{
/*
2011-03-03 01:50:39 +05:00
surfelements.Elem(eli).Delete();
2016-12-11 16:12:05 +05:00
surfelements.Elem(eli).PNum(1).Invalidate();
surfelements.Elem(eli).PNum(2).Invalidate();
surfelements.Elem(eli).PNum(3).Invalidate();
*/
surfelements[eli-1].Delete();
2019-08-09 03:23:12 +05:00
/*
surfelements[eli-1].PNum(1).Invalidate();
surfelements[eli-1].PNum(2).Invalidate();
surfelements[eli-1].PNum(3).Invalidate();
2019-08-09 03:23:12 +05:00
*/
2011-03-03 01:50:39 +05:00
timestamp = NextTimeStamp();
}
2009-01-13 04:40:13 +05:00
[[deprecated("Use Delete(SurfaceElementIndex) instead !")]]
2011-03-03 01:50:39 +05:00
void DeleteSurfaceElement (SurfaceElementIndex eli)
{
2019-08-09 03:23:12 +05:00
// for (auto & p : surfelements[eli].PNums()) p.Invalidate();
2016-12-12 00:17:07 +05:00
surfelements[eli].Delete();
timestamp = NextTimeStamp();
2011-03-03 01:50:39 +05:00
}
void Delete (SurfaceElementIndex eli)
{
2019-08-09 03:23:12 +05:00
// for (auto & p : surfelements[eli].PNums()) p.Invalidate();
surfelements[eli].Delete();
timestamp = NextTimeStamp();
}
2009-01-13 04:40:13 +05:00
2019-01-31 22:41:20 +05:00
auto GetNSE () const { return surfelements.Size(); }
2016-12-12 00:17:07 +05:00
2019-08-09 12:02:50 +05:00
// [[deprecated("Use SurfaceElement(SurfaceElementIndex) instead of int !")]]
Element2d & SurfaceElement(int i) { return surfelements[i-1]; }
2019-08-09 12:02:50 +05:00
// [[deprecated("Use SurfaceElement(SurfaceElementIndex) instead of int !")]]
const Element2d & SurfaceElement(int i) const { return surfelements[i-1]; }
2019-08-09 12:02:50 +05:00
// [[deprecated("Use mesh[](SurfaceElementIndex) instead !")]]
2011-03-03 01:50:39 +05:00
Element2d & SurfaceElement(SurfaceElementIndex i) { return surfelements[i]; }
2019-08-09 12:02:50 +05:00
// [[deprecated("Use mesh[](SurfaceElementIndex) instead !")]]
2011-03-03 01:50:39 +05:00
const Element2d & SurfaceElement(SurfaceElementIndex i) const { return surfelements[i]; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
const Element2d & operator[] (SurfaceElementIndex ei) const
{ return surfelements[ei]; }
Element2d & operator[] (SurfaceElementIndex ei)
{ return surfelements[ei]; }
2009-01-13 04:40:13 +05:00
const auto & SurfaceElements() const { return surfelements; }
auto & SurfaceElements() { return surfelements; }
2014-08-31 15:14:18 +06:00
2009-01-13 04:40:13 +05:00
DLL_HEADER void RebuildSurfaceElementLists ();
DLL_HEADER void GetSurfaceElementsOfFace (int facenr, Array<SurfaceElementIndex> & sei) const;
2009-01-13 04:40:13 +05:00
DLL_HEADER ElementIndex AddVolumeElement (const Element & el);
2018-01-04 22:45:07 +05:00
// write to pre-allocated container, thread-safe
DLL_HEADER void SetVolumeElement (ElementIndex sei, const Element & el);
2009-01-13 04:40:13 +05:00
2019-01-31 22:41:20 +05:00
auto GetNE () const { return volelements.Size(); }
2009-01-13 04:40:13 +05:00
2016-12-11 16:12:05 +05:00
// [[deprecated("Use VolumeElement(ElementIndex) instead of int !")]]
2019-08-09 03:23:12 +05:00
Element & VolumeElement(int i) { return volelements[i-1]; }
2016-12-11 16:12:05 +05:00
// [[deprecated("Use VolumeElement(ElementIndex) instead of int !")]]
2019-08-09 03:23:12 +05:00
const Element & VolumeElement(int i) const { return volelements[i-1]; }
2019-08-09 12:02:50 +05:00
// [[deprecated("Use mesh[](VolumeElementIndex) instead !")]]
2011-03-03 01:50:39 +05:00
Element & VolumeElement(ElementIndex i) { return volelements[i]; }
2019-08-09 12:02:50 +05:00
// [[deprecated("Use mesh[](VolumeElementIndex) instead !")]]
2011-03-03 01:50:39 +05:00
const Element & VolumeElement(ElementIndex i) const { return volelements[i]; }
2009-01-13 04:40:13 +05:00
const Element & operator[] (ElementIndex ei) const { return volelements[ei]; }
Element & operator[] (ElementIndex ei) { return volelements[ei]; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
ELEMENTTYPE ElementType (ElementIndex i) const
{ return (volelements[i].flags.fixed) ? FIXEDELEMENT : FREEELEMENT; }
2009-01-13 04:40:13 +05:00
2016-12-12 00:17:07 +05:00
const auto & VolumeElements() const { return volelements; }
auto & VolumeElements() { return volelements; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
2011-07-25 14:40:23 +06:00
DLL_HEADER double ElementError (int eli, const MeshingParameters & mp) const;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
DLL_HEADER void AddLockedPoint (PointIndex pi);
2011-03-03 01:50:39 +05:00
///
void ClearLockedPoints ();
2009-01-13 04:40:13 +05:00
2016-12-12 00:17:07 +05:00
const auto & LockedPoints() const { return lockedpoints; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// Returns number of domains
DLL_HEADER int GetNDomains() const;
2011-03-03 01:50:39 +05:00
///
2016-12-12 00:17:07 +05:00
int GetDimension() const { return dimension; }
void SetDimension (int dim) { dimension = dim; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// sets internal tables
DLL_HEADER void CalcSurfacesOfNode ();
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// additional (temporarily) fix points
2019-08-28 17:00:49 +05:00
void FixPoints (const NgBitArray & fixpoints);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/**
finds elements without neighbour and
boundary elements without inner element.
Results are stored in openelements.
if dom == 0, all sub-domains, else subdomain dom */
DLL_HEADER void FindOpenElements (int dom = 0);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/**
finds segments without surface element,
and surface elements without neighbours.
store in opensegmentsy
*/
DLL_HEADER void FindOpenSegments (int surfnr = 0);
2011-03-03 01:50:39 +05:00
/**
remove one layer of surface elements
*/
DLL_HEADER void RemoveOneLayerSurfaceElements ();
2011-03-03 01:50:39 +05:00
int GetNOpenSegments () { return opensegments.Size(); }
const Segment & GetOpenSegment (int nr) { return opensegments.Get(nr); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/**
Checks overlap of boundary
return == 1, iff overlap
*/
DLL_HEADER int CheckOverlappingBoundary ();
2011-03-03 01:50:39 +05:00
/**
Checks consistent boundary
return == 0, everything ok
*/
DLL_HEADER int CheckConsistentBoundary () const;
2011-03-03 01:50:39 +05:00
/*
checks element orientation
*/
DLL_HEADER int CheckVolumeMesh () const;
2011-03-03 01:50:39 +05:00
/**
finds average h of surface surfnr if surfnr > 0,
else of all surfaces.
*/
DLL_HEADER double AverageH (int surfnr = 0) const;
2011-03-03 01:50:39 +05:00
/// Calculates localh
2011-07-25 14:40:23 +06:00
DLL_HEADER void CalcLocalH (double grading);
2011-03-03 01:50:39 +05:00
///
2014-12-02 18:23:36 +05:00
DLL_HEADER void SetLocalH (netgen::Point<3> pmin, netgen::Point<3> pmax, double grading);
2011-03-03 01:50:39 +05:00
///
DLL_HEADER void RestrictLocalH (const Point3d & p, double hloc);
2011-03-03 01:50:39 +05:00
///
DLL_HEADER void RestrictLocalHLine (const Point3d & p1, const Point3d & p2,
2011-03-03 01:50:39 +05:00
double hloc);
/// number of elements per radius
2011-07-25 14:40:23 +06:00
DLL_HEADER void CalcLocalHFromSurfaceCurvature(double grading, double elperr);
2011-03-03 01:50:39 +05:00
///
2011-07-25 14:40:23 +06:00
DLL_HEADER void CalcLocalHFromPointDistances(double grading);
2011-03-03 01:50:39 +05:00
///
DLL_HEADER void RestrictLocalH (resthtype rht, int nr, double loch);
2011-03-03 01:50:39 +05:00
///
2014-08-31 18:12:31 +06:00
DLL_HEADER void LoadLocalMeshSize (const string & meshsizefilename);
2011-03-03 01:50:39 +05:00
///
DLL_HEADER void SetGlobalH (double h);
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void SetMinimalH (double h);
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER double MaxHDomain (int dom) const;
2011-03-03 01:50:39 +05:00
///
2019-07-09 13:39:16 +05:00
DLL_HEADER void SetMaxHDomain (const NgArray<double> & mhd);
2011-03-03 01:50:39 +05:00
///
DLL_HEADER double GetH (const Point3d & p) const;
2011-03-03 01:50:39 +05:00
///
double GetMinH (const Point3d & pmin, const Point3d & pmax);
///
2016-02-23 22:22:00 +05:00
bool HasLocalHFunction () { return lochfunc != nullptr; }
///
2011-03-03 01:50:39 +05:00
LocalH & LocalHFunction () { return * lochfunc; }
///
bool LocalHFunctionGenerated(void) const { return (lochfunc != NULL); }
/// Find bounding box
DLL_HEADER void GetBox (Point3d & pmin, Point3d & pmax, int dom = -1) const;
2011-03-03 01:50:39 +05:00
/// Find bounding box of points of typ ptyp or less
DLL_HEADER void GetBox (Point3d & pmin, Point3d & pmax, POINTTYPE ptyp ) const;
2011-03-03 01:50:39 +05:00
///
int GetNOpenElements() const
{ return openelements.Size(); }
///
const Element2d & OpenElement(int i) const
{ return openelements.Get(i); }
2019-02-03 10:20:52 +05:00
auto & OpenElements() const { return openelements; }
2011-03-03 01:50:39 +05:00
/// are also quads open elements
bool HasOpenQuads () const;
/// split into connected pieces
2015-10-19 13:08:30 +05:00
DLL_HEADER void SplitIntoParts ();
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void SplitSeparatedFaces ();
2011-03-03 01:50:39 +05:00
/// Refines mesh and projects points to true surface
// void Refine (int levels, const CSGeometry * geom);
2009-01-13 04:40:13 +05:00
2017-09-22 19:55:10 +05:00
2011-03-03 01:50:39 +05:00
bool BoundaryEdge (PointIndex pi1, PointIndex pi2) const
{
if(!boundaryedges)
const_cast<Mesh *>(this)->BuildBoundaryEdges();
INDEX_2 i2 (pi1, pi2);
i2.Sort();
return boundaryedges->Used (i2);
}
bool IsSegment (PointIndex pi1, PointIndex pi2) const
{
INDEX_2 i2 (pi1, pi2);
i2.Sort();
return segmentht->Used (i2);
}
SegmentIndex SegmentNr (PointIndex pi1, PointIndex pi2) const
{
INDEX_2 i2 (pi1, pi2);
i2.Sort();
return segmentht->Get (i2);
}
/**
Remove unused points. etc.
*/
DLL_HEADER void Compress ();
2011-03-03 01:50:39 +05:00
2016-05-13 15:06:12 +05:00
/// first vertex has lowest index
void OrderElements();
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void Save (ostream & outfile) const;
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void Load (istream & infile);
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void Merge (istream & infile, const int surfindex_offset = 0);
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void Save (const string & filename) const;
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void Load (const string & filename);
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void Merge (const string & filename, const int surfindex_offset = 0);
2011-03-03 01:50:39 +05:00
2018-11-29 22:35:30 +05:00
DLL_HEADER void DoArchive (Archive & archive);
2011-03-03 01:50:39 +05:00
///
2015-10-19 13:08:30 +05:00
DLL_HEADER void ImproveMesh (const MeshingParameters & mp, OPTIMIZEGOAL goal = OPT_QUALITY);
2019-09-04 21:00:47 +05:00
DLL_HEADER void ImproveMeshSequential (const MeshingParameters & mp, OPTIMIZEGOAL goal = OPT_QUALITY);
2011-03-03 01:50:39 +05:00
///
2019-08-28 17:00:49 +05:00
void ImproveMeshJacobian (const MeshingParameters & mp, OPTIMIZEGOAL goal = OPT_QUALITY, const NgBitArray * usepoint = NULL);
2011-03-03 01:50:39 +05:00
///
2011-07-25 17:33:19 +06:00
void ImproveMeshJacobianOnSurface (const MeshingParameters & mp,
2019-08-28 17:00:49 +05:00
const NgBitArray & usepoint,
2019-07-09 13:39:16 +05:00
const NgArray< Vec<3>* > & nv,
2011-03-03 01:50:39 +05:00
OPTIMIZEGOAL goal = OPT_QUALITY,
2019-07-09 13:39:16 +05:00
const NgArray< NgArray<int,PointIndex::BASE>* > * idmaps = NULL);
2011-03-03 01:50:39 +05:00
/**
free nodes in environment of openelements
for optimiztion
*/
void FreeOpenElementsEnvironment (int layers);
2019-10-04 15:25:14 +05:00
DLL_HEADER double CalcTotalBad (const MeshingParameters & mp);
FlatArray<int> GetQualityHistogram() { return tets_in_qualclass; }
2011-03-03 01:50:39 +05:00
///
bool LegalTet (Element & el) const
{
if (el.IllegalValid())
return !el.Illegal();
return LegalTet2 (el);
}
///
bool LegalTet2 (Element & el) const;
///
// Find trigs with same vertices
// return: number of illegal trigs
int FindIllegalTrigs ();
2011-03-03 01:50:39 +05:00
bool LegalTrig (const Element2d & el) const;
/**
if values non-null, return values in 4-double array:
triangle angles min/max, tetangles min/max
if null, output results on cout
*/
2015-10-19 13:08:30 +05:00
DLL_HEADER void CalcMinMaxAngle (double badellimit, double * retvalues = NULL);
2011-03-03 01:50:39 +05:00
/*
Marks elements which are dangerous to refine
return: number of illegal elements
*/
2015-10-19 13:08:30 +05:00
DLL_HEADER int MarkIllegalElements ();
2011-03-03 01:50:39 +05:00
/// orient surface mesh, for one sub-domain only
2015-10-19 13:08:30 +05:00
DLL_HEADER void SurfaceMeshOrientation ();
2011-03-03 01:50:39 +05:00
/// convert mixed element mesh to tet-mesh
2015-10-19 13:08:30 +05:00
DLL_HEADER void Split2Tets();
2011-03-03 01:50:39 +05:00
/// build box-search tree
2011-09-02 18:37:54 +06:00
DLL_HEADER void BuildElementSearchTree ();
2011-03-03 01:50:39 +05:00
void SetPointSearchStartElement(const int el) const {ps_startelement = el;}
/// gives element of point, barycentric coordinates
2013-04-03 02:29:53 +06:00
int GetElementOfPoint (const netgen::Point<3> & p,
2011-03-03 01:50:39 +05:00
double * lami,
bool build_searchtree = 0,
const int index = -1,
const bool allowindex = true) const;
2013-04-03 02:29:53 +06:00
int GetElementOfPoint (const netgen::Point<3> & p,
2011-03-03 01:50:39 +05:00
double * lami,
2019-07-09 13:39:16 +05:00
const NgArray<int> * const indices,
2011-03-03 01:50:39 +05:00
bool build_searchtree = 0,
const bool allowindex = true) const;
2013-04-03 02:29:53 +06:00
int GetSurfaceElementOfPoint (const netgen::Point<3> & p,
2011-03-03 01:50:39 +05:00
double * lami,
bool build_searchtree = 0,
const int index = -1,
const bool allowindex = true) const;
2013-04-03 02:29:53 +06:00
int GetSurfaceElementOfPoint (const netgen::Point<3> & p,
2011-03-03 01:50:39 +05:00
double * lami,
2019-07-09 13:39:16 +05:00
const NgArray<int> * const indices,
2011-03-03 01:50:39 +05:00
bool build_searchtree = 0,
const bool allowindex = true) const;
/// give list of vol elements which are int the box(p1,p2)
void GetIntersectingVolEls(const Point3d& p1, const Point3d& p2,
2019-07-09 13:39:16 +05:00
NgArray<int> & locels) const;
2011-03-03 01:50:39 +05:00
///
int AddFaceDescriptor(const FaceDescriptor& fd)
{ facedecoding.Append(fd); return facedecoding.Size(); }
2011-03-03 01:50:39 +05:00
int AddEdgeDescriptor(const EdgeDescriptor & fd)
{ edgedecoding.Append(fd); return edgedecoding.Size() - 1; }
2011-03-03 01:50:39 +05:00
2019-02-12 01:38:05 +05:00
auto GetCommunicator() const { return this->comm; }
void SetCommunicator(NgMPI_Comm acomm);
2011-03-03 01:50:39 +05:00
///
2016-02-27 00:30:40 +05:00
DLL_HEADER void SetMaterial (int domnr, const string & mat);
2011-03-03 01:50:39 +05:00
///
2017-07-19 22:18:04 +05:00
DLL_HEADER const string & GetMaterial (int domnr) const;
DLL_HEADER static string defaultmat;
2016-02-27 00:30:40 +05:00
const string * GetMaterialPtr (int domnr) const // 1-based
2017-05-13 13:24:12 +05:00
{
return domnr <= materials.Size() ? materials.Get(domnr) : &defaultmat;
}
2009-01-13 04:40:13 +05:00
DLL_HEADER void SetNBCNames ( int nbcn );
2009-01-13 04:40:13 +05:00
DLL_HEADER void SetBCName ( int bcnr, const string & abcname );
2009-01-13 04:40:13 +05:00
2017-07-19 22:18:04 +05:00
DLL_HEADER const string & GetBCName ( int bcnr ) const;
2016-10-04 22:30:57 +05:00
DLL_HEADER void SetNCD2Names (int ncd2n);
DLL_HEADER void SetCD2Name (int cd2nr, const string & abcname);
2017-07-19 22:18:04 +05:00
DLL_HEADER const string & GetCD2Name (int cd2nr ) const;
DLL_HEADER static string cd2_default_name;
2017-04-03 21:15:34 +05:00
string * GetCD2NamePtr (int cd2nr ) const
{
if (cd2nr < cd2names.Size() && cd2names[cd2nr]) return cd2names[cd2nr];
return &cd2_default_name;
}
2016-10-28 19:49:50 +05:00
size_t GetNCD2Names() const { return cd2names.Size(); }
2009-01-13 04:40:13 +05:00
2018-08-06 20:09:03 +05:00
DLL_HEADER void SetNCD3Names (int ncd3n);
DLL_HEADER void SetCD3Name (int cd3nr, const string & abcname);
DLL_HEADER const string & GetCD3Name (int cd3nr ) const;
DLL_HEADER static string cd3_default_name;
string * GetCD3NamePtr (int cd3nr ) const
{
if (cd3nr < cd3names.Size() && cd3names[cd3nr]) return cd3names[cd3nr];
return &cd3_default_name;
}
size_t GetNCD3Names() const { return cd3names.Size(); }
DLL_HEADER static string default_bc;
2016-02-27 00:30:40 +05:00
string * GetBCNamePtr (int bcnr) const
{ return (bcnr < bcnames.Size() && bcnames[bcnr]) ? bcnames[bcnr] : &default_bc; }
2009-01-13 04:40:13 +05:00
2019-10-06 02:02:32 +05:00
NgArray<string*> & GetRegionNamesCD (int codim);
2011-03-03 01:50:39 +05:00
///
void ClearFaceDescriptors()
{ facedecoding.SetSize(0); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
int GetNFD () const
{ return facedecoding.Size(); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
const FaceDescriptor & GetFaceDescriptor (int i) const
{ return facedecoding.Get(i); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
const EdgeDescriptor & GetEdgeDescriptor (int i) const
{ return edgedecoding[i]; }
2009-09-22 13:12:00 +06:00
2011-03-03 01:50:39 +05:00
///
FaceDescriptor & GetFaceDescriptor (int i)
{ return facedecoding.Elem(i); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
// #ifdef NONE
// /*
// Identify points pi1 and pi2, due to
// identification nr identnr
// */
// void AddIdentification (int pi1, int pi2, int identnr);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
// int GetIdentification (int pi1, int pi2) const;
// int GetIdentificationSym (int pi1, int pi2) const;
// ///
// INDEX_2_HASHTABLE<int> & GetIdentifiedPoints ()
// {
// return *identifiedpoints;
// }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
// ///
2019-07-09 13:39:16 +05:00
// void GetIdentificationMap (int identnr, NgArray<int> & identmap) const;
2011-03-03 01:50:39 +05:00
// ///
2019-07-09 13:39:16 +05:00
// void GetIdentificationPairs (int identnr, NgArray<INDEX_2> & identpairs) const;
2011-03-03 01:50:39 +05:00
// ///
// int GetMaxIdentificationNr () const
// {
// return maxidentnr;
// }
// #endif
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// return periodic, close surface etc. identifications
Identifications & GetIdentifications () { return *ident; }
/// return periodic, close surface etc. identifications
const Identifications & GetIdentifications () const { return *ident; }
2016-02-23 22:22:00 +05:00
///
bool HasIdentifications() const { return ident != nullptr; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
void InitPointCurve(double red = 1, double green = 0, double blue = 0) const;
void AddPointCurvePoint(const Point3d & pt) const;
int GetNumPointCurves(void) const;
int GetNumPointsOfPointCurve(int curve) const;
Point3d & GetPointCurvePoint(int curve, int n) const;
void GetPointCurveColor(int curve, double & red, double & green, double & blue) const;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// find number of vertices
void ComputeNVertices ();
/// number of vertices (no edge-midpoints)
int GetNV () const;
/// remove edge points
void SetNP (int np);
2009-01-13 04:40:13 +05:00
Table<ElementIndex, PointIndex> CreatePoint2ElementTable() const;
Table<SurfaceElementIndex, PointIndex> CreatePoint2SurfaceElementTable() const;
2009-01-13 04:40:13 +05:00
2016-01-07 17:37:48 +05:00
DLL_HEADER bool PureTrigMesh (int faceindex = 0) const;
DLL_HEADER bool PureTetMesh () const;
2009-01-13 04:40:13 +05:00
2016-01-07 17:37:48 +05:00
const MeshTopology & GetTopology () const
{ return topology; }
2009-01-13 04:40:13 +05:00
2018-01-04 15:48:45 +05:00
DLL_HEADER void UpdateTopology (TaskManager tm = &DummyTaskManager,
Tracer tracer = &DummyTracer);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
class CurvedElements & GetCurvedElements () const
{ return *curvedelems; }
2016-01-07 17:37:48 +05:00
DLL_HEADER void BuildCurvedElements (const class Refinement * ref, int aorder, bool arational = false);
2018-05-02 00:20:54 +05:00
DLL_HEADER void BuildCurvedElements (int aorder);
2015-04-27 14:18:22 +05:00
2011-03-03 01:50:39 +05:00
const class AnisotropicClusters & GetClusters () const
{ return *clusters; }
2009-01-13 04:40:13 +05:00
2012-10-22 19:13:57 +06:00
class CSurfaceArea
{
const Mesh & mesh;
bool valid;
double area;
public:
CSurfaceArea (const Mesh & amesh)
: mesh(amesh), valid(false) { ; }
void Add (const Element2d & sel)
{
if (sel.GetNP() == 3)
area += Cross ( mesh[sel[1]]-mesh[sel[0]],
mesh[sel[2]]-mesh[sel[0]] ).Length() / 2;
else
2014-12-02 18:23:36 +05:00
area += Cross (Vec3d (mesh[sel.PNum(1)], mesh[sel.PNum(3)]),
Vec3d (mesh[sel.PNum(1)], mesh[sel.PNum(4)])).Length() / 2;;
2012-10-22 19:13:57 +06:00
}
void ReCalc ()
{
area = 0;
2019-08-18 16:10:58 +05:00
/*
2012-10-22 19:13:57 +06:00
for (SurfaceElementIndex sei = 0; sei < mesh.GetNSE(); sei++)
Add (mesh[sei]);
2019-08-18 16:10:58 +05:00
*/
for (const Element2d & el : mesh.SurfaceElements())
Add (el);
2012-10-22 19:13:57 +06:00
valid = true;
}
operator double () const { return area; }
bool Valid() const { return valid; }
};
CSurfaceArea surfarea;
CSurfaceArea & SurfaceArea() { return surfarea; }
const CSurfaceArea & SurfaceArea() const { return surfarea; }
2011-03-03 01:50:39 +05:00
int GetTimeStamp() const { return timestamp; }
void SetNextTimeStamp()
{ timestamp = NextTimeStamp(); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
int GetMajorTimeStamp() const { return majortimestamp; }
void SetNextMajorTimeStamp()
{ majortimestamp = timestamp = NextTimeStamp(); }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// return mutex
NgMutex & Mutex () { return mutex; }
NgMutex & MajorMutex () { return majormutex; }
2009-01-13 04:40:13 +05:00
2015-08-08 22:10:48 +05:00
shared_ptr<NetgenGeometry> GetGeometry() const
{
static auto global_geometry = make_shared<NetgenGeometry>();
return geometry ? geometry : global_geometry;
2015-08-08 22:10:48 +05:00
}
void SetGeometry (shared_ptr<NetgenGeometry> geom)
{
geometry = geom;
}
2011-03-03 01:50:39 +05:00
///
2019-07-09 13:39:16 +05:00
void SetUserData(const char * id, NgArray<int> & data);
2011-03-03 01:50:39 +05:00
///
2019-07-09 13:39:16 +05:00
bool GetUserData(const char * id, NgArray<int> & data, int shift = 0) const;
2011-03-03 01:50:39 +05:00
///
2019-07-09 13:39:16 +05:00
void SetUserData(const char * id, NgArray<double> & data);
2011-03-03 01:50:39 +05:00
///
2019-07-09 13:39:16 +05:00
bool GetUserData(const char * id, NgArray<double> & data, int shift = 0) const;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
///
friend void OptimizeRestart (Mesh & mesh3d);
///
void PrintMemInfo (ostream & ost) const;
///
friend class Meshing3;
2009-01-13 04:40:13 +05:00
2019-10-02 20:20:13 +05:00
// only for saving the geometry
2011-03-03 01:50:39 +05:00
enum GEOM_TYPE { NO_GEOM = 0, GEOM_2D = 1, GEOM_CSG = 10, GEOM_STL = 11, GEOM_OCC = 12, GEOM_ACIS = 13 };
GEOM_TYPE geomtype;
2009-01-13 04:40:13 +05:00
#ifdef PARALLEL
2011-03-03 01:50:39 +05:00
/// returns parallel topology
class ParallelMeshTopology & GetParallelTopology () const
{ return *paralleltop; }
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// distributes the master-mesh to local meshes
void Distribute ();
2019-07-09 13:39:16 +05:00
void Distribute (NgArray<int> & volume_weights, NgArray<int> & surface_weights,
NgArray<int> & segment_weights);
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// find connection to parallel meshes
// void FindExchangePoints () ;
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
// void FindExchangeEdges ();
// void FindExchangeFaces ();
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
/// use metis to decompose master mesh
2019-07-09 13:39:16 +05:00
void ParallelMetis (); // NgArray<int> & neloc );
void ParallelMetis (NgArray<int> & volume_weights, NgArray<int> & surface_weights,
NgArray<int> & segment_weights);
2012-10-17 16:31:43 +06:00
2019-07-09 13:39:16 +05:00
void PartHybridMesh (); // NgArray<int> & neloc );
void PartDualHybridMesh (); // NgArray<int> & neloc );
void PartDualHybridMesh2D (); // ( NgArray<int> & neloc );
2009-01-13 04:40:13 +05:00
2011-07-04 18:29:02 +06:00
/// send mesh from master to local procs
void SendRecvMesh ();
2011-03-03 01:50:39 +05:00
/// send mesh to parallel machine, keep global mesh at master
2019-07-09 13:39:16 +05:00
void SendMesh ( ) const; // Mesh * mastermesh, NgArray<int> & neloc) const;
2011-07-04 18:29:02 +06:00
/// loads a mesh sent from master processor
void ReceiveParallelMesh ();
2019-07-09 13:39:16 +05:00
NgArray<int> vol_partition;
NgArray<int> surf_partition;
NgArray<int> seg_partition;
#else
void Distribute () {}
void SendRecvMesh () {}
2019-07-09 13:39:16 +05:00
void Distribute (NgArray<int> & volume_weights, NgArray<int> & surface_weights,
NgArray<int> & segment_weights){ }
2009-01-13 04:40:13 +05:00
#endif
2011-03-03 01:50:39 +05:00
};
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
inline ostream& operator<<(ostream& ost, const Mesh& mesh)
{
ost << "mesh: " << endl;
mesh.Save(ost);
return ost;
}
2009-01-13 04:40:13 +05:00
2011-03-03 01:50:39 +05:00
}
2009-01-13 04:40:13 +05:00
#endif