netgen/libsrc/meshing/basegeom.cpp

218 lines
5.9 KiB
C++
Raw Normal View History

2010-03-23 17:52:07 +05:00
#include <mystdlib.h>
#include "meshing.hpp"
namespace netgen
{
2013-02-06 18:55:20 +06:00
DLL_HEADER GeometryRegisterArray geometryregister;
2019-07-09 13:39:16 +05:00
//DLL_HEADER NgArray<GeometryRegister*> geometryregister;
2011-01-11 01:18:01 +05:00
GeometryRegister :: ~GeometryRegister()
{ ; }
2019-10-24 16:17:00 +05:00
void NetgenGeometry :: Analyse(Mesh& mesh,
2019-10-28 18:41:31 +05:00
const MeshingParameters& mparam) const
2019-10-24 16:17:00 +05:00
{
static Timer t1("SetLocalMeshsize"); RegionTimer regt(t1);
mesh.SetGlobalH(mparam.maxh);
mesh.SetMinimalH(mparam.minh);
mesh.SetLocalH(bounding_box.PMin(), bounding_box.PMax(),
mparam.grading);
if(mparam.uselocalh)
RestrictLocalMeshsize(mesh, mparam);
2019-10-24 16:17:00 +05:00
mesh.LoadLocalMeshSize(mparam.meshsizefilename);
}
2019-10-28 18:41:31 +05:00
void NetgenGeometry :: FindEdges(Mesh& mesh,
const MeshingParameters& mparam) const
{
}
void NetgenGeometry :: MeshSurface(Mesh& mesh,
const MeshingParameters& mparam) const
{
static Timer t1("Surface Meshing"); RegionTimer regt(t1);
Array<int, PointIndex> glob2loc(mesh.GetNP());
for(auto k : Range(faces))
{
const auto& face = *faces[k];
auto bb = face.GetBoundingBox();
bb.Increase(bb.Diam()/10);
Meshing2 meshing(*this, mparam, bb);
glob2loc = 0;
int cntp = 0;
for(auto& seg : mesh.LineSegments())
{
if(seg.si == k+1)
{
for(auto j : Range(2))
{
auto pi = seg[j];
if(glob2loc[pi] == 0)
{
meshing.AddPoint(mesh[pi], pi);
cntp++;
glob2loc[pi] = cntp;
}
}
}
}
for(auto & seg : mesh.LineSegments())
{
if(seg.si == k+1)
{
PointGeomInfo gi0, gi1;
gi0.trignum = gi1.trignum = k+1;
gi0.u = seg.epgeominfo[0].u;
gi0.v = seg.epgeominfo[0].v;
gi1.u = seg.epgeominfo[1].u;
gi1.v = seg.epgeominfo[1].v;
meshing.AddBoundaryElement(glob2loc[seg[0]],
glob2loc[seg[1]],
gi0, gi1);
}
}
// TODO Set max area 2* area of face
auto noldsurfels = mesh.GetNSE();
static Timer t("GenerateMesh"); RegionTimer reg(t);
MESHING2_RESULT res = meshing.GenerateMesh(mesh, mparam, mparam.maxh, k+1);
for(auto i : Range(noldsurfels, mesh.GetNSE()))
{
mesh.SurfaceElements()[i].SetIndex(k+1);
}
}
}
void NetgenGeometry :: OptimizeSurface(Mesh& mesh, const MeshingParameters& mparam) const
{
const auto savetask = multithread.task;
multithread.task = "Optimizing surface";
static Timer timer_opt2d("Optimization 2D");
RegionTimer reg(timer_opt2d);
auto meshopt = MeshOptimize2d(mesh);
for(auto i : Range(mparam.optsteps2d))
{
PrintMessage(2, "Optimization step ", i);
for(auto optstep : mparam.optimize2d)
{
switch(optstep)
{
case 's':
meshopt.EdgeSwapping(0);
break;
case 'S':
meshopt.EdgeSwapping(1);
break;
case 'm':
meshopt.ImproveMesh(mparam);
break;
case 'c':
meshopt.CombineImprove();
break;
}
}
}
mesh.CalcSurfacesOfNode();
mesh.Compress();
multithread.task = savetask;
}
shared_ptr<NetgenGeometry> GeometryRegisterArray :: LoadFromMeshFile (istream & ist) const
{
for (int i = 0; i < Size(); i++)
{
NetgenGeometry * hgeom = (*this)[i]->LoadFromMeshFile (ist);
if (hgeom)
return shared_ptr<NetgenGeometry>(hgeom);
}
return nullptr;
}
2011-01-11 01:18:01 +05:00
2010-03-23 17:52:07 +05:00
int NetgenGeometry :: GenerateMesh (shared_ptr<Mesh> & mesh, MeshingParameters & mparam)
2010-03-23 17:52:07 +05:00
{
2019-10-02 20:20:13 +05:00
multithread.percent = 0;
2010-03-23 17:52:07 +05:00
2019-10-02 20:20:13 +05:00
if(mparam.perfstepsstart <= MESHCONST_ANALYSE)
2010-03-23 17:52:07 +05:00
{
2019-10-02 20:20:13 +05:00
if(!mesh)
mesh = make_shared<Mesh>();
mesh->geomtype = GetGeomType();
Analyse(*mesh, mparam);
}
2010-03-23 17:52:07 +05:00
2019-10-02 20:20:13 +05:00
if(multithread.terminate || mparam.perfstepsend <= MESHCONST_ANALYSE)
return 0;
if(mparam.perfstepsstart <= MESHCONST_MESHEDGES)
FindEdges(*mesh, mparam);
if(multithread.terminate || mparam.perfstepsend <= MESHCONST_MESHEDGES)
return 0;
if (mparam.perfstepsstart <= MESHCONST_MESHSURFACE)
{
MeshSurface(*mesh, mparam);
mesh->CalcSurfacesOfNode();
2010-03-23 17:52:07 +05:00
}
2019-10-02 20:20:13 +05:00
if (multithread.terminate || mparam.perfstepsend <= MESHCONST_MESHSURFACE)
return 0;
2019-10-02 20:20:13 +05:00
if (mparam.perfstepsstart <= MESHCONST_OPTSURFACE)
OptimizeSurface(*mesh, mparam);
if (multithread.terminate || mparam.perfstepsend <= MESHCONST_OPTSURFACE)
return 0;
2010-03-23 17:52:07 +05:00
2019-10-02 20:20:13 +05:00
if(mparam.perfstepsstart <= MESHCONST_MESHVOLUME)
{
multithread.task = "Volume meshing";
MESHING3_RESULT res = MeshVolume (mparam, *mesh);
if (res != MESHING3_OK) return 1;
if (multithread.terminate) return 0;
RemoveIllegalElements (*mesh);
if (multithread.terminate) return 0;
MeshQuality3d (*mesh);
}
if (multithread.terminate || mparam.perfstepsend <= MESHCONST_MESHVOLUME)
2010-03-23 17:52:07 +05:00
return 0;
2010-03-23 17:52:07 +05:00
if (mparam.perfstepsstart <= MESHCONST_OPTVOLUME)
2010-03-23 17:52:07 +05:00
{
multithread.task = "Volume optimization";
2010-03-23 17:52:07 +05:00
OptimizeVolume (mparam, *mesh);
if (multithread.terminate) return 0;
}
2019-10-02 20:20:13 +05:00
FinalizeMesh(*mesh);
2010-03-23 17:52:07 +05:00
return 0;
2019-10-02 20:20:13 +05:00
}
2010-03-23 17:52:07 +05:00
2011-01-11 01:18:01 +05:00
void NetgenGeometry :: Save (string filename) const
{
throw NgException("Cannot save geometry - no geometry available");
}
2018-12-14 16:01:58 +05:00
static RegisterClassForArchive<NetgenGeometry> regnggeo;
2010-03-23 17:52:07 +05:00
}