51 namespace NekMeshUtils
56 "Generates a high-order surface mesh based on CAD");
61 ConfigOption(
true,
"0",
"Perform edge node optimisation.");
71 cout << endl <<
"\tHigh-Order Surface meshing" << endl;
84 int nq =
m_mesh->m_nummode;
86 int np = nq * (nq + 1) / 2;
88 int ni = (nq - 2) * (nq - 3) / 2;
92 int niq = npq - 4 - 4 * (nq - 2);
96 bool qOpti =
m_config[
"opti"].beenSet;
104 for (
int i = 0; i <
m_mesh->m_element[2].size(); i++)
106 vector<EdgeSharedPtr> es =
m_mesh->m_element[2][i]->GetEdgeList();
107 for (
int j = 0; j < es.size(); j++)
108 surfaceEdges.insert(es[j]);
111 for (
int i = 0; i <
m_mesh->m_element[2].size(); i++)
116 "\t\tSurface elements");
119 if (!
m_mesh->m_element[2][i]->m_parentCAD)
127 int surf = s->
GetId();
131 bool dumFace =
false;
140 f = std::shared_ptr<Face>(
new Face(
141 m_mesh->m_element[2][i]->GetVertexList(),
142 vector<NodeSharedPtr>(),
m_mesh->m_element[2][i]->GetEdgeList(),
150 vector<EdgeSharedPtr> edges = f->m_edgeList;
151 for (
int j = 0; j < edges.size(); j++)
158 EdgeSet::iterator test = completedEdges.find(e);
160 if (test != completedEdges.end())
170 EdgeSet::iterator it = surfaceEdges.find(e);
172 "could not find edge in surface");
174 if ((*it)->m_parentCAD)
176 e->m_parentCAD = (*it)->m_parentCAD;
183 vector<NodeSharedPtr> honodes(
m_mesh->m_nummode - 2);
187 int cid = e->m_parentCAD->GetId();
189 std::dynamic_pointer_cast<
CADCurve>(e->m_parentCAD);
190 NekDouble tb = e->m_n1->GetCADCurveInfo(cid);
191 NekDouble te = e->m_n2->GetCADCurveInfo(cid);
195 for (
int k = 0; k <
m_mesh->m_nummode; k++)
198 tb * (1.0 - gll[k]) / 2.0 + te * (1.0 + gll[k]) / 2.0;
204 for (
int k = 1; k < nq - 1; k++)
214 for (
int k = 0; k < nq - 2; k++)
220 for (
int k = 0; k < nq - 2; k++)
234 for (
int k = 0; k < nq - 2; k++)
236 Norm += J(k, 0) * J(k, 0) / (bnds[1] - bnds[0]) /
248 cout <<
"failed to optimise on curve" << endl;
249 for (
int k = 0; k < nq; k++)
251 ti[k] = tb * (1.0 - gll[k]) / 2.0 +
252 te * (1.0 + gll[k]) / 2.0;
262 cout <<
"BFGS reported no update, curve on " 263 << c->GetId() << endl;
269 ti = opti->GetSolution();
271 vector<pair<CADSurfSharedPtr, CADOrientation::Orientation>> s =
274 for (
int k = 1; k <
m_mesh->m_nummode - 1; k++)
278 new Node(0, loc[0], loc[1], loc[2]));
280 nn->SetCADCurve(c, ti[k]);
281 for (
int m = 0; m < s.size(); m++)
284 nn->SetCADSurf(s[m].first, uv);
294 uvb = e->m_n1->GetCADSurfInfo(surf);
295 uve = e->m_n2->GetCADSurfInfo(surf);
303 for (
int k = 0; k < nq; k++)
306 uv[0] = uvb[0] * (1.0 - gll[k]) / 2.0 +
307 uve[0] * (1.0 + gll[k]) / 2.0;
308 uv[1] = uvb[1] * (1.0 - gll[k]) / 2.0 +
309 uve[1] * (1.0 + gll[k]) / 2.0;
317 for (
int k = 0; k < nq; k++)
319 all[k * 2 + 0] = uvi[k][0];
320 all[k * 2 + 1] = uvi[k][1];
324 for (
int k = 1; k < nq - 1; k++)
326 xi[(k - 1) * 2 + 0] = all[k * 2 + 0];
327 xi[(k - 1) * 2 + 1] = all[k * 2 + 1];
333 DNekMat B(2 * (nq - 2), 2 * (nq - 2),
335 for (
int k = 0; k < 2 * (nq - 2); k++)
339 DNekMat H(2 * (nq - 2), 2 * (nq - 2),
341 for (
int k = 0; k < 2 * (nq - 2); k++)
353 for (
int k = 0; k < 2 * (nq - 2); k++)
378 cout <<
"failed to optimise on edge " << Norm
380 for (
int k = 0; k < nq; k++)
383 uv[0] = uvb[0] * (1.0 - gll[k]) / 2.0 +
384 uve[0] * (1.0 + gll[k]) / 2.0;
385 uv[1] = uvb[1] * (1.0 - gll[k]) / 2.0 +
386 uve[1] * (1.0 + gll[k]) / 2.0;
397 cout <<
"BFGS reported no update, edge on " 405 all = opti->GetSolution();
408 for (
int k = 0; k < nq; k++)
410 uvi[k][0] = all[k * 2 + 0];
411 uvi[k][1] = all[k * 2 + 1];
415 for (
int k = 1; k < nq - 1; k++)
419 new Node(0, loc[0], loc[1], loc[2]));
420 nn->SetCADSurf(s, uvi[k]);
425 e->m_edgeNodes = honodes;
427 completedEdges.insert(e);
431 vector<NodeSharedPtr> vertices = f->m_vertexList;
444 xmap->BwdTrans(coeffs0,xc);
445 xmap->BwdTrans(coeffs1,yc);
446 xmap->BwdTrans(coeffs2,zc);
448 if(vertices.size() == 3)
451 vector<Array<OneD, NekDouble> > uvi;
452 for(
int j = np-ni; j < np; j++)
459 loc[0] = xmap->PhysEvaluate(xp, xc);
460 loc[1] = xmap->PhysEvaluate(xp, yc);
461 loc[2] = xmap->PhysEvaluate(xp, zc);
467 vector<NodeSharedPtr> honodes;
468 for(
int j = 0; j < ni; j++)
473 Node(0,loc[0],loc[1],loc[2]));
474 nn->SetCADSurf(s, uvi[j]);
475 honodes.push_back(nn);
478 f->m_faceNodes = honodes;
481 else if(vertices.size() == 4)
484 vector<Array<OneD, NekDouble> > uvi;
485 for(
int i = 1; i < nq - 1; i++)
487 for(
int j = 1; j < nq - 1; j++)
494 loc[0] = xmap->PhysEvaluate(xp, xc);
495 loc[1] = xmap->PhysEvaluate(xp, yc);
496 loc[2] = xmap->PhysEvaluate(xp, zc);
503 vector<NodeSharedPtr> honodes;
504 for(
int j = 0; j < niq; j++)
509 Node(0,loc[0],loc[1],loc[2]));
510 nn->SetCADSurf(s, uvi[j]);
511 honodes.push_back(nn);
514 f->m_faceNodes = honodes;
520 m_mesh->m_element[2][i]->SetVolumeNodes(f->m_faceNodes);
521 m_mesh->m_element[2][i]->SetCurveType(f->m_curveType);
std::shared_ptr< CADSurf > CADSurfSharedPtr
#define ASSERTL0(condition, msg)
base class for CAD curves.
int PrintProgressbar(const int position, const int goal, const std::string message, int lastprogress=-1)
Prints a progressbar.
std::shared_ptr< OptiEdge > OptiEdgeSharedPtr
std::unordered_set< EdgeSharedPtr, EdgeHash > EdgeSet
int GetId()
Return ID of the CAD object.
Represents a face comprised of three or more edges.
MeshSharedPtr m_mesh
Mesh object.
std::shared_ptr< Edge > EdgeSharedPtr
Shared pointer to an edge.
std::shared_ptr< Mesh > MeshSharedPtr
Shared pointer to a mesh.
std::shared_ptr< Node > NodeSharedPtr
std::shared_ptr< Face > FaceSharedPtr
1D Evenly-spaced points using Lagrange polynomial
std::shared_ptr< StdExpansion > StdExpansionSharedPtr
std::pair< ModuleType, std::string > ModuleKey
std::shared_ptr< CADCurve > CADCurveSharedPtr
Represents a command-line configuration option.
std::shared_ptr< Geometry > GeometrySharedPtr
base class for a cad surface
static std::shared_ptr< DataType > AllocateSharedPtr(const Args &...args)
Allocate a shared pointer from the memory pool.
PointsManagerT & PointsManager(void)
Defines a specification for a set of points.
std::map< std::string, ConfigOption > m_config
List of configuration values.
std::shared_ptr< CADObject > CADObjectSharedPtr
Abstract base class for processing modules.
bool BGFSUpdate(OptiObjSharedPtr opti, DNekMat &J, DNekMat &B, DNekMat &H)
tKey RegisterCreatorFunction(tKey idKey, CreatorFunction classCreator, std::string pDesc="")
Register a class with the factory.
1D Gauss-Lobatto-Legendre quadrature points
2D Nodal Electrostatic Points on a Triangle
ModuleFactory & GetModuleFactory()