NEMoSys  0.63.0
A modular, extensible resource with robust automated mesh generation, mesh quality analysis, adaptive mesh refinement, and data transfer between arbitrary meshes.
NEM::MSH::exoGeoMesh Class Reference

A concrete implementation of geoMeshBase representing an Exodus II mesh. More...

Detailed Description

Note that only the title, dimension, element blocks, element block properties, element block variables, node variables, global variables, node sets, and side sets (and the names of each of these fields) are read and stored in an exoGeoMesh class. Side set sides are ignored if the source element does not have the same dimensionality as the mesh.

Definition at line 56 of file exoGeoMesh.H.

Classes

struct  elemBlock
 
struct  nodeSet
 

Public Member Functions

vtkSmartPointer< vtkPolyData > getSS ()
 
 exoGeoMesh ()
 Reads an EXODUS II file into an exoGeoMesh object. More...
 
 exoGeoMesh (const std::string &fileName, int timeStep=1)
 exoGeoMesh constructor from file. More...
 
 ~exoGeoMesh () override
 
void write (const std::string &fileName) override
 Write exoGeoMesh out to a file. More...
 
void report (std::ostream &out) const override
 Write a summary of this exoGeoMesh to out. More...
 
void reconstructGeo () override
 Construct the geometry from the mesh alone. More...
 
void takeGeoMesh (geoMeshBase *otherGeoMesh) override
 Take the GeoMesh of another geoMeshBase. More...
 
const std::string & getTitle () const
 Get the title of the exoGeoMesh (used for writing out to EXODUS II file) More...
 
void setTitle (const std::string &title)
 Set the title of the exoGeoMesh (used for writing out to EXODUS II file) More...
 
int getNumElemBlocks () const
 Get number of element blocks. More...
 
std::map< int, std::string > getElemBlockNames () const
 Get all element block names. More...
 
const std::string & getElemBlockName (int id) const
 Get the name of an element block (used for writing out to EXODUS II file) More...
 
void setElemBlockName (int id, const std::string &name)
 Set the name of an element block (used for writing out to EXODUS II file) More...
 
std::vector< int > getElemBlockIds () const
 Get all element block IDs. More...
 
int getElemBlockId (vtkIdType cellIdx) const
 Get the element block ID of a cell. More...
 
std::vector< vtkIdType > getElemBlock (int blockId) const
 Get (0-based) indices of the cells that are in a specific element block. More...
 
int addElemBlock (vtkUnstructuredGrid *elements, const std::string &name="", float tol=1e-15f)
 Add a new element block to the mesh. More...
 
void addCellsToBlock (vtkUnstructuredGrid *elements, int blockId, float tol=1e-15f)
 Add cells to an existing element block. More...
 
int reassignCells (const std::vector< vtkIdType > &cells, int blockId=-1, const std::string &elemBlockName={})
 Reassign cells to a different element block. More...
 
bool addElemBlockProperty (const std::string &propName)
 Add a property to element blocks (with default value 0 on all element blocks) More...
 
std::vector< std::string > getElemBlockPropertyNames () const
 Get the names of all block properties. More...
 
int getElemBlockProperty (const std::string &propName, int blockId) const
 Get the value of an element block property on a block. More...
 
void setElemBlockProperty (const std::string &propName, int blockId, int value)
 Set the value of an element block property on a block. More...
 
int getNumSideSets () const
 Get number of side sets. More...
 
const std::map< int, std::string > & getSideSetNames () const
 Get all side set names. More...
 
const std::string & getSideSetName (int id) const
 Get the name of a side set (used for writing out to EXODUS II file) More...
 
void setSideSetName (int id, const std::string &name)
 Set the name of a side set (used for writing out to EXODUS II file) More...
 
std::vector< int > getSideSetIds () const
 Get all side set IDs. More...
 
std::pair< std::vector< vtkIdType >, std::vector< int > > getSideSet (int sideSetId) const
 Get sides in a side set. More...
 
int addSideSet (const std::vector< vtkIdType > &elements, const std::vector< int > &sides, const std::string &name="")
 Add a new side set. More...
 
int getNumNodeSets () const
 Get number of node sets. More...
 
std::map< int, std::string > getNodeSetNames () const
 Get all node set names. More...
 
const std::string & getNodeSetName (int id) const
 Get the name of a node set (used for writing out to EXODUS II file) More...
 
void setNodeSetName (int id, const std::string &name)
 Set the name of a node set (used for writing out to EXODUS II file) More...
 
std::vector< int > getNodeSetIds () const
 Get the IDs of all node sets. More...
 
const std::vector< vtkIdType > & getNodeSet (int nodeSetId) const
 Get the nodes of a node set. More...
 
int addNodeSet (const std::vector< vtkIdType > &nodes, const std::string &name="")
 Add a new node set. More...
 
const std::string & getPhysGrpPropertyName () const
 Get the name of the element block property that maps element blocks to physical groups (if empty, each element block represents its own physical group) More...
 
void setPhysGrpPropertyName (const std::string &physGrpName)
 Sets the name of the element block property that maps element blocks to physical groups (if empty, each element block represents its own physical group) More...
 
void stitch (const exoGeoMesh &otherGM, float tol=1e-15f)
 Stitch another exoGeoMesh object onto this one. More...
 
void scaleNodes (double scale)
 Scale point locations. More...
 
virtual void mergeGeoMesh (geoMeshBase *otherGeoMesh)
 Merge mesh data from a new geoMesh to an existing geoMesh. More...
 
const std::string & getGeoEntArrayName () const
 Get the name of the geometric entities array. More...
 
void setGeoEntArrayName (const std::string &geoEntArrayName)
 Set the name of the geometric entities array. More...
 
double getAngleThreshold () const
 Get the angle threshold used for surface classification. More...
 
void setAngleThreshold (double angleThreshold)
 Set the angle threshold used for surface classification. More...
 
nemId_t getNumberOfPoints () const
 Get the number of points in mesh. More...
 
nemId_t getNumberOfCells () const
 Get the number of cells in mesh. More...
 
void getPoint (nemId_t id, std::array< double, 3 > *x) const
 Get the coordinate of a point. More...
 
std::array< double, 3 > getPoint (nemId_t id) const
 Get the coordinate of a point. More...
 
void getCell (nemId_t cellId, vtkGenericCell *cell) const
 Get cell. More...
 
vtkCell * getCell (nemId_t cellId) const
 Get cell. More...
 
void getCellBounds (nemId_t cellId, std::array< double, 6 > *bounds) const
 Get cell bounds. More...
 
std::array< double, 6 > getCellBounds (nemId_t cellId) const
 Get cell bounds. More...
 
VTKCellType getCellType (nemId_t cellId) const
 Get VTK cell type. More...
 
void getCellPoints (nemId_t cellId, vtkIdList *ptIds) const
 Get list of point ids defining specified cell. More...
 
void getPointCells (nemId_t ptId, vtkIdList *cellIds) const
 Get list of cell ids using specified point. More...
 
void getCellNeighbors (nemId_t cellId, vtkIdList *ptIds, vtkIdList *cellIds) const
 Get list of cells sharing points ptIds excluding cellId. More...
 
int getNumberOfPointDataArrays () const
 Get number of arrays in the point data. More...
 
void getPointDataArrayCopy (const std::string &arrayName, vtkAbstractArray *array, int *arrayIdx=nullptr) const
 Get copy of point data array by name. More...
 
vtkSmartPointer< vtkAbstractArray > getPointDataArrayCopy (const std::string &arrayName, int *arrayIdx=nullptr) const
 Create and return a copy of point data array by name. More...
 
void getPointDataArrayCopy (int arrayIdx, vtkAbstractArray *array) const
 Get copy of point data array by index. More...
 
vtkSmartPointer< vtkAbstractArray > getPointDataArrayCopy (int arrayIdx) const
 Create and return a copy of point data array by index. More...
 
int getNumberOfCellDataArrays () const
 Get number of arrays in the cell data. More...
 
void getCellDataArrayCopy (const std::string &arrayName, vtkAbstractArray *array, int *arrayIdx=nullptr) const
 Get copy of cell data array by name. More...
 
vtkSmartPointer< vtkAbstractArray > getCellDataArrayCopy (const std::string &arrayName, int *arrayIdx=nullptr) const
 Create and return a copy of cell data array by name. More...
 
void getCellDataArrayCopy (int arrayIdx, vtkAbstractArray *array) const
 Get copy of cell data array by index. More...
 
vtkSmartPointer< vtkAbstractArray > getCellDataArrayCopy (int arrayIdx) const
 Create and return a copy of cell data array by index. More...
 
int getNumberOfFieldDataArrays () const
 Get number of arrays in the field data. More...
 
void getFieldDataArrayCopy (const std::string &arrayName, vtkAbstractArray *array, int *arrayIdx=nullptr) const
 Get copy of field data array by name. More...
 
vtkSmartPointer< vtkAbstractArray > getFieldDataArrayCopy (const std::string &arrayName, int *arrayIdx=nullptr) const
 Create and return a copy of field data array by name. More...
 
void getFieldDataArrayCopy (int arrayIdx, vtkAbstractArray *array) const
 Get copy of field data array by index. More...
 
vtkSmartPointer< vtkAbstractArray > getFieldDataArrayCopy (int arrayIdx) const
 Create and return a copy of field data array by index. More...
 

Static Public Member Functions

static exoGeoMeshNew ()
 

Protected Member Functions

 exoGeoMesh (const vtkSmartPointer< vtkExodusIIReader > &reader)
 exoGeoMesh constructor from vtkExodusIIReader More...
 
int setPointDataArray (vtkAbstractArray *array)
 Set point data. More...
 
int setCellDataArray (vtkAbstractArray *array)
 Set cell data. More...
 
int setFieldDataArray (vtkAbstractArray *array)
 Set field data. More...
 
void unsetPointDataArray (int arrayIdx)
 Remove point data array by index. More...
 
void unsetPointDataArray (const std::string &arrayName)
 Remove point data array by name. More...
 
void unsetCellDataArray (int arrayIdx)
 Remove cell data array by index. More...
 
void unsetCellDataArray (const std::string &arrayName)
 Remove cell data array by name. More...
 
void unsetFieldDataArray (int arrayIdx)
 Remove field data array by index. More...
 
void unsetFieldDataArray (const std::string &arrayName)
 Remove field data array by name. More...
 
const GeoMeshgetGeoMesh () const
 Get the underlying geometry object. More...
 
void setGeoMesh (const geoMeshBase::GeoMesh &geoMesh)
 Set the underlying geometry object. More...
 

Static Protected Attributes

static constexpr auto GEO_ENT_DEFAULT_NAME = "GeoEnt"
 

Private Member Functions

void resetElemBlocks ()
 Clears element block names, element block properties. More...
 
void resetNodeSetPoints (vtkIdTypeArray *nodeMap=nullptr)
 Renumbers the nodes in all node sets based on nodeMap if provided. More...
 
void setSideSetObjId ()
 Sets the (Exodus) side set IDs of each cell in the GeoMesh.sideSet by creating a side set for each pair (side entity, parent entity). More...
 
void resetNative () override
 

Static Private Member Functions

static vtkSmartPointer< vtkExodusIIReader > getExoReader (const std::string &fileName, int timeStep=1)
 
static GeoMesh exoReader2GM (vtkSmartPointer< vtkExodusIIReader > reader)
 
static const char * getExoIdArrName ()
 

Private Attributes

std::string _title
 
std::map< int, elemBlock_elemBlocks
 
std::map< int, std::string > _sideSetNames
 
std::map< int, nodeSet_nodeSets
 
std::set< std::string > _elemBlockPropNames
 
std::string _physGrpName
 

Inherits NEM::MSH::geoMeshBase.

Constructor & Destructor Documentation

◆ exoGeoMesh() [1/3]

NEM::MSH::exoGeoMesh::exoGeoMesh ( )
Parameters
fileNameName of file to read. Empty string interpreted as creating new exoGeoMesh with empty mesh
timeStepTime step (using EXODUS II indexing) to read
Returns
Pointer to a new exoGeoMesh object

Definition at line 257 of file exoGeoMesh.C.

Referenced by NEM::MSH::vtkStandardNewMacro().

257 : exoGeoMesh("") {}
exoGeoMesh()
Reads an EXODUS II file into an exoGeoMesh object.
Definition: exoGeoMesh.C:257

◆ exoGeoMesh() [2/3]

NEM::MSH::exoGeoMesh::exoGeoMesh ( const std::string &  fileName,
int  timeStep = 1 
)
explicit
Parameters
fileNameName of EXODUS II file to read
timeStepTime step (using EXODUS II indexing) to read

Definition at line 377 of file exoGeoMesh.C.

378  : exoGeoMesh(getExoReader(fileName, timeStep)) {}
exoGeoMesh()
Reads an EXODUS II file into an exoGeoMesh object.
Definition: exoGeoMesh.C:257
static vtkSmartPointer< vtkExodusIIReader > getExoReader(const std::string &fileName, int timeStep=1)
Definition: exoGeoMesh.C:1605

◆ ~exoGeoMesh()

NEM::MSH::exoGeoMesh::~exoGeoMesh ( )
override

Definition at line 380 of file exoGeoMesh.C.

380 { std::cout << "exoGeoMesh destructed" << std::endl; }

◆ exoGeoMesh() [3/3]

NEM::MSH::exoGeoMesh::exoGeoMesh ( const vtkSmartPointer< vtkExodusIIReader > &  reader)
explicitprotected

Note that side set side indices in the reader's output are ignored and are read from reader->GetFileName() instead. Element block properties are also read from the file separately.

Parameters
readerExisting vtkExodusIIReader from which to create exoGeoMesh object. Update() should already have been called.

Definition at line 259 of file exoGeoMesh.C.

References _elemBlockPropNames, _elemBlocks, _nodeSets, _sideSetNames, _title, cellType, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::geoMeshBase::GeoMesh::mesh, nodes, and nodeSets.

260  : geoMeshBase(exoReader2GM(reader)) {
261  if (reader && reader->GetOutput() &&
262  reader->GetOutput()->GetNumberOfBlocks() == 8) {
263  auto mbds = reader->GetOutput();
264  _title = reader->GetTitle();
265  auto elemBlocks = vtkMultiBlockDataSet::SafeDownCast(mbds->GetBlock(0));
266  for (unsigned int i = 0; i < elemBlocks->GetNumberOfBlocks(); ++i) {
267  std::string elemBlockName =
268  elemBlocks->GetMetaData(i)->Get(vtkMultiBlockDataSet::NAME());
269  auto elemBlock =
270  vtkUnstructuredGrid::SafeDownCast(elemBlocks->GetBlock(i));
271  int elemBlockId;
272  VTKCellType cellType;
273  if (elemBlock->GetNumberOfCells() > 0) {
274  elemBlockId =
275  vtkIntArray::FastDownCast(
276  elemBlock->GetCellData()->GetAbstractArray(getExoIdArrName()))
277  ->GetValue(0);
278  cellType = static_cast<VTKCellType>(elemBlock->GetCellType(0));
279  } else {
280  elemBlockId =
281  vtkIntArray::FastDownCast(
282  elemBlock->GetFieldData()->GetAbstractArray("ElementBlockIds"))
283  ->GetValue(0);
284  cellType = VTK_EMPTY_CELL;
285  }
286  _elemBlocks[elemBlockId] = {elemBlockName, cellType, {}};
287  }
288  auto sideSets = vtkMultiBlockDataSet::SafeDownCast(mbds->GetBlock(4));
289  if (sideSets->GetNumberOfBlocks() >= 1) {
290  for (int i = 0; i < sideSets->GetNumberOfBlocks(); ++i) {
291  auto sideSetName = reader->GetSideSetArrayName(i);
292  auto sideSetId = reader->GetObjectId(vtkExodusIIReader::SIDE_SET, i);
293  _sideSetNames[sideSetId] = sideSetName ? sideSetName : "";
294  }
295  }
296 
297  auto mesh = getGeoMesh().mesh;
298  std::map<vtkIdType, vtkIdType> globalNodeId2meshIdx;
299  auto globalNodeIdArr =
300  vtkIdTypeArray::FastDownCast(mesh->GetPointData()->GetAbstractArray(
301  reader->GetGlobalNodeIdArrayName()));
302  for (vtkIdType i = 0; i < mesh->GetNumberOfPoints(); ++i) {
303  globalNodeId2meshIdx[globalNodeIdArr->GetValue(i)] = i;
304  }
305  mesh->GetPointData()->RemoveArray(reader->GetGlobalNodeIdArrayName());
306  mesh->GetPointData()->RemoveArray(reader->GetPedigreeNodeIdArrayName());
307  auto nodeSets = vtkMultiBlockDataSet::SafeDownCast(mbds->GetBlock(7));
308  for (unsigned int i = 0; i < nodeSets->GetNumberOfBlocks(); ++i) {
309  std::string nodeSetName =
310  nodeSets->GetMetaData(i)->Get(vtkMultiBlockDataSet::NAME());
311  auto nodeSet = vtkUnstructuredGrid::SafeDownCast(nodeSets->GetBlock(i));
312  auto nodeSetId =
313  vtkIntArray::FastDownCast(
314  nodeSet->GetCellData()->GetAbstractArray(getExoIdArrName()))
315  ->GetValue(0);
316  std::vector<vtkIdType> nodes;
317  nodes.reserve(nodeSet->GetNumberOfCells());
318  auto nodeSetGlobalNodeIdArr = vtkIdTypeArray::FastDownCast(
319  nodeSet->GetPointData()->GetAbstractArray(
320  reader->GetGlobalNodeIdArrayName()));
321  for (vtkIdType j = 0; j < nodeSet->GetNumberOfCells(); ++j) {
322  auto nodeGlobalId = nodeSetGlobalNodeIdArr->GetValue(
323  nodeSet->GetCell(j)->GetPointId(0));
324  auto find = globalNodeId2meshIdx.find(nodeGlobalId);
325  if (find != globalNodeId2meshIdx.end()) {
326  nodes.emplace_back(find->second);
327  }
328  }
329  _nodeSets[nodeSetId] = {nodeSetName, nodes};
330  }
331  // Unfortunately the vtkExodusIIReader does not seem to support exodus
332  // properties at the moment.
333  int comp_ws = sizeof(double);
334  int io_ws = 0;
335  float version;
336  auto exoid =
337  ex_open(reader->GetFileName(), EX_READ, &comp_ws, &io_ws, &version);
338  checkExodusErr(exoid, true);
339  // We get the properties in order, so, just in case, we get the element
340  // block ids in order
341  std::vector<int> elemBlockIds;
342  elemBlockIds.resize(_elemBlocks.size());
343  auto err = ex_get_ids(exoid, EX_ELEM_BLOCK, elemBlockIds.data());
344  checkExodusErr(err);
345  int numProps = ex_inquire_int(exoid, EX_INQ_EB_PROP);
346  std::vector<std::string> propNames;
347  propNames.resize(numProps);
348  std::vector<const char *> propNamesPtr;
349  propNamesPtr.reserve(numProps);
350  for (int i = 0; i < numProps; ++i) {
351  propNames[i].resize(MAX_NAME_LENGTH);
352  propNamesPtr.emplace_back(propNames[i].c_str());
353  }
354  err = ex_get_prop_names(exoid, EX_ELEM_BLOCK,
355  const_cast<char **>(propNamesPtr.data()));
356  checkExodusErr(err);
357  for (int i = 0; i < numProps; ++i) {
358  if (strcmp(propNamesPtr[i], "ID") != 0) {
359  std::vector<int> propVals;
360  propVals.resize(_elemBlocks.size());
361  err = ex_get_prop_array(exoid, EX_ELEM_BLOCK, propNamesPtr[i],
362  propVals.data());
363  checkExodusErr(err);
364  _elemBlockPropNames.insert(propNamesPtr[i]);
365  for (std::size_t j = 0; j < _elemBlocks.size(); ++j) {
366  _elemBlocks[elemBlockIds[j]].properties[propNamesPtr[i]] =
367  propVals[j];
368  }
369  }
370  }
371  err = ex_close(exoid);
372  checkExodusErr(err);
373  }
374  std::cout << "exoGeoMesh constructed" << std::endl;
375 }
std::string _title
Definition: exoGeoMesh.H:387
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
std::vector< std::pair< vtkIdType, std::vector< double > > > nodes
Each entry stores (node ID in .inp file, coordinates)
Definition: inpGeoMesh.C:139
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
std::map< std::string, std::vector< vtkIdType > > nodeSets
Map from NSET name to node ids (ids given by .inp file)
Definition: inpGeoMesh.C:152
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390
VTKCellType cellType
Definition: inpGeoMesh.C:129
std::shared_ptr< meshBase > mesh
static GeoMesh exoReader2GM(vtkSmartPointer< vtkExodusIIReader > reader)
Definition: exoGeoMesh.C:1472
geoMeshBase()
Query for conversion from vtk to gmsh.
Definition: geoMeshBase.C:77
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

Member Function Documentation

◆ addCellsToBlock()

void NEM::MSH::exoGeoMesh::addCellsToBlock ( vtkUnstructuredGrid *  elements,
int  blockId,
float  tol = 1e-15f 
)

Invalidates geometry, if any. PointData and CellData arrays are intersected.

Parameters
elementsvtkUnstructuredGrid of cells to add to the mesh. All cells should be of the same type as cells in the block given by blockId.
blockIdID of existing element block
tolTolerance for merging points

Definition at line 938 of file exoGeoMesh.C.

References _elemBlocks, NEM::MSH::exoGeoMesh::elemBlock::cellType, NEM::MSH::geoMeshBase::GeoMesh::geo, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::geoMeshBase::GeoMesh::link, mesh, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::New(), resetNodeSetPoints(), NEM::MSH::geoMeshBase::setGeoMesh(), and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

Referenced by addElemBlock().

939  {
940  if (elements && elements->GetNumberOfCells() > 0) {
941  auto types = vtkSmartPointer<vtkCellTypes>::New();
942  elements->GetCellTypes(types);
943  if (types->GetNumberOfTypes() > 1) {
944  std::cerr << "Single element block cannot have multiple cell types"
945  << std::endl;
946  exit(1);
947  }
948  auto elemBlock = _elemBlocks.find(blockId);
949  if (getGeoMesh().mesh->GetNumberOfCells() == 0) {
950  _elemBlocks.clear();
951  std::cerr << "No existing element blocks." << std::endl;
952  exit(1);
953  }
954  if (elemBlock == _elemBlocks.end()) {
955  std::cerr << "No existing element block with id: " << blockId
956  << std::endl;
957  exit(1);
958  }
959  if (types->GetCellType(0) != elemBlock->second.cellType) {
960  std::cerr
961  << "Cell type does not match cell type of existing element block."
962  << std::endl;
963  exit(1);
964  }
965  vtkSmartPointer<vtkAbstractArray> oldBlockIdArr =
966  elements->GetCellData()->GetAbstractArray(getExoIdArrName());
967  if (oldBlockIdArr) {
968  elements->GetCellData()->RemoveArray(getExoIdArrName());
969  }
970  auto mesh = getGeoMesh().mesh;
971  auto newBlockIdArr = vtkSmartPointer<vtkIntArray>::Take(
972  vtkIntArray::FastDownCast(mesh->GetCellData()
973  ->GetAbstractArray(getExoIdArrName())
974  ->NewInstance()));
975  newBlockIdArr->SetName(getExoIdArrName());
976  newBlockIdArr->SetNumberOfValues(elements->GetNumberOfCells());
977  newBlockIdArr->FillComponent(0, blockId);
978  elements->GetCellData()->AddArray(newBlockIdArr);
979 #ifdef HAVE_GMSH
980  if (!getGeoMesh().geo.empty()) {
981  gmsh::model::setCurrent(getGeoMesh().geo);
982  gmsh::model::remove();
983  setGeoMesh({mesh, "", "", getGeoMesh().sideSet});
984  }
985 #endif
987  auto nodeMaps = mergeMeshes(mesh, elements, newMesh, tol);
988  setGeoMesh(
989  {newMesh, getGeoMesh().geo, getGeoMesh().link, getGeoMesh().sideSet});
990  resetNodeSetPoints(nodeMaps.first);
991  resetSideSetPoints(newMesh, getGeoMesh().sideSet.sides, nodeMaps.first);
992  elements->GetCellData()->RemoveArray(getExoIdArrName());
993  if (oldBlockIdArr) {
994  elements->GetCellData()->AddArray(oldBlockIdArr);
995  }
996  } else {
997  std::cerr << "No elements to add." << std::endl;
998  }
999 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::shared_ptr< meshBase > mesh
void resetNodeSetPoints(vtkIdTypeArray *nodeMap=nullptr)
Renumbers the nodes in all node sets based on nodeMap if provided.
Definition: exoGeoMesh.C:1699
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ addElemBlock()

int NEM::MSH::exoGeoMesh::addElemBlock ( vtkUnstructuredGrid *  elements,
const std::string &  name = "",
float  tol = 1e-15f 
)

Invalidates geometry, if any. PointData and CellData arrays are intersected.

Parameters
elementsvtkUnstructuredGrid of cells to add to the mesh. All cells should be of same cell type.
nameName of new element block
tolTolerance for merging points
Returns
The ID of the new element block.

Definition at line 901 of file exoGeoMesh.C.

References _elemBlocks, addCellsToBlock(), NEM::MSH::exoGeoMesh::elemBlock::cellType, NEM::MSH::geoMeshBase::getGeoMesh(), nemAux::leastUnusedKey(), mesh, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::exoGeoMesh::elemBlock::name, NEM::MSH::New(), resetNative(), and NEM::MSH::geoMeshBase::setGeoMesh().

902  {
903  if (elements && elements->GetNumberOfCells() > 0) {
904  auto types = vtkSmartPointer<vtkCellTypes>::New();
905  elements->GetCellTypes(types);
906  if (types->GetNumberOfTypes() > 1) {
907  std::cerr << "Single element block cannot have multiple cell types"
908  << std::endl;
909  return -1;
910  }
911  auto mesh = getGeoMesh().mesh;
912  if (mesh->GetNumberOfCells() == 0) {
913  mesh->DeepCopy(elements);
914 #ifdef HAVE_GMSH
915  if (!getGeoMesh().geo.empty()) {
916  gmsh::model::setCurrent(getGeoMesh().geo);
917  gmsh::model::remove();
918  }
919 #endif
920  setGeoMesh({mesh, "", "", {}});
921  resetNative();
922  // Assumption that there is exactly one element block now.
923  return _elemBlocks.begin()->first;
924  } else {
925  int newElemBlockId = nemAux::leastUnusedKey(_elemBlocks);
926  auto &elemBlock = _elemBlocks[newElemBlockId];
927  elemBlock.cellType = static_cast<VTKCellType>(types->GetCellType(0));
928  elemBlock.name = name;
929  addCellsToBlock(elements, newElemBlockId, tol);
930  return newElemBlockId;
931  }
932  } else {
933  std::cerr << "No elements to add." << std::endl;
934  return -1;
935  }
936 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
A leastUnusedKey(const std::map< A, B > &map, A min=1)
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void resetNative() override
Definition: exoGeoMesh.C:1639
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
void addCellsToBlock(vtkUnstructuredGrid *elements, int blockId, float tol=1e-15f)
Add cells to an existing element block.
Definition: exoGeoMesh.C:938
std::shared_ptr< meshBase > mesh
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ addElemBlockProperty()

bool NEM::MSH::exoGeoMesh::addElemBlockProperty ( const std::string &  propName)
Parameters
propNameName of new property
Returns
Whether or not new property was added

Definition at line 1040 of file exoGeoMesh.C.

References _elemBlockPropNames, and NEM::MSH::geoMeshBase::getGeoMesh().

1040  {
1041  if (getGeoMesh().mesh->GetNumberOfCells() == 0) {
1042  return false;
1043  }
1044  return _elemBlockPropNames.insert(propName).second;
1045 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
std::shared_ptr< meshBase > mesh
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ addNodeSet()

int NEM::MSH::exoGeoMesh::addNodeSet ( const std::vector< vtkIdType > &  nodes,
const std::string &  name = "" 
)
Parameters
nodesNode indices that should belong on the new node set (0-based indexing)
nameName of new node set
Returns
ID of new node set

Definition at line 1257 of file exoGeoMesh.C.

References _nodeSets, NEM::MSH::geoMeshBase::getGeoMesh(), nemAux::leastUnusedKey(), and NEM::MSH::geoMeshBase::GeoMesh::mesh.

1258  {
1259  if (!nodes.empty()) {
1260  auto minmax = std::minmax_element(nodes.begin(), nodes.end());
1261  if (*minmax.first < 0) {
1262  std::cerr << "Unknown node " << *minmax.first << std::endl;
1263  return -1;
1264  } else if (*minmax.second >= getGeoMesh().mesh->GetNumberOfPoints()) {
1265  std::cerr << "Unknown node " << *minmax.second << std::endl;
1266  return -1;
1267  }
1268  auto newId = nemAux::leastUnusedKey(_nodeSets);
1269  _nodeSets[newId] = {name, nodes};
1270  return newId;
1271  }
1272  return -1;
1273 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
A leastUnusedKey(const std::map< A, B > &map, A min=1)
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ addSideSet()

int NEM::MSH::exoGeoMesh::addSideSet ( const std::vector< vtkIdType > &  elements,
const std::vector< int > &  sides,
const std::string &  name = "" 
)
Parameters
elementsThe (0-based) index of the cells that each side comes from
sidesThe index of the face/edge that of the side (according to VTK face/edge ordering)
nameName of new side set
Returns
ID of new side set

Definition at line 1145 of file exoGeoMesh.C.

References _sideSetNames, NEM::MSH::geoMeshBase::GeoMesh::geo, getExoIdArrName(), NEM::MSH::geoMeshBase::SideSet::getGeoEntArr(), NEM::MSH::geoMeshBase::getGeoMesh(), nemAux::leastUnusedKey(), NEM::MSH::geoMeshBase::GeoMesh::link, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::New(), NEM::MSH::geoMeshBase::setGeoMesh(), and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

1147  {
1148  if (!elements.empty() && elements.size() == sides.size()) {
1149  auto newId = nemAux::leastUnusedKey(_sideSetNames);
1150  auto gm = getGeoMesh();
1151  if (!gm.sideSet.sides) {
1152  auto sideSetPD = vtkSmartPointer<vtkPolyData>::New();
1153  sideSetPD->Allocate();
1154  sideSetPD->SetPoints(getGeoMesh().mesh->GetPoints());
1155  auto sideSetExoId = vtkSmartPointer<vtkIntArray>::New();
1156  sideSetExoId->SetName(getExoIdArrName());
1157  sideSetPD->GetCellData()->AddArray(sideSetExoId);
1158  auto sideSetEntities = vtkSmartPointer<vtkIntArray>::New();
1159  auto sideSetOrigCellId = vtkSmartPointer<vtkIdTypeArray>::New();
1160  sideSetOrigCellId->SetNumberOfComponents(2);
1161  auto sideSetCellFaceId = vtkSmartPointer<vtkIntArray>::New();
1162  sideSetCellFaceId->SetNumberOfComponents(2);
1163  setGeoMesh(
1164  {getGeoMesh().mesh,
1165  getGeoMesh().geo,
1166  getGeoMesh().link,
1167  {sideSetPD, sideSetEntities, sideSetOrigCellId, sideSetCellFaceId}});
1168  }
1169  auto sideSet = getGeoMesh().sideSet;
1170  auto sideSetExoId = vtkIntArray::FastDownCast(
1171  sideSet.sides->GetCellData()->GetAbstractArray(getExoIdArrName()));
1172  sideSetExoId->Resize(sideSet.sides->GetNumberOfCells() + elements.size());
1173  auto sideSetEntities = sideSet.getGeoEntArr();
1174  sideSetEntities->Resize(sideSet.sides->GetNumberOfCells() +
1175  elements.size());
1176  auto sideSetOrigCellId = sideSet.getOrigCellArr();
1177  sideSetOrigCellId->Resize(sideSet.sides->GetNumberOfCells() +
1178  elements.size());
1179  auto sideSetCellFaceId = sideSet.getCellFaceArr();
1180  sideSetCellFaceId->Resize(sideSet.sides->GetNumberOfCells() +
1181  elements.size());
1182 
1183  auto mesh = getGeoMesh().mesh;
1184  auto elemIt = elements.begin();
1185  auto sidesIt = sides.begin();
1186  for (; elemIt != elements.end(); ++sidesIt, ++elemIt) {
1187  auto parent = mesh->GetCell(*elemIt);
1188  if (!parent) {
1189  std::cerr << "No cell found with index " << *elemIt << std::endl;
1190  continue;
1191  }
1192  auto side = parent->GetCellDimension() == 2 ? parent->GetEdge(*sidesIt)
1193  : parent->GetFace(*sidesIt);
1194  sideSet.sides->InsertNextCell(side->GetCellType(), side->GetPointIds());
1195  sideSetExoId->InsertNextValue(newId);
1196  sideSetEntities->InsertNextValue(newId);
1197  sideSetOrigCellId->InsertNextTuple2(*elemIt, -1);
1198  sideSetCellFaceId->InsertNextTuple2(*sidesIt, -1);
1199  }
1200 
1201  _sideSetNames[newId] = name;
1202  return newId;
1203  }
1204  return -1;
1205 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
A leastUnusedKey(const std::map< A, B > &map, A min=1)
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::shared_ptr< meshBase > mesh
vtkSmartPointer< vtkIntArray > getGeoEntArr() const
Definition: geoMeshBase.C:252
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ exoReader2GM()

geoMeshBase::GeoMesh NEM::MSH::exoGeoMesh::exoReader2GM ( vtkSmartPointer< vtkExodusIIReader >  reader)
staticprivate

Definition at line 1472 of file exoGeoMesh.C.

References getExoIdArrName(), mesh, and NEM::MSH::New().

1473  {
1475  SideSet sideSet{};
1476  if (!reader) {
1477  return {mesh, "", "", {}};
1478  }
1479 
1480  auto mbds = reader->GetOutput();
1481  if (mbds->GetNumberOfBlocks() != 8) {
1482  std::cerr << "Malformed output of vtkExodusIIReader. Check that file "
1483  "exists and is valid Exodus II file."
1484  << std::endl;
1485  exit(1);
1486  }
1487  // Map from "GlobalElementId", set by vtkExodusIIReader, to the index in
1488  // mesh, which becomes GeoMesh.mesh
1489  std::map<vtkIdType, vtkIdType> elemId2MeshIdx;
1490  if (reader->GetNumberOfElementsInFile() > 0) {
1491  auto exoElemBlocks = vtkMultiBlockDataSet::SafeDownCast(mbds->GetBlock(0));
1492  auto merge = vtkSmartPointer<mergeCells>::New();
1493  merge->SetUnstructuredGrid(mesh);
1494  merge->SetTotalNumberOfDataSets(exoElemBlocks->GetNumberOfBlocks());
1495  merge->SetTotalNumberOfPoints(reader->GetNumberOfNodes());
1496  merge->SetTotalNumberOfCells(reader->GetTotalNumberOfElements());
1497  merge->SetUseGlobalIds(1);
1498  merge->SetUseGlobalCellIds(1);
1499  auto it = vtkSmartPointer<vtkCompositeDataIterator>::Take(
1500  exoElemBlocks->NewIterator());
1501  for (it->InitTraversal(); !it->IsDoneWithTraversal(); it->GoToNextItem()) {
1502  merge->MergeDataSet(vtkDataSet::SafeDownCast(it->GetCurrentDataObject()));
1503  }
1504  merge->Finish();
1505  for (int i = mesh->GetCellData()->GetNumberOfArrays() - 1; i >= 0; --i) {
1506  if (mesh->GetCellData()->GetArray(i)->GetNumberOfTuples() !=
1507  mesh->GetNumberOfCells()) {
1508  mesh->GetCellData()->RemoveArray(i);
1509  }
1510  }
1511  for (int i = mesh->GetPointData()->GetNumberOfArrays() - 1; i >= 0; --i) {
1512  if (mesh->GetPointData()->GetArray(i)->GetNumberOfTuples() !=
1513  mesh->GetNumberOfPoints()) {
1514  mesh->GetPointData()->RemoveArray(i);
1515  }
1516  }
1517  auto globalElemIdArr = vtkIdTypeArray::FastDownCast(
1518  mesh->GetCellData()->GetArray(reader->GetGlobalElementIdArrayName()));
1519  for (vtkIdType i = 0; i < mesh->GetNumberOfCells(); ++i) {
1520  elemId2MeshIdx[globalElemIdArr->GetValue(i)] = i;
1521  }
1522  mesh->GetCellData()->RemoveArray(reader->GetPedigreeElementIdArrayName());
1523  mesh->GetCellData()->RemoveArray(reader->GetGlobalElementIdArrayName());
1524  }
1525  if (reader->GetNumberOfSideSetArrays() > 0 &&
1526  reader->GetDimensionality() >= 2) {
1527  auto sideSetPD = vtkSmartPointer<vtkPolyData>::New();
1528  sideSetPD->SetPoints(mesh->GetPoints());
1529  sideSetPD->Allocate();
1530  auto sideSetExoId = vtkSmartPointer<vtkIntArray>::New();
1531  sideSetExoId->SetName(getExoIdArrName());
1532  auto sideSetEntities = vtkSmartPointer<vtkIntArray>::New();
1533  auto sideSetOrigCellId = vtkSmartPointer<vtkIdTypeArray>::New();
1534  sideSetOrigCellId->SetNumberOfComponents(2);
1535  auto sideSetCellFaceId = vtkSmartPointer<vtkIntArray>::New();
1536  sideSetCellFaceId->SetNumberOfComponents(2);
1537 
1538  int comp_ws = sizeof(double);
1539  int io_ws = 0;
1540  float version;
1541  auto exoid =
1542  ex_open(reader->GetFileName(), EX_READ, &comp_ws, &io_ws, &version);
1543  checkExodusErr(exoid, true);
1544 
1545  auto exoSideSets = vtkMultiBlockDataSet::SafeDownCast(mbds->GetBlock(4));
1546  for (unsigned int i = 0; i < exoSideSets->GetNumberOfBlocks(); ++i) {
1547  auto exoSideSet =
1548  vtkUnstructuredGrid::SafeDownCast(exoSideSets->GetBlock(i));
1549  // vtkExodusIIReader sets the element id off by 1 compared to
1550  // GlobalElementId (see vtkExodusIIReader.cxx::832 in v7.1.0)
1551  auto sourceElemArr = vtkIdTypeArray::FastDownCast(
1552  exoSideSet->GetCellData()->GetAbstractArray(
1553  reader->GetSideSetSourceElementIdArrayName()));
1554  auto objectIdArr = exoSideSet->GetCellData()->GetArray(getExoIdArrName());
1555  // Because the element ids are off by 1 compared to GlobalElementId,
1556  // the side number is off because the wrong parent cell type is used to
1557  // convert Exodus side index to VTK side index. Thus we do not use
1558  // exoSideSet->GetCellData()->GetAbstractArray(
1559  // reader->GetSideSetSourceElementSideArrayName());
1560  // and instead read from the file.
1561  // Here we rely on the assumption that vtkExodusIIReader does not change
1562  // the order of entries in the side set.
1563  std::vector<int> sourceSideVec;
1564  sourceSideVec.resize(exoSideSet->GetNumberOfCells());
1565  auto err = ex_get_set(
1566  exoid, EX_SIDE_SET,
1567  vtkIntArray::FastDownCast(
1568  exoSideSet->GetCellData()->GetAbstractArray(getExoIdArrName()))
1569  ->GetValue(0),
1570  nullptr, sourceSideVec.data());
1571  checkExodusErr(err);
1572 
1573  for (vtkIdType j = 0; j < exoSideSet->GetNumberOfCells(); ++j) {
1574  auto origCellId = elemId2MeshIdx.at(sourceElemArr->GetValue(j) + 1);
1575  auto parent = mesh->GetCell(origCellId);
1576  auto cellFaceId = exoSide2vtkSide(
1577  sourceSideVec[j], static_cast<VTKCellType>(parent->GetCellType()));
1578  if (reader->GetDimensionality() == parent->GetCellDimension()) {
1579  if (reader->GetDimensionality() == 2) {
1580  auto edge = parent->GetEdge(cellFaceId);
1581  sideSetPD->InsertNextCell(edge->GetCellType(), edge->GetPointIds());
1582  } else if (reader->GetDimensionality() == 3) {
1583  auto face = parent->GetFace(cellFaceId);
1584  sideSetPD->InsertNextCell(face->GetCellType(), face->GetPointIds());
1585  }
1586  sideSetExoId->InsertNextValue(
1587  static_cast<int>(objectIdArr->GetComponent(j, 0)));
1588  sideSetEntities->InsertNextValue(
1589  static_cast<int>(objectIdArr->GetComponent(j, 0)));
1590  sideSetOrigCellId->InsertNextTuple2(origCellId, -1);
1591  sideSetCellFaceId->InsertNextTuple2(cellFaceId, -1);
1592  }
1593  }
1594  }
1595  sideSetPD->GetCellData()->AddArray(sideSetExoId);
1596  sideSetPD->Squeeze();
1597  sideSet = {sideSetPD, sideSetEntities, sideSetOrigCellId,
1598  sideSetCellFaceId};
1599  auto err = ex_close(exoid);
1600  checkExodusErr(err);
1601  }
1602  return {mesh, "", "", sideSet};
1603 }
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
std::shared_ptr< meshBase > mesh
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253

◆ getAngleThreshold()

double NEM::MSH::geoMeshBase::getAngleThreshold ( ) const
inlineinherited
Returns
angle threshold (in radians)

Definition at line 171 of file geoMeshBase.H.

171 { return _angleThreshold; }
double _angleThreshold
Dihedral angle threshold (in radians) to classify surfaces (Default: 30 degrees)
Definition: geoMeshBase.H:554

◆ getCell() [1/2]

void NEM::MSH::geoMeshBase::getCell ( nemId_t  cellId,
vtkGenericCell *  cell 
) const
inlineinherited
Parameters
cellIdcell id
cellcell

Definition at line 214 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

214  {
215  _geoMesh.mesh->GetCell(cellId, cell);
216  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCell() [2/2]

vtkCell* NEM::MSH::geoMeshBase::getCell ( nemId_t  cellId) const
inlineinherited
Parameters
cellIdcell id
Returns
cell

Definition at line 222 of file geoMeshBase.H.

222  {
223  return _geoMesh.mesh->GetCell(cellId);
224  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellBounds() [1/2]

void NEM::MSH::geoMeshBase::getCellBounds ( nemId_t  cellId,
std::array< double, 6 > *  bounds 
) const
inlineinherited
Parameters
cellIdcell id
boundsarray of bounds as (x_min,x_max, y_min,y_max, z_min,z_max)

Definition at line 230 of file geoMeshBase.H.

230  {
231  _geoMesh.mesh->GetCellBounds(cellId, bounds->data());
232  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellBounds() [2/2]

std::array<double, 6> NEM::MSH::geoMeshBase::getCellBounds ( nemId_t  cellId) const
inlineinherited
Parameters
cellIdcell id
Returns
array of bounds as (x_min,x_max, y_min,y_max, z_min,z_max)

Definition at line 238 of file geoMeshBase.H.

238  {
239  std::array<double, 6> bounds{};
240  getCellBounds(cellId, &bounds);
241  return bounds;
242  }
void getCellBounds(nemId_t cellId, std::array< double, 6 > *bounds) const
Get cell bounds.
Definition: geoMeshBase.H:230

◆ getCellDataArrayCopy() [1/4]

void NEM::MSH::geoMeshBase::getCellDataArrayCopy ( const std::string &  arrayName,
vtkAbstractArray *  array,
int *  arrayIdx = nullptr 
) const
inherited

Optionally, get array index.

Parameters
arrayNamearray name
arraycell data array
arrayIdxarray index

Definition at line 180 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

Referenced by NEM::MSH::diffMesh().

182  {
183  getArrCopy(_geoMesh.mesh->GetCellData(), arrayName, arrayIdx, array);
184 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellDataArrayCopy() [2/4]

vtkSmartPointer< vtkAbstractArray > NEM::MSH::geoMeshBase::getCellDataArrayCopy ( const std::string &  arrayName,
int *  arrayIdx = nullptr 
) const
inherited

Optionally, get array index.

Parameters
arrayNamearray name
arrayIdxarray index
Returns
pointer to copy of array

Definition at line 186 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

187  {
188  return getArrCopy(_geoMesh.mesh->GetCellData(), arrayName, arrayIdx);
189 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellDataArrayCopy() [3/4]

void NEM::MSH::geoMeshBase::getCellDataArrayCopy ( int  arrayIdx,
vtkAbstractArray *  array 
) const
inherited
Parameters
arrayIdxarray index
arraycell data array

Definition at line 191 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

192  {
193  getArrCopy(_geoMesh.mesh->GetCellData(), arrayIdx, array);
194 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellDataArrayCopy() [4/4]

vtkSmartPointer< vtkAbstractArray > NEM::MSH::geoMeshBase::getCellDataArrayCopy ( int  arrayIdx) const
inherited
Parameters
arrayIdxarray index
Returns
pointer to copy of array

Definition at line 196 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

197  {
198  return getArrCopy(_geoMesh.mesh->GetCellData(), arrayIdx);
199 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellNeighbors()

void NEM::MSH::geoMeshBase::getCellNeighbors ( nemId_t  cellId,
vtkIdList *  ptIds,
vtkIdList *  cellIds 
) const
inlineinherited
Parameters
cellIdid of cell to exclude
ptIdspoint id
cellIdslist of cell ids

Definition at line 273 of file geoMeshBase.H.

274  {
275  _geoMesh.mesh->GetCellNeighbors(cellId, ptIds, cellIds);
276  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellPoints()

void NEM::MSH::geoMeshBase::getCellPoints ( nemId_t  cellId,
vtkIdList *  ptIds 
) const
inlineinherited
Parameters
cellIdcell id
ptIdslist of point ids

Definition at line 256 of file geoMeshBase.H.

256  {
257  _geoMesh.mesh->GetCellPoints(cellId, ptIds);
258  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getCellType()

VTKCellType NEM::MSH::geoMeshBase::getCellType ( nemId_t  cellId) const
inlineinherited
Parameters
cellIdcell id
Returns
VTK cell type (see vtk documentation for specifics)

Definition at line 248 of file geoMeshBase.H.

248  {
249  return static_cast<VTKCellType>(_geoMesh.mesh->GetCellType(cellId));
250  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getElemBlock()

std::vector< vtkIdType > NEM::MSH::exoGeoMesh::getElemBlock ( int  blockId) const
Parameters
blockIdID of an element block
Returns
Indices of all cells that belong to blockID

Definition at line 869 of file exoGeoMesh.C.

References _elemBlocks, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), and NEM::MSH::geoMeshBase::GeoMesh::mesh.

869  {
870  auto blockIt = _elemBlocks.find(blockId);
871  if (blockIt == _elemBlocks.end()) {
872  std::cerr << "No block found with id: " << blockId << std::endl;
873  exit(1);
874  }
875  std::vector<vtkIdType> cellIdxList;
876  auto elemBlockIdArr = vtkIntArray::FastDownCast(
877  getGeoMesh().mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
878  for (vtkIdType i = 0; i < getGeoMesh().mesh->GetNumberOfCells(); ++i) {
879  if (elemBlockIdArr->GetValue(i) == blockId) {
880  cellIdxList.emplace_back(i);
881  }
882  }
883  return cellIdxList;
884 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::shared_ptr< meshBase > mesh
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ getElemBlockId()

int NEM::MSH::exoGeoMesh::getElemBlockId ( vtkIdType  cellIdx) const
Parameters
cellIdx0-based index of a cell
Returns
block ID that the cell belongs to; -1 if not found

Definition at line 886 of file exoGeoMesh.C.

References getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), and NEM::MSH::geoMeshBase::GeoMesh::mesh.

886  {
887  auto mesh = getGeoMesh().mesh;
888  if (!mesh || mesh->GetNumberOfCells() == 0) {
889  std::cerr << "Mesh is empty. No cells to find" << std::endl;
890  return -1;
891  }
892  if (cellIdx < 0 || cellIdx >= mesh->GetNumberOfCells()) {
893  std::cerr << "No cell found with index: " << cellIdx << std::endl;
894  return -1;
895  }
896  auto elemBlockIdArr = vtkIntArray::FastDownCast(
897  mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
898  return elemBlockIdArr->GetValue(cellIdx);
899 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
std::shared_ptr< meshBase > mesh
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ getElemBlockIds()

std::vector< int > NEM::MSH::exoGeoMesh::getElemBlockIds ( ) const
Returns
All element block IDs.

Definition at line 860 of file exoGeoMesh.C.

References _elemBlocks.

860  {
861  std::vector<int> ids;
862  ids.reserve(_elemBlocks.size());
863  for (const auto &elemBlock : _elemBlocks) {
864  ids.emplace_back(elemBlock.first);
865  }
866  return ids;
867 }
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ getElemBlockName()

const std::string & NEM::MSH::exoGeoMesh::getElemBlockName ( int  id) const
Parameters
idID of the element block
Returns
reference to block name

Definition at line 840 of file exoGeoMesh.C.

References _elemBlocks.

840  {
841  auto it = _elemBlocks.find(id);
842  if (it == _elemBlocks.end()) {
843  std::cerr << "No block found with id: " << id << std::endl;
844  exit(1);
845  } else {
846  return it->second.name;
847  }
848 }
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ getElemBlockNames()

std::map< int, std::string > NEM::MSH::exoGeoMesh::getElemBlockNames ( ) const
Returns
element block names, indexed by ID

Definition at line 829 of file exoGeoMesh.C.

References _elemBlocks.

829  {
830  std::map<int, std::string> names;
831  std::transform(_elemBlocks.begin(), _elemBlocks.end(),
832  std::inserter(names, names.begin()),
833  [](const decltype(_elemBlocks)::value_type &block)
834  -> decltype(names)::value_type {
835  return {block.first, block.second.name};
836  });
837  return names;
838 }
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ getElemBlockProperty()

int NEM::MSH::exoGeoMesh::getElemBlockProperty ( const std::string &  propName,
int  blockId 
) const
Parameters
propNameName of an element block property
blockIdID of an element block
Returns
Value of a property on an element block

Definition at line 1053 of file exoGeoMesh.C.

References _elemBlockPropNames, and _elemBlocks.

Referenced by reconstructGeo(), and setPhysGrpPropertyName().

1054  {
1055  if (_elemBlockPropNames.find(propName) == _elemBlockPropNames.end()) {
1056  std::cerr << "No property found with name: " << propName << std::endl;
1057  exit(1);
1058  }
1059  auto blockIt = _elemBlocks.find(blockId);
1060  if (blockIt == _elemBlocks.end()) {
1061  std::cerr << "No block found with id: " << blockId << std::endl;
1062  exit(1);
1063  } else {
1064  auto it = blockIt->second.properties.find(propName);
1065  if (it == blockIt->second.properties.end()) {
1066  return 0;
1067  } else {
1068  return it->second;
1069  }
1070  }
1071 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ getElemBlockPropertyNames()

std::vector< std::string > NEM::MSH::exoGeoMesh::getElemBlockPropertyNames ( ) const
Returns
Names of all element block properties

Definition at line 1047 of file exoGeoMesh.C.

References _elemBlockPropNames.

1047  {
1048  std::vector<std::string> names;
1049  names.assign(_elemBlockPropNames.begin(), _elemBlockPropNames.end());
1050  return names;
1051 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391

◆ getExoIdArrName()

const char * NEM::MSH::exoGeoMesh::getExoIdArrName ( )
staticprivate

◆ getExoReader()

vtkSmartPointer< vtkExodusIIReader > NEM::MSH::exoGeoMesh::getExoReader ( const std::string &  fileName,
int  timeStep = 1 
)
staticprivate

Definition at line 1605 of file exoGeoMesh.C.

References NEM::MSH::New().

1606  {
1607  static constexpr std::array<vtkExodusIIReader::ObjectType, 8> objectTypes = {
1608  vtkExodusIIReader::ObjectType::ELEM_BLOCK_ELEM_CONN,
1609  vtkExodusIIReader::ObjectType::NODE_SET_CONN,
1610  vtkExodusIIReader::ObjectType::SIDE_SET_CONN,
1611  vtkExodusIIReader::ObjectType::NODAL,
1612  vtkExodusIIReader::ObjectType::GLOBAL,
1613  vtkExodusIIReader::ObjectType::ELEM_BLOCK,
1614  vtkExodusIIReader::ObjectType::NODE_SET,
1615  vtkExodusIIReader::ObjectType::SIDE_SET};
1616  if (fileName.empty()) {
1617  return nullptr;
1618  }
1620  reader->SetFileName(fileName.c_str());
1621  // time steps are 1-indexed in Exodus
1622  reader->SetTimeStep(timeStep - 1);
1623  reader->UpdateInformation();
1624  for (const auto &objectType : objectTypes) {
1625  reader->SetAllArrayStatus(objectType, 1);
1626  }
1627  for (int i = 0; i < reader->GetNumberOfNodeMapArrays(); ++i) {
1628  reader->SetNodeMapArrayStatus(reader->GetNodeMapArrayName(i), 0);
1629  }
1630  for (int i = 0; i < reader->GetNumberOfElementMapArrays(); ++i) {
1631  reader->SetElementMapArrayStatus(reader->GetElementMapArrayName(i), 0);
1632  }
1633  reader->GenerateGlobalElementIdArrayOn();
1634  reader->GenerateGlobalNodeIdArrayOn();
1635  reader->Update();
1636  return reader;
1637 }
geoMeshBase * New(MeshType meshType)
Create a new mesh object.

◆ getFieldDataArrayCopy() [1/4]

void NEM::MSH::geoMeshBase::getFieldDataArrayCopy ( const std::string &  arrayName,
vtkAbstractArray *  array,
int *  arrayIdx = nullptr 
) const
inherited

Optionally, get array index.

Parameters
arrayNamearray name
arrayfield data array
arrayIdxarray index

Definition at line 201 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

203  {
204  getArrCopy(_geoMesh.mesh->GetFieldData(), arrayName, arrayIdx, array);
205 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getFieldDataArrayCopy() [2/4]

vtkSmartPointer< vtkAbstractArray > NEM::MSH::geoMeshBase::getFieldDataArrayCopy ( const std::string &  arrayName,
int *  arrayIdx = nullptr 
) const
inherited

Optionally, get array index.

Parameters
arrayNamearray name
arrayIdxarray index
Returns
pointer to copy of array

Definition at line 207 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

208  {
209  return getArrCopy(_geoMesh.mesh->GetFieldData(), arrayName, arrayIdx);
210 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getFieldDataArrayCopy() [3/4]

void NEM::MSH::geoMeshBase::getFieldDataArrayCopy ( int  arrayIdx,
vtkAbstractArray *  array 
) const
inherited
Parameters
arrayIdxarray index
arrayfield data array

Definition at line 212 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

213  {
214  getArrCopy(_geoMesh.mesh->GetFieldData(), arrayIdx, array);
215 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getFieldDataArrayCopy() [4/4]

vtkSmartPointer< vtkAbstractArray > NEM::MSH::geoMeshBase::getFieldDataArrayCopy ( int  arrayIdx) const
inherited
Parameters
arrayIdxarray index
Returns
pointer to copy of array

Definition at line 217 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

218  {
219  return getArrCopy(_geoMesh.mesh->GetFieldData(), arrayIdx);
220 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getGeoEntArrayName()

const std::string& NEM::MSH::geoMeshBase::getGeoEntArrayName ( ) const
inlineinherited
Returns
name of geometric entities array

Definition at line 157 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

157 { return _geoMesh.link; }

◆ getGeoMesh()

◆ getNodeSet()

const std::vector< vtkIdType > & NEM::MSH::exoGeoMesh::getNodeSet ( int  nodeSetId) const
Parameters
nodeSetIdID of a node set
Returns
Vector of (0-based) node indices of the nodes in the node set.

Definition at line 1248 of file exoGeoMesh.C.

References _nodeSets.

1248  {
1249  auto it = _nodeSets.find(nodeSetId);
1250  if (it == _nodeSets.end()) {
1251  std::cerr << "No node set found with id: " << nodeSetId << std::endl;
1252  exit(1);
1253  }
1254  return it->second.nodes;
1255 }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ getNodeSetIds()

std::vector< int > NEM::MSH::exoGeoMesh::getNodeSetIds ( ) const
Returns
All node set IDs

Definition at line 1239 of file exoGeoMesh.C.

References _nodeSets.

1239  {
1240  std::vector<int> ids;
1241  ids.reserve(_nodeSets.size());
1242  for (const auto &nodeSet : _nodeSets) {
1243  ids.emplace_back(nodeSet.first);
1244  }
1245  return ids;
1246 }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ getNodeSetName()

const std::string & NEM::MSH::exoGeoMesh::getNodeSetName ( int  id) const
Parameters
idID of a node set
Returns
Reference to the name of a node set

Definition at line 1219 of file exoGeoMesh.C.

References _nodeSets.

1219  {
1220  auto it = _nodeSets.find(id);
1221  if (it == _nodeSets.end()) {
1222  std::cerr << "No side set found with id: " << id << std::endl;
1223  exit(1);
1224  } else {
1225  return it->second.name;
1226  }
1227 }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ getNodeSetNames()

std::map< int, std::string > NEM::MSH::exoGeoMesh::getNodeSetNames ( ) const
Returns
node set names, indexed by ID

Definition at line 1209 of file exoGeoMesh.C.

References _nodeSets.

1209  {
1210  std::map<int, std::string> names;
1211  std::transform(_nodeSets.begin(), _nodeSets.end(),
1212  std::inserter(names, names.begin()),
1213  [](const std::pair<int, nodeSet> &set) {
1214  return std::make_pair(set.first, set.second.name);
1215  });
1216  return names;
1217 }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ getNumberOfCellDataArrays()

int NEM::MSH::geoMeshBase::getNumberOfCellDataArrays ( ) const
inlineinherited
Returns
number of arrays in the cell data

Definition at line 318 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

318  {
319  return _geoMesh.mesh->GetCellData()->GetNumberOfArrays();
320  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getNumberOfCells()

nemId_t NEM::MSH::geoMeshBase::getNumberOfCells ( ) const
inlineinherited
Returns
number of cells in mesh

Definition at line 190 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

190 { return _geoMesh.mesh->GetNumberOfCells(); }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getNumberOfFieldDataArrays()

int NEM::MSH::geoMeshBase::getNumberOfFieldDataArrays ( ) const
inlineinherited
Returns
number of arrays in the field data

Definition at line 355 of file geoMeshBase.H.

355  {
356  return _geoMesh.mesh->GetFieldData()->GetNumberOfArrays();
357  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getNumberOfPointDataArrays()

int NEM::MSH::geoMeshBase::getNumberOfPointDataArrays ( ) const
inlineinherited
Returns
number of arrays in the point data

Definition at line 281 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

281  {
282  return _geoMesh.mesh->GetPointData()->GetNumberOfArrays();
283  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getNumberOfPoints()

nemId_t NEM::MSH::geoMeshBase::getNumberOfPoints ( ) const
inlineinherited
Returns
number of points in mesh

Definition at line 183 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

183  {
184  return _geoMesh.mesh->GetNumberOfPoints();
185  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getNumElemBlocks()

int NEM::MSH::exoGeoMesh::getNumElemBlocks ( ) const
Returns
number of element blocks

Definition at line 827 of file exoGeoMesh.C.

References _elemBlocks.

827 { return _elemBlocks.size(); }
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ getNumNodeSets()

int NEM::MSH::exoGeoMesh::getNumNodeSets ( ) const
Returns
number of node sets

Definition at line 1207 of file exoGeoMesh.C.

References _nodeSets.

1207 { return _nodeSets.size(); }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ getNumSideSets()

int NEM::MSH::exoGeoMesh::getNumSideSets ( ) const
Returns
number of side sets

Definition at line 1088 of file exoGeoMesh.C.

References _sideSetNames.

1088 { return _sideSetNames.size(); }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389

◆ getPhysGrpPropertyName()

const std::string & NEM::MSH::exoGeoMesh::getPhysGrpPropertyName ( ) const
Returns
Name of element block property mapping element blocks to physical groups (or empty string if not set)

Definition at line 1275 of file exoGeoMesh.C.

References _physGrpName.

1275  {
1276  return _physGrpName;
1277 }
std::string _physGrpName
Definition: exoGeoMesh.H:392

◆ getPoint() [1/2]

void NEM::MSH::geoMeshBase::getPoint ( nemId_t  id,
std::array< double, 3 > *  x 
) const
inlineinherited
Parameters
idpoint id
xarray of coordinates as (x,y,z)

Definition at line 196 of file geoMeshBase.H.

Referenced by NEM::MSH::diffMesh().

196  {
197  _geoMesh.mesh->GetPoint(id, x->data());
198  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getPoint() [2/2]

std::array<double, 3> NEM::MSH::geoMeshBase::getPoint ( nemId_t  id) const
inlineinherited
Parameters
idpoint id
Returns
array of coordinates as (x,y,z)

Definition at line 204 of file geoMeshBase.H.

204  {
205  std::array<double, 3> x{};
206  getPoint(id, &x);
207  return x;
208  }
void getPoint(nemId_t id, std::array< double, 3 > *x) const
Get the coordinate of a point.
Definition: geoMeshBase.H:196

◆ getPointCells()

void NEM::MSH::geoMeshBase::getPointCells ( nemId_t  ptId,
vtkIdList *  cellIds 
) const
inlineinherited
Parameters
ptIdpoint id
cellIdslist of cell ids

Definition at line 264 of file geoMeshBase.H.

264  {
265  _geoMesh.mesh->GetPointCells(ptId, cellIds);
266  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getPointDataArrayCopy() [1/4]

void NEM::MSH::geoMeshBase::getPointDataArrayCopy ( const std::string &  arrayName,
vtkAbstractArray *  array,
int *  arrayIdx = nullptr 
) const
inherited

Optionally, get array index.

Parameters
arrayNamearray name
arraypoint data array
arrayIdxarray index

Definition at line 159 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

Referenced by NEM::MSH::diffMesh().

161  {
162  getArrCopy(_geoMesh.mesh->GetPointData(), arrayName, arrayIdx, array);
163 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getPointDataArrayCopy() [2/4]

vtkSmartPointer< vtkAbstractArray > NEM::MSH::geoMeshBase::getPointDataArrayCopy ( const std::string &  arrayName,
int *  arrayIdx = nullptr 
) const
inherited

Optionally, get array index.

Parameters
arrayNamearray name
arrayIdxarray index
Returns
pointer to copy of array

Definition at line 165 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

166  {
167  return getArrCopy(_geoMesh.mesh->GetPointData(), arrayName, arrayIdx);
168 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getPointDataArrayCopy() [3/4]

void NEM::MSH::geoMeshBase::getPointDataArrayCopy ( int  arrayIdx,
vtkAbstractArray *  array 
) const
inherited
Parameters
arrayIdxarray index
arraypoint data array

Definition at line 170 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

171  {
172  getArrCopy(_geoMesh.mesh->GetPointData(), arrayIdx, array);
173 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getPointDataArrayCopy() [4/4]

vtkSmartPointer< vtkAbstractArray > NEM::MSH::geoMeshBase::getPointDataArrayCopy ( int  arrayIdx) const
inherited
Parameters
arrayIdxarray index
Returns
pointer to copy of array

Definition at line 175 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

176  {
177  return getArrCopy(_geoMesh.mesh->GetPointData(), arrayIdx);
178 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ getSideSet()

std::pair< std::vector< vtkIdType >, std::vector< int > > NEM::MSH::exoGeoMesh::getSideSet ( int  sideSetId) const
Parameters
sideSetIdID of a side set
Returns
Pair of vectors, first of which contains the (0-based) index of the cell the side belongs to and the second contains the side (according to VTK face/edge ordering)

Definition at line 1123 of file exoGeoMesh.C.

References _sideSetNames, getExoIdArrName(), and NEM::MSH::geoMeshBase::getGeoMesh().

1124  {
1125  std::vector<vtkIdType> cellIdVec;
1126  std::vector<int> sideVec;
1127  if (_sideSetNames.find(sideSetId) == _sideSetNames.end()) {
1128  std::cerr << "No side set found with id: " << sideSetId << std::endl;
1129  }
1130  auto geoMesh = getGeoMesh();
1131  auto sideSet = geoMesh.sideSet;
1132  auto sideSetExoId = vtkIntArray::FastDownCast(
1133  sideSet.sides->GetCellData()->GetAbstractArray(getExoIdArrName()));
1134  auto sideSetOrigCellId = geoMesh.sideSet.getOrigCellArr();
1135  auto sideSetCellFaceId = geoMesh.sideSet.getCellFaceArr();
1136  for (vtkIdType i = 0; i < sideSet.sides->GetNumberOfCells(); ++i) {
1137  if (sideSetExoId->GetValue(i) == sideSetId) {
1138  cellIdVec.emplace_back(sideSetOrigCellId->GetTypedComponent(i, 0));
1139  sideVec.emplace_back(sideSetCellFaceId->GetTypedComponent(i, 0));
1140  }
1141  }
1142  return {cellIdVec, sideVec};
1143 }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ getSideSetIds()

std::vector< int > NEM::MSH::exoGeoMesh::getSideSetIds ( ) const
Returns
All side set IDs.

Definition at line 1114 of file exoGeoMesh.C.

References _sideSetNames.

1114  {
1115  std::vector<int> ids;
1116  ids.reserve(_sideSetNames.size());
1117  for (const auto &sideSet : _sideSetNames) {
1118  ids.emplace_back(sideSet.first);
1119  }
1120  return ids;
1121 }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389

◆ getSideSetName()

const std::string & NEM::MSH::exoGeoMesh::getSideSetName ( int  id) const
Parameters
idID of a side set
Returns
Reference to the name of a side set

Definition at line 1094 of file exoGeoMesh.C.

References _sideSetNames.

1094  {
1095  auto it = _sideSetNames.find(id);
1096  if (it == _sideSetNames.end()) {
1097  std::cerr << "No side set found with id: " << id << std::endl;
1098  exit(1);
1099  } else {
1100  return it->second;
1101  }
1102 }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389

◆ getSideSetNames()

const std::map< int, std::string > & NEM::MSH::exoGeoMesh::getSideSetNames ( ) const
Returns
side set names, indexed by ID

Definition at line 1090 of file exoGeoMesh.C.

References _sideSetNames.

1090  {
1091  return _sideSetNames;
1092 }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389

◆ getSS()

vtkSmartPointer<vtkPolyData> NEM::MSH::exoGeoMesh::getSS ( )
inline

Definition at line 58 of file exoGeoMesh.H.

References NEM::MSH::New(), nodes, NEM::MSH::Read(), and sides.

58 { return getGeoMesh().sideSet.sides; }
vtkSmartPointer< vtkPolyData > sides
Cells represent edges/faces of some GeoMesh.
Definition: geoMeshBase.H:399
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ getTitle()

const std::string & NEM::MSH::exoGeoMesh::getTitle ( ) const
Returns
reference to title

Definition at line 823 of file exoGeoMesh.C.

References _title.

823 { return _title; }
std::string _title
Definition: exoGeoMesh.H:387

◆ mergeGeoMesh()

void NEM::MSH::geoMeshBase::mergeGeoMesh ( geoMeshBase otherGeoMesh)
virtualinherited

Deletes the data from the new geoMesh pointer

Parameters
otherGeoMeshA new geoMesh data to merge

Definition at line 113 of file geoMeshBase.C.

References NEM::MSH::geoMeshBase::_geoMesh, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::New(), and NEM::MSH::geoMeshBase::resetNative().

113  {
114  vtkSmartPointer<vtkAppendFilter> appendFilter =
116  appendFilter->AddInputData(_geoMesh.mesh);
117  appendFilter->AddInputData(otherGeoMesh->_geoMesh.mesh);
118  appendFilter->MergePointsOn();
119  appendFilter->Update();
120  _geoMesh.mesh = appendFilter->GetOutput();
121  otherGeoMesh->_geoMesh = {
123  otherGeoMesh->resetNative();
124 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
virtual void resetNative()=0

◆ New()

static exoGeoMesh* NEM::MSH::exoGeoMesh::New ( )
static

◆ reassignCells()

int NEM::MSH::exoGeoMesh::reassignCells ( const std::vector< vtkIdType > &  cells,
int  blockId = -1,
const std::string &  elemBlockName = {} 
)

Cells must all have same cell type. May result in empty blocks. Invalidates geometry, if any.

Parameters
cellsvector of cell indices
blockIdid of block to assign to; if not an existing block, one is created (if blockId is positive, the new block will have that ID; otherwise, one is chosen)
elemBlockNameif blockId is not an existing block, the name of the new block
Returns
element block that the cells were assigned to

Definition at line 1001 of file exoGeoMesh.C.

References _elemBlocks, cellType, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), nemAux::leastUnusedKey(), mesh, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::geoMeshBase::setGeoMesh(), and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

1002  {
1003  if (!cells.empty()) {
1004  auto mesh = getGeoMesh().mesh;
1005  auto cellType =
1006  static_cast<VTKCellType>(mesh->GetCellType(cells.front()));
1007  for (const auto &cell : cells) {
1008  if (mesh->GetCellType(cell) != cellType) {
1009  std::cerr << "Single element block cannot have multiple cell types"
1010  << std::endl;
1011  exit(1);
1012  }
1013  }
1014  auto elemBlockIt = _elemBlocks.find(blockId);
1015  if (elemBlockIt == _elemBlocks.end()) {
1016  if (blockId <= 0) {
1018  }
1019  _elemBlocks[blockId] = {elemBlockName, cellType, {}};
1020  }
1021  auto elemBlockIdArr = vtkIntArray::FastDownCast(
1022  mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
1023  for (const auto &cell : cells) {
1024  elemBlockIdArr->SetValue(cell, blockId);
1025  }
1026 #ifdef HAVE_GMSH
1027  if (!getGeoMesh().geo.empty()) {
1028  gmsh::model::setCurrent(getGeoMesh().geo);
1029  gmsh::model::remove();
1030  setGeoMesh({mesh, "", "", getGeoMesh().sideSet});
1031  }
1032 #endif
1033  return blockId;
1034  } else {
1035  std::cerr << "No cells to add." << std::endl;
1036  return -1;
1037  }
1038 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
A leastUnusedKey(const std::map< A, B > &map, A min=1)
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
VTKCellType cellType
Definition: inpGeoMesh.C:129
std::shared_ptr< meshBase > mesh
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ reconstructGeo()

void NEM::MSH::exoGeoMesh::reconstructGeo ( )
overridevirtual

Sets geometry, link, and side set. Does not alter the mesh. If physGrpName is not empty, then physical groups are set based on the property physGrpName for each element block. Otherwise, each element block represents its own physical group.

Reimplemented from NEM::MSH::geoMeshBase.

Definition at line 796 of file exoGeoMesh.C.

References _physGrpName, NEM::MSH::geoMeshBase::GeoMesh::geo, NEM::MSH::geoMeshBase::GEO_ENT_DEFAULT_NAME, getElemBlockProperty(), getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::geoMeshBase::GeoMesh::link, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::New(), NEM::MSH::geoMeshBase::reconstructGeo(), NEM::MSH::geoMeshBase::setGeoMesh(), setSideSetObjId(), and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

796  {
797  std::string link =
799  auto mesh = getGeoMesh().mesh;
800  vtkSmartPointer<vtkDataArray> linkArr =
801  mesh->GetCellData()->GetArray(link.c_str());
802  if (!linkArr) {
804  linkArr->SetName(link.c_str());
805  linkArr->SetNumberOfTuples(mesh->GetNumberOfCells());
806  mesh->GetCellData()->AddArray(linkArr);
807  }
808  auto elemBlockIdArr = vtkIntArray::FastDownCast(
809  mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
810  for (vtkIdType i = 0; i < mesh->GetNumberOfCells(); ++i) {
811  auto physGroup = elemBlockIdArr->GetValue(i);
812  if (!_physGrpName.empty()) {
813  physGroup = getElemBlockProperty(_physGrpName, physGroup);
814  }
815  linkArr->SetComponent(i, 0, physGroup);
816  }
819  // Should now always have side set
820  setSideSetObjId();
821 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
virtual void reconstructGeo()
Construct the geometry from the mesh alone.
int getElemBlockProperty(const std::string &propName, int blockId) const
Get the value of an element block property on a block.
Definition: exoGeoMesh.C:1053
static constexpr auto GEO_ENT_DEFAULT_NAME
Definition: geoMeshBase.H:446
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
void setSideSetObjId()
Sets the (Exodus) side set IDs of each cell in the GeoMesh.sideSet by creating a side set for each pa...
Definition: exoGeoMesh.C:1709
std::shared_ptr< meshBase > mesh
std::string _physGrpName
Definition: exoGeoMesh.H:392
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ report()

void NEM::MSH::exoGeoMesh::report ( std::ostream &  out) const
overridevirtual
Parameters
outStream to write summary to.

Implements NEM::MSH::geoMeshBase.

Definition at line 770 of file exoGeoMesh.C.

References _elemBlocks, _nodeSets, _sideSetNames, _title, and NEM::MSH::geoMeshBase::report().

770  {
771  geoMeshBase::report(out);
772  out << "Title:\t" << _title << '\n';
773  out << "Element Blocks:\t" << _elemBlocks.size() << '\n';
774  out << "Side Sets:\t" << _sideSetNames.size() << '\n';
775  out << "Node Sets:\t" << _nodeSets.size() << '\n';
776 }
std::string _title
Definition: exoGeoMesh.H:387
virtual void report(std::ostream &out) const =0
Print a report about the mesh.
Definition: geoMeshBase.C:97
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ resetElemBlocks()

void NEM::MSH::exoGeoMesh::resetElemBlocks ( )
private

Creates element blocks and sets the dimension based on the GeoMesh.

Definition at line 1667 of file exoGeoMesh.C.

References _elemBlockPropNames, _elemBlocks, _physGrpName, cellType, NEM::MSH::exoGeoMesh::elemBlock::cellType, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), nemAux::leastUnusedKey(), NEM::MSH::geoMeshBase::GeoMesh::mesh, and NEM::MSH::exoGeoMesh::elemBlock::properties.

Referenced by resetNative().

1667  {
1668  _elemBlocks.clear();
1669  _elemBlockPropNames.clear();
1670  if (!_physGrpName.empty()) {
1672  }
1673  std::map<std::pair<int, VTKCellType>, int> old2newElemBlock;
1674  auto mesh = getGeoMesh().mesh;
1675  auto elemBlockIds = vtkIntArray::SafeDownCast(
1676  mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
1677  vtkIdType i = 0;
1678  auto nextElemBlockId = nemAux::leastUnusedKey(_elemBlocks);
1679  for (auto it =
1680  vtkSmartPointer<vtkCellIterator>::Take(mesh->NewCellIterator());
1681  !it->IsDoneWithTraversal(); it->GoToNextCell()) {
1682  auto oldElemBlockId = elemBlockIds->GetValue(i);
1683  auto cellType = static_cast<VTKCellType>(it->GetCellType());
1684  auto inserted =
1685  old2newElemBlock.insert({{oldElemBlockId, cellType}, nextElemBlockId});
1686  if (inserted.second) {
1687  auto &elemBlock = _elemBlocks[nextElemBlockId];
1688  elemBlock.cellType = cellType;
1689  if (!_physGrpName.empty()) {
1690  elemBlock.properties[_physGrpName] = oldElemBlockId;
1691  }
1692  nextElemBlockId = nemAux::leastUnusedKey(_elemBlocks);
1693  }
1694  elemBlockIds->SetValue(i, inserted.first->second);
1695  ++i;
1696  }
1697 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
A leastUnusedKey(const std::map< A, B > &map, A min=1)
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
VTKCellType cellType
Definition: inpGeoMesh.C:129
std::shared_ptr< meshBase > mesh
std::string _physGrpName
Definition: exoGeoMesh.H:392
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ resetNative()

void NEM::MSH::exoGeoMesh::resetNative ( )
overrideprivatevirtual

Implements NEM::MSH::geoMeshBase.

Definition at line 1639 of file exoGeoMesh.C.

References _nodeSets, _physGrpName, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::geoMeshBase::GeoMesh::link, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::New(), resetElemBlocks(), NEM::MSH::geoMeshBase::setGeoMesh(), and setSideSetObjId().

Referenced by addElemBlock().

1639  {
1640  _nodeSets.clear();
1641  auto mesh = this->getGeoMesh().mesh;
1642  auto link = this->getGeoMesh().link;
1643  _physGrpName = link;
1644  if (!mesh->GetCellData()->HasArray(getExoIdArrName())) {
1645  auto elemBlockIdArr = vtkSmartPointer<vtkIntArray>::New();
1646  elemBlockIdArr->SetName(getExoIdArrName());
1647  auto linkArr = mesh->GetCellData()->GetArray(link.c_str());
1648  if (!link.empty() && linkArr) {
1649  elemBlockIdArr->Allocate(mesh->GetNumberOfCells());
1650  for (vtkIdType i = 0; i < mesh->GetNumberOfCells(); ++i) {
1651  elemBlockIdArr->InsertNextValue(
1652  static_cast<int>(linkArr->GetComponent(i, 0)));
1653  }
1654  } else {
1655  elemBlockIdArr->SetNumberOfValues(mesh->GetNumberOfCells());
1656  elemBlockIdArr->FillComponent(0, 1);
1657  }
1658  mesh->GetCellData()->AddArray(elemBlockIdArr);
1659  }
1660  resetElemBlocks();
1661  auto gm = getGeoMesh();
1662  gm.findSide2OrigCell();
1663  setGeoMesh(gm);
1664  setSideSetObjId();
1665 }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void resetElemBlocks()
Clears element block names, element block properties.
Definition: exoGeoMesh.C:1667
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390
void setSideSetObjId()
Sets the (Exodus) side set IDs of each cell in the GeoMesh.sideSet by creating a side set for each pa...
Definition: exoGeoMesh.C:1709
std::shared_ptr< meshBase > mesh
std::string _physGrpName
Definition: exoGeoMesh.H:392
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ resetNodeSetPoints()

void NEM::MSH::exoGeoMesh::resetNodeSetPoints ( vtkIdTypeArray *  nodeMap = nullptr)
private

Removes duplicate node ids within a node set.

Parameters
nodeMapmap from old to new node indices (can be many-to-one)

Definition at line 1699 of file exoGeoMesh.C.

References _nodeSets, and NEM::MSH::exoGeoMesh::nodeSet::nodes.

Referenced by addCellsToBlock(), stitch(), and write().

1699  {
1700  for (auto &nodeSet : _nodeSets) {
1701  std::unordered_set<vtkIdType> set;
1702  for (const auto &node : nodeSet.second.nodes) {
1703  set.insert(nodeMap ? nodeMap->GetValue(node) : node);
1704  }
1705  nodeSet.second.nodes.assign(set.begin(), set.end());
1706  }
1707 }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ scaleNodes()

void NEM::MSH::exoGeoMesh::scaleNodes ( double  scale)

Does not change point data.

Parameters
scaleMultiplicative factor for point locations

Definition at line 1457 of file exoGeoMesh.C.

References NEM::MSH::geoMeshBase::GeoMesh::geo, NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::geoMeshBase::GeoMesh::link, mesh, NEM::MSH::New(), NEM::MSH::geoMeshBase::setGeoMesh(), NEM::MSH::geoMeshBase::SideSet::sides, and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

1457  {
1458  auto transform = vtkSmartPointer<vtkTransform>::New();
1459  transform->Scale(scale, scale, scale);
1460  auto transformFilter = vtkSmartPointer<vtkTransformFilter>::New();
1461  transformFilter->SetTransform(transform);
1462  transformFilter->SetInputData(getGeoMesh().mesh);
1463  transformFilter->Update();
1464  auto mesh = vtkUnstructuredGrid::SafeDownCast(transformFilter->GetOutput());
1465  auto sideSet = getGeoMesh().sideSet;
1466  if (sideSet.sides) {
1467  sideSet.sides->SetPoints(mesh->GetPoints());
1468  }
1470 }
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
vtkSmartPointer< vtkPolyData > sides
Cells represent edges/faces of some GeoMesh.
Definition: geoMeshBase.H:399
std::shared_ptr< meshBase > mesh
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ setAngleThreshold()

void NEM::MSH::geoMeshBase::setAngleThreshold ( double  angleThreshold)
inlineinherited
Parameters
angleThreshold(in radians)

Definition at line 176 of file geoMeshBase.H.

176  {
177  _angleThreshold = angleThreshold;
178  }
double _angleThreshold
Dihedral angle threshold (in radians) to classify surfaces (Default: 30 degrees)
Definition: geoMeshBase.H:554

◆ setCellDataArray()

int NEM::MSH::geoMeshBase::setCellDataArray ( vtkAbstractArray *  array)
inlineprotectedinherited
Parameters
arrayarray pointer
Returns
array index

Definition at line 473 of file geoMeshBase.H.

473  {
474  return _geoMesh.mesh->GetCellData()->AddArray(array);
475  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ setElemBlockName()

void NEM::MSH::exoGeoMesh::setElemBlockName ( int  id,
const std::string &  name 
)
Parameters
idID of the element block
namenew name of the element block

Definition at line 850 of file exoGeoMesh.C.

References _elemBlocks.

850  {
851  auto it = _elemBlocks.find(id);
852  if (it == _elemBlocks.end()) {
853  std::cerr << "No block found with id: " << id << std::endl;
854  exit(1);
855  } else {
856  it->second.name = name;
857  }
858 }
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ setElemBlockProperty()

void NEM::MSH::exoGeoMesh::setElemBlockProperty ( const std::string &  propName,
int  blockId,
int  value 
)
Parameters
propNameName of an element block property
blockIdID of an element block
valueValue of a property on an element block

Definition at line 1073 of file exoGeoMesh.C.

References _elemBlockPropNames, and _elemBlocks.

1074  {
1075  if (_elemBlockPropNames.find(propName) == _elemBlockPropNames.end()) {
1076  std::cerr << "No property found with name: " << propName << std::endl;
1077  exit(1);
1078  }
1079  auto blockIt = _elemBlocks.find(blockId);
1080  if (blockIt == _elemBlocks.end()) {
1081  std::cerr << "No block found with id: " << blockId << std::endl;
1082  exit(1);
1083  } else {
1084  blockIt->second.properties[propName] = value;
1085  }
1086 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388

◆ setFieldDataArray()

int NEM::MSH::geoMeshBase::setFieldDataArray ( vtkAbstractArray *  array)
inlineprotectedinherited
Parameters
arrayarray pointer
Returns
array index

Definition at line 481 of file geoMeshBase.H.

481  {
482  return _geoMesh.mesh->GetFieldData()->AddArray(array);
483  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ setGeoEntArrayName()

void NEM::MSH::geoMeshBase::setGeoEntArrayName ( const std::string &  geoEntArrayName)
inlineinherited
Parameters
geoEntArrayNamename of geometric entities array

Definition at line 162 of file geoMeshBase.H.

162  {
163  auto a = _geoMesh.mesh->GetCellData()->GetArray(_geoMesh.link.c_str());
164  if (a) a->SetName(geoEntArrayName.c_str());
165  _geoMesh.link = geoEntArrayName;
166  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ setGeoMesh()

void NEM::MSH::geoMeshBase::setGeoMesh ( const geoMeshBase::GeoMesh geoMesh)
inlineprotectedinherited
Parameters
geoMesha mesh and geometry

Definition at line 538 of file geoMeshBase.H.

References NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::geoMeshBase::SideSet::sides, and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

Referenced by addCellsToBlock(), addElemBlock(), addSideSet(), reassignCells(), reconstructGeo(), NEM::MSH::gmshGeoMesh::resetNative(), resetNative(), scaleNodes(), NEM::MSH::foamGeoMesh::setFoamMesh(), NEM::MSH::oshGeoMesh::setOshMesh(), NEM::MSH::smeshGeoMesh::setSMeshMesh(), NEM::MSH::vtkGeoMesh::setVtkMesh(), stitch(), NEM::MSH::oshGeoMesh::takeGeoMesh(), and takeGeoMesh().

538  {
539  assert(geoMesh.mesh->GetNumberOfCells() == 0 ||
540  geoMesh.mesh->GetNumberOfPoints() == 0 ||
541  geoMesh.sideSet.sides == nullptr ||
542  geoMesh.sideSet.sides->GetPoints() == geoMesh.mesh->GetPoints());
543  _geoMesh = geoMesh;
544  }

◆ setNodeSetName()

void NEM::MSH::exoGeoMesh::setNodeSetName ( int  id,
const std::string &  name 
)
Parameters
idID of a node set
nameNew name of the node set

Definition at line 1229 of file exoGeoMesh.C.

References _nodeSets.

1229  {
1230  auto it = _nodeSets.find(id);
1231  if (it == _nodeSets.end()) {
1232  std::cerr << "No side set found with id: " << id << std::endl;
1233  exit(1);
1234  } else {
1235  it->second.name = name;
1236  }
1237 }
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390

◆ setPhysGrpPropertyName()

void NEM::MSH::exoGeoMesh::setPhysGrpPropertyName ( const std::string &  physGrpName)
Parameters
physGrpNameName of element block property mapping element blocks to physical groups (use empty string to unset). Must be an existing element block property name.

Definition at line 1279 of file exoGeoMesh.C.

References _elemBlockPropNames, _physGrpName, getElemBlockProperty(), getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::geoMeshBase::GeoMesh::link, and NEM::MSH::geoMeshBase::GeoMesh::mesh.

1279  {
1280  if (_elemBlockPropNames.find(physGrpName) == _elemBlockPropNames.end()) {
1281  std::cerr << "No property found with name " << physGrpName << std::endl;
1282  return;
1283  }
1284  _physGrpName = physGrpName;
1285  auto link = getGeoMesh().link;
1286  if (!link.empty()) {
1287  auto mesh = getGeoMesh().mesh;
1288  auto elemBlockIdArr = vtkIntArray::FastDownCast(
1289  mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
1290  auto linkArr = mesh->GetCellData()->GetArray(link.c_str());
1291  if (linkArr) {
1292  for (vtkIdType i = 0; i < mesh->GetNumberOfCells(); ++i) {
1293  linkArr->SetComponent(
1294  i, 0,
1295  getElemBlockProperty(_physGrpName, elemBlockIdArr->GetValue(i)));
1296  }
1297  }
1298  }
1299 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
int getElemBlockProperty(const std::string &propName, int blockId) const
Get the value of an element block property on a block.
Definition: exoGeoMesh.C:1053
std::shared_ptr< meshBase > mesh
std::string _physGrpName
Definition: exoGeoMesh.H:392
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ setPointDataArray()

int NEM::MSH::geoMeshBase::setPointDataArray ( vtkAbstractArray *  array)
inlineprotectedinherited
Parameters
arrayarray pointer
Returns
array index

Definition at line 465 of file geoMeshBase.H.

465  {
466  return _geoMesh.mesh->GetPointData()->AddArray(array);
467  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ setSideSetName()

void NEM::MSH::exoGeoMesh::setSideSetName ( int  id,
const std::string &  name 
)
Parameters
idID of a side set
nameNew name of the side set

Definition at line 1104 of file exoGeoMesh.C.

References _sideSetNames.

1104  {
1105  auto it = _sideSetNames.find(id);
1106  if (it == _sideSetNames.end()) {
1107  std::cerr << "No side set found with id: " << id << std::endl;
1108  exit(1);
1109  } else {
1110  it->second = name;
1111  }
1112 }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389

◆ setSideSetObjId()

void NEM::MSH::exoGeoMesh::setSideSetObjId ( )
private

Definition at line 1709 of file exoGeoMesh.C.

References _sideSetNames, getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), and NEM::MSH::New().

Referenced by reconstructGeo(), and resetNative().

1709  {
1710  _sideSetNames.clear();
1711  auto gm = getGeoMesh();
1712  auto mesh = gm.mesh;
1713  auto link = gm.link;
1714  auto sideSet = gm.sideSet;
1715  if (sideSet.sides) {
1716  auto sideSetObjId = vtkIntArray::FastDownCast(
1717  sideSet.sides->GetCellData()->GetAbstractArray(getExoIdArrName()));
1718  if (sideSetObjId) {
1719  for (vtkIdType i = 0; i < sideSet.sides->GetNumberOfCells(); ++i) {
1720  _sideSetNames[sideSetObjId->GetValue(i)];
1721  }
1722  } else {
1723  sideSetObjId = vtkIntArray::New();
1724  sideSetObjId->SetName(getExoIdArrName());
1725  sideSetObjId->Allocate(sideSet.sides->GetNumberOfCells());
1726  sideSet.sides->GetCellData()->AddArray(sideSetObjId);
1727  auto sideSetEntities = gm.sideSet.getGeoEntArr();
1728  auto nameArr = sideSet.getSideSetNames();
1729  // Exodus II requires IDs to be positive, which is not always the case for
1730  // other mesh types, hence use of extra array
1731  std::map<int, int> geoEnt2ExoId;
1732  int nextSideSetId = 1;
1733  for (vtkIdType i = 0; i < sideSet.sides->GetNumberOfCells(); ++i) {
1734  int geoEnt = sideSetEntities->GetValue(i);
1735  // If geoEnt is not found in geoEnt2ExoID, call to operator[] to sets
1736  // geoEnt2ExoId[geoEnt] to 0 (which is used as sentinel value)
1737  auto &exoID = geoEnt2ExoId[geoEnt];
1738  if (exoID == 0) {
1739  exoID = nextSideSetId;
1740  auto emplaceIter = _sideSetNames.emplace(exoID, std::string{});
1741  if (emplaceIter.second && nameArr && geoEnt >= 0 &&
1742  geoEnt < nameArr->GetNumberOfValues()) {
1743  emplaceIter.first->second = nameArr->GetValue(geoEnt);
1744  }
1745  ++nextSideSetId;
1746  }
1747  sideSetObjId->InsertNextValue(exoID);
1748  }
1749  sideSetObjId->Delete();
1750  }
1751  }
1752 }
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
std::shared_ptr< meshBase > mesh
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ setTitle()

void NEM::MSH::exoGeoMesh::setTitle ( const std::string &  title)
Parameters
titlenew title to set

Definition at line 825 of file exoGeoMesh.C.

References _title.

825 { _title = title; }
std::string _title
Definition: exoGeoMesh.H:387

◆ stitch()

void NEM::MSH::exoGeoMesh::stitch ( const exoGeoMesh otherGM,
float  tol = 1e-15f 
)

PointData and CellData arrays are intersected. Adds side sets and node sets if available. Element block properties from otherGM are copied if property also defined in this exoGeoMesh.

Parameters
otherGMOther exoGeoMesh to addd to this one
tolTolerance for merging points

Definition at line 1301 of file exoGeoMesh.C.

References _elemBlockPropNames, _elemBlocks, _nodeSets, _sideSetNames, NEM::MSH::geoMeshBase::GeoMesh::geo, NEM::MSH::geoMeshBase::GeoMesh::getDimension(), getExoIdArrName(), NEM::MSH::geoMeshBase::SideSet::getGeoEntArr(), NEM::MSH::geoMeshBase::getGeoMesh(), nemAux::leastUnusedKey(), NEM::MSH::geoMeshBase::GeoMesh::link, mesh, NEM::MSH::geoMeshBase::GeoMesh::mesh, NEM::MSH::exoGeoMesh::nodeSet::name, NEM::MSH::New(), NEM::MSH::exoGeoMesh::nodeSet::nodes, resetNodeSetPoints(), NEM::MSH::geoMeshBase::setGeoMesh(), and NEM::MSH::geoMeshBase::GeoMesh::sideSet.

1301  {
1302  auto mesh = this->getGeoMesh().mesh;
1303  if (mesh->GetNumberOfCells() == 0) {
1304  std::cerr << "Current mesh is empty. Cannot stitch onto empty mesh."
1305  << std::endl;
1306  exit(1);
1307  }
1308  if (this->getGeoMesh().getDimension() !=
1309  otherGM.getGeoMesh().getDimension()) {
1310  std::cerr << "Dimension of meshes does not match." << std::endl;
1311  exit(1);
1312  }
1313  auto numOrigCells = mesh->GetNumberOfCells();
1314  auto otherMesh = otherGM.getGeoMesh().mesh;
1315  std::map<int, int> old2newElemBlock;
1316 
1317  std::set<std::string> propsToCopy;
1318  std::set_intersection(_elemBlockPropNames.begin(), _elemBlockPropNames.end(),
1319  otherGM._elemBlockPropNames.begin(),
1320  otherGM._elemBlockPropNames.end(),
1321  std::inserter(propsToCopy, propsToCopy.begin()));
1322  auto newBlockId = nemAux::leastUnusedKey(this->_elemBlocks);
1323  for (const auto &otherElemBlock : otherGM._elemBlocks) {
1324  old2newElemBlock[otherElemBlock.first] = newBlockId;
1325  auto &newElemBlock = this->_elemBlocks[newBlockId];
1326  newElemBlock.name = otherElemBlock.second.name;
1327  newElemBlock.cellType = otherElemBlock.second.cellType;
1328  for (const auto &property : propsToCopy) {
1329  auto it = otherElemBlock.second.properties.find(property);
1330  if (it != otherElemBlock.second.properties.end()) {
1331  newElemBlock.properties[property] = it->second;
1332  }
1333  }
1334  newBlockId = nemAux::leastUnusedKey(this->_elemBlocks, newBlockId);
1335  }
1336  auto oldOtherBlockIdArr =
1337  vtkSmartPointer<vtkIntArray>(vtkIntArray::FastDownCast(
1338  otherMesh->GetCellData()->GetAbstractArray(getExoIdArrName())));
1339  otherMesh->GetCellData()->RemoveArray(getExoIdArrName());
1340  auto newOtherBlockIdArr = vtkSmartPointer<vtkIntArray>::Take(
1341  vtkIntArray::FastDownCast(mesh->GetCellData()
1342  ->GetAbstractArray(getExoIdArrName())
1343  ->NewInstance()));
1344  newOtherBlockIdArr->SetName(getExoIdArrName());
1345  newOtherBlockIdArr->SetNumberOfValues(otherMesh->GetNumberOfCells());
1346  for (vtkIdType i = 0; i < otherMesh->GetNumberOfCells(); ++i) {
1347  newOtherBlockIdArr->SetComponent(
1348  i, 0, old2newElemBlock.at(oldOtherBlockIdArr->GetValue(i)));
1349  }
1350  otherMesh->GetCellData()->AddArray(newOtherBlockIdArr);
1351 
1352 #ifdef HAVE_GMSH
1353  if (!this->getGeoMesh().geo.empty()) {
1354  gmsh::model::setCurrent(this->getGeoMesh().geo);
1355  gmsh::model::remove();
1356  mesh->GetCellData()->RemoveArray(this->getGeoMesh().link.c_str());
1357  this->setGeoMesh({mesh, "", "", this->getGeoMesh().sideSet});
1358  }
1359 #endif
1361  auto nodeMaps = mergeMeshes(mesh, otherMesh, newMesh, tol);
1362  resetNodeSetPoints(nodeMaps.first);
1363  if (!otherGM._nodeSets.empty()) {
1364  auto nextNodeSetId = nemAux::leastUnusedKey(_nodeSets);
1365  for (const auto &otherNodeSet : otherGM._nodeSets) {
1366  auto &nodeSet = _nodeSets[nextNodeSetId];
1367  nodeSet.name = otherNodeSet.second.name;
1368  nodeSet.nodes.reserve(otherNodeSet.second.nodes.size());
1369  std::transform(
1370  otherNodeSet.second.nodes.begin(), otherNodeSet.second.nodes.end(),
1371  std::back_inserter(nodeSet.nodes),
1372  [&nodeMaps](vtkIdType x) { return nodeMaps.second->GetValue(x); });
1373  nextNodeSetId = nemAux::leastUnusedKey(_nodeSets, nextNodeSetId);
1374  }
1375  }
1376  resetSideSetPoints(newMesh, getGeoMesh().sideSet.sides, nodeMaps.first);
1377  setGeoMesh(
1378  {newMesh, getGeoMesh().geo, getGeoMesh().link, getGeoMesh().sideSet});
1379  auto otherGeoMesh = otherGM.getGeoMesh();
1380  if (otherGeoMesh.sideSet.sides) {
1381  auto otherSideSet = otherGeoMesh.sideSet;
1382  auto otherExoIdArr = vtkIntArray::FastDownCast(
1383  otherSideSet.sides->GetCellData()->GetAbstractArray(getExoIdArrName()));
1384  auto otherEntitiesArr = otherGeoMesh.sideSet.getGeoEntArr();
1385  auto otherOrigCellIdArr = otherGeoMesh.sideSet.getOrigCellArr();
1386  auto otherCellFaceIdArr = otherGeoMesh.sideSet.getCellFaceArr();
1387  auto geoMesh = this->getGeoMesh();
1388  auto sideSet = geoMesh.sideSet;
1389  vtkSmartPointer<vtkIntArray> sideSetExoId;
1390  vtkSmartPointer<vtkIntArray> sideSetEntities;
1391  vtkSmartPointer<vtkIdTypeArray> sideSetOrigCellId;
1392  vtkSmartPointer<vtkIntArray> sideSetCellFaceId;
1393  if (sideSet.sides) {
1394  sideSetExoId = vtkIntArray::FastDownCast(
1395  sideSet.sides->GetCellData()->GetAbstractArray(getExoIdArrName()));
1396  sideSetEntities = geoMesh.sideSet.getGeoEntArr();
1397  sideSetOrigCellId = geoMesh.sideSet.getOrigCellArr();
1398  sideSetCellFaceId = geoMesh.sideSet.getCellFaceArr();
1399  } else {
1400  auto sideSetPD = vtkSmartPointer<vtkPolyData>::New();
1401  sideSetPD->Allocate(otherSideSet.sides);
1402  sideSetExoId = vtkSmartPointer<vtkIntArray>::New();
1403  sideSetExoId->SetName(getExoIdArrName());
1404  sideSetExoId->Allocate(otherSideSet.sides->GetNumberOfCells());
1405  sideSet.sides->GetCellData()->AddArray(sideSetExoId);
1406  sideSetEntities = vtkSmartPointer<vtkIntArray>::New();
1407  sideSetEntities->Allocate(otherSideSet.sides->GetNumberOfCells());
1408  sideSetOrigCellId = vtkSmartPointer<vtkIdTypeArray>::New();
1409  sideSetOrigCellId->SetNumberOfComponents(2);
1410  sideSetOrigCellId->Allocate(otherSideSet.sides->GetNumberOfCells());
1411  sideSetCellFaceId = vtkSmartPointer<vtkIntArray>::New();
1412  sideSetCellFaceId->SetNumberOfComponents(2);
1413  sideSetCellFaceId->Allocate(otherSideSet.sides->GetNumberOfCells());
1414  sideSet = {sideSetPD, sideSetEntities, sideSetOrigCellId,
1415  sideSetCellFaceId};
1416  this->setGeoMesh({newMesh, this->getGeoMesh().geo,
1417  this->getGeoMesh().link, sideSet});
1418  }
1419  std::map<int, int> old2newSideSet;
1420  auto newSideSetId = nemAux::leastUnusedKey(this->_sideSetNames);
1421  for (const auto &otherSet : otherGM._sideSetNames) {
1422  old2newSideSet[otherSet.first] = newSideSetId;
1423  this->_sideSetNames[newSideSetId] = otherSet.second;
1424  newSideSetId = nemAux::leastUnusedKey(this->_sideSetNames, newSideSetId);
1425  }
1426  std::map<int, int> old2newGeoEnt;
1427  for (vtkIdType i = 0; i < sideSet.sides->GetNumberOfCells(); ++i) {
1428  old2newGeoEnt[sideSetEntities->GetValue(i)] = -1;
1429  }
1430  int nextSideSetEntId = nemAux::leastUnusedKey(old2newGeoEnt);
1431  for (vtkIdType i = 0; i < otherSideSet.sides->GetNumberOfCells(); ++i) {
1432  auto origCellId = otherOrigCellIdArr->GetTypedComponent(i, 0) + numOrigCells;
1433  auto cellFaceId = otherCellFaceIdArr->GetTypedComponent(i, 0);
1434  auto parent = newMesh->GetCell(origCellId);
1435  auto side = parent->GetCellDimension() == 2 ? parent->GetEdge(cellFaceId)
1436  : parent->GetFace(cellFaceId);
1437  sideSet.sides->InsertNextCell(side->GetCellType(), side->GetPointIds());
1438  int newEntId = otherEntitiesArr->GetValue(i);
1439  auto insertIter = old2newGeoEnt.insert({newEntId, nextSideSetEntId});
1440  if (insertIter.second || insertIter.first->second == -1) {
1441  if (insertIter.first->second == -1) {
1442  insertIter.first->second = nextSideSetEntId;
1443  }
1444  nextSideSetEntId =
1445  nemAux::leastUnusedKey(old2newGeoEnt, nextSideSetEntId);
1446  }
1447  sideSetExoId->InsertNextValue(old2newSideSet[otherExoIdArr->GetValue(i)]);
1448  sideSetEntities->InsertNextValue(insertIter.first->second);
1449  sideSetOrigCellId->InsertNextTuple2(origCellId, -1);
1450  sideSetCellFaceId->InsertNextTuple2(cellFaceId, -1);
1451  }
1452  }
1453  otherMesh->GetCellData()->RemoveArray(getExoIdArrName());
1454  otherMesh->GetCellData()->AddArray(oldOtherBlockIdArr);
1455 }
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419
A leastUnusedKey(const std::map< A, B > &map, A min=1)
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390
std::shared_ptr< meshBase > mesh
void resetNodeSetPoints(vtkIdTypeArray *nodeMap=nullptr)
Renumbers the nodes in all node sets based on nodeMap if provided.
Definition: exoGeoMesh.C:1699
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
int getDimension() const
Get dimension of mesh.
Definition: geoMeshBase.C:436
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

◆ takeGeoMesh()

void NEM::MSH::exoGeoMesh::takeGeoMesh ( geoMeshBase otherGeoMesh)
overridevirtual

Note that otherGeoMesh will be left with an empty mesh.

Parameters
otherGeoMeshother geoMeshBase object; mesh will be left empty

Reimplemented from NEM::MSH::geoMeshBase.

Definition at line 778 of file exoGeoMesh.C.

References _elemBlockPropNames, _elemBlocks, _nodeSets, _physGrpName, _sideSetNames, _title, NEM::MSH::New(), NEM::MSH::geoMeshBase::setGeoMesh(), and NEM::MSH::geoMeshBase::takeGeoMesh().

778  {
779  auto otherExoGM = dynamic_cast<exoGeoMesh *>(otherGeoMesh);
780  if (otherExoGM) {
781  setGeoMesh(otherExoGM->getGeoMesh());
782  otherExoGM->setGeoMesh(
784  _title = std::move(otherExoGM->_title);
785  _elemBlocks = std::move(otherExoGM->_elemBlocks);
786  _sideSetNames = std::move(otherExoGM->_sideSetNames);
787  _nodeSets = std::move(otherExoGM->_nodeSets);
788  _elemBlockPropNames = std::move(otherExoGM->_elemBlockPropNames);
789  _physGrpName = std::move(otherExoGM->_physGrpName);
790  otherExoGM->resetNative();
791  } else {
792  geoMeshBase::takeGeoMesh(otherGeoMesh);
793  }
794 }
std::string _title
Definition: exoGeoMesh.H:387
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
geoMeshBase * New(MeshType meshType)
Create a new mesh object.
void setGeoMesh(const geoMeshBase::GeoMesh &geoMesh)
Set the underlying geometry object.
Definition: geoMeshBase.H:538
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390
exoGeoMesh()
Reads an EXODUS II file into an exoGeoMesh object.
Definition: exoGeoMesh.C:257
std::string _physGrpName
Definition: exoGeoMesh.H:392
virtual void takeGeoMesh(geoMeshBase *otherGeoMesh)
Take the GeoMesh of another geoMeshBase.
Definition: geoMeshBase.C:104

◆ unsetCellDataArray() [1/2]

void NEM::MSH::geoMeshBase::unsetCellDataArray ( int  arrayIdx)
inlineprotectedinherited
Parameters
arrayIdxarray index

Definition at line 503 of file geoMeshBase.H.

503  {
504  _geoMesh.mesh->GetCellData()->RemoveArray(arrayIdx);
505  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ unsetCellDataArray() [2/2]

void NEM::MSH::geoMeshBase::unsetCellDataArray ( const std::string &  arrayName)
inlineprotectedinherited
Parameters
arrayNamearray name

Definition at line 510 of file geoMeshBase.H.

510  {
511  _geoMesh.mesh->GetCellData()->RemoveArray(arrayName.c_str());
512  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ unsetFieldDataArray() [1/2]

void NEM::MSH::geoMeshBase::unsetFieldDataArray ( int  arrayIdx)
inlineprotectedinherited
Parameters
arrayIdxarray index

Definition at line 517 of file geoMeshBase.H.

517  {
518  _geoMesh.mesh->GetFieldData()->RemoveArray(arrayIdx);
519  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ unsetFieldDataArray() [2/2]

void NEM::MSH::geoMeshBase::unsetFieldDataArray ( const std::string &  arrayName)
inlineprotectedinherited
Parameters
arrayNamearray name

Definition at line 524 of file geoMeshBase.H.

524  {
525  _geoMesh.mesh->GetFieldData()->RemoveArray(arrayName.c_str());
526  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ unsetPointDataArray() [1/2]

void NEM::MSH::geoMeshBase::unsetPointDataArray ( int  arrayIdx)
inlineprotectedinherited
Parameters
arrayIdxarray index

Definition at line 489 of file geoMeshBase.H.

489  {
490  _geoMesh.mesh->GetPointData()->RemoveArray(arrayIdx);
491  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ unsetPointDataArray() [2/2]

void NEM::MSH::geoMeshBase::unsetPointDataArray ( const std::string &  arrayName)
inlineprotectedinherited
Parameters
arrayNamearray name

Definition at line 496 of file geoMeshBase.H.

496  {
497  _geoMesh.mesh->GetPointData()->RemoveArray(arrayName.c_str());
498  }
vtkSmartPointer< vtkUnstructuredGrid > mesh
Definition: geoMeshBase.H:419

◆ write()

void NEM::MSH::exoGeoMesh::write ( const std::string &  fileName)
overridevirtual

If fileName already exists, it is overwritten. If there are more than 900 side sets, they are concatenated, with a side set variable named "NEM_SIDE_SET_ID" added that contains the id of the side in this exoGeoMesh.

Parameters
fileNameName of file. Must end in ".exo", ".e", ".gen", or ".g"

Implements NEM::MSH::geoMeshBase.

Definition at line 382 of file exoGeoMesh.C.

References _elemBlockPropNames, _elemBlocks, _nodeSets, _sideSetNames, _title, cellType, data, nemAux::find_ext(), getExoIdArrName(), NEM::MSH::geoMeshBase::getGeoMesh(), NEM::MSH::exoGeoMesh::nodeSet::name, nodes, NEM::MSH::exoGeoMesh::nodeSet::nodes, and resetNodeSetPoints().

382  {
383  std::string fileExt = nemAux::find_ext(fileName);
384  if (fileExt == ".exo" || fileExt == ".e" || fileExt == ".gen" ||
385  fileExt == ".g") {
386  int comp_ws = sizeof(double);
387  int io_ws = sizeof(double);
388  int exoid = ex_create(fileName.c_str(), EX_CLOBBER, &comp_ws, &io_ws);
389  checkExodusErr(exoid, true);
390 
391  auto geoMesh = this->getGeoMesh();
392  auto mesh = geoMesh.mesh;
393  auto sideSet = geoMesh.sideSet;
394  if (!mesh || mesh->GetNumberOfCells() == 0) {
395  std::cerr << "No mesh information to write." << std::endl;
396  return;
397  }
398 
399  // Make sure no empty element blocks
400  std::map<int, std::vector<vtkIdType>> elemBlocks;
401  {
402  auto meshEntities = vtkIntArray::FastDownCast(
403  mesh->GetCellData()->GetAbstractArray(getExoIdArrName()));
404  for (const auto &elemBlock : _elemBlocks) {
405  elemBlocks[elemBlock.first];
406  }
407  for (vtkIdType i = 0; i < mesh->GetNumberOfCells(); ++i) {
408  auto entity = meshEntities->GetValue(i);
409  elemBlocks.at(entity).emplace_back(i);
410  }
411  for (auto it = elemBlocks.begin(); it != elemBlocks.end();) {
412  if (it->second.empty()) {
413  it = elemBlocks.erase(it);
414  } else {
415  ++it;
416  }
417  }
418  }
419 
420  // Get number of element block variables, nodal variables, and global
421  // variables
422  int numElemVars = 0;
423  int numNodeVars = 0;
424  int numGlobalVars = 0;
425  std::vector<bool> cellDataWriteFlag;
426  std::vector<bool> pointDataWriteFlag;
427  std::vector<bool> fieldDataWriteFlag;
428  int timeStep = 1;
429  {
430  // Cell Data
431  auto globalIds = mesh->GetCellData()->GetGlobalIds();
432  const char *globalIdName;
433  if (globalIds) {
434  globalIdName = globalIds->GetName();
435  } else {
436  globalIdName = "GlobalElementId";
437  }
438  auto pedigreeIds = mesh->GetCellData()->GetPedigreeIds();
439  const char *pedgreeIdName;
440  if (pedigreeIds) {
441  pedgreeIdName = pedigreeIds->GetName();
442  } else {
443  pedgreeIdName = "PedigreeElementId";
444  }
445  auto numCells = mesh->GetNumberOfCells();
446  cellDataWriteFlag.resize(mesh->GetCellData()->GetNumberOfArrays(), false);
447  for (int i = 0; i < mesh->GetCellData()->GetNumberOfArrays(); ++i) {
448  // Use GetArray instead of GetAbstractArray to filter for vtkDataArray
449  auto arr = mesh->GetCellData()->GetArray(i);
450  if (arr) {
451  auto arrName = arr->GetName();
452  if (strcmp(arrName, globalIdName) != 0 &&
453  strcmp(arrName, pedgreeIdName) != 0 &&
454  strcmp(arrName, getExoIdArrName()) != 0 &&
455  arr->GetNumberOfTuples() == numCells) {
456  auto numComponents = arr->GetNumberOfComponents();
457  cellDataWriteFlag[i] = (numComponents > 0);
458  numElemVars += numComponents;
459  }
460  }
461  }
462  // Point Data
463  globalIds = mesh->GetPointData()->GetGlobalIds();
464  if (globalIds) {
465  globalIdName = globalIds->GetName();
466  } else {
467  globalIdName = "GlobalNodeId";
468  }
469  pedigreeIds = mesh->GetPointData()->GetPedigreeIds();
470  if (pedigreeIds) {
471  pedgreeIdName = pedigreeIds->GetName();
472  } else {
473  pedgreeIdName = "PedigreeNodeId";
474  }
475  auto numNodes = mesh->GetNumberOfPoints();
476  pointDataWriteFlag.resize(mesh->GetPointData()->GetNumberOfArrays(),
477  false);
478  for (int i = 0; i < mesh->GetPointData()->GetNumberOfArrays(); ++i) {
479  // Use GetArray instead of GetAbstractArray to filter for vtkDataArray
480  auto arr = mesh->GetPointData()->GetArray(i);
481  if (arr) {
482  auto arrName = arr->GetName();
483  if (strcmp(arrName, globalIdName) != 0 &&
484  strcmp(arrName, pedgreeIdName) != 0 &&
485  arr->GetNumberOfTuples() == numNodes) {
486  auto numComponents = arr->GetNumberOfComponents();
487  pointDataWriteFlag[i] = (numComponents > 0);
488  numNodeVars += numComponents;
489  }
490  }
491  }
492  // Field Data
493  fieldDataWriteFlag.resize(mesh->GetFieldData()->GetNumberOfArrays(),
494  false);
495  for (int i = 0; i < mesh->GetFieldData()->GetNumberOfArrays(); ++i) {
496  // Use GetArray instead of GetAbstractArray to filter for vtkDataArray
497  auto arr = mesh->GetFieldData()->GetArray(i);
498  if (arr && arr->GetNumberOfTuples() == 1) {
499  auto numComponents = arr->GetNumberOfComponents();
500  fieldDataWriteFlag[i] = (numComponents > 0);
501  numGlobalVars += numComponents;
502  }
503  }
504  }
505 
506  // Have to make sure no empty side sets; might as well get the
507  // indices now.
508  std::map<int, std::vector<vtkIdType>> exoSideSets;
509  if (sideSet.sides) {
510  auto sideSetExoId = vtkIntArray::FastDownCast(
511  sideSet.sides->GetCellData()->GetAbstractArray(getExoIdArrName()));
512  for (vtkIdType i = 0; i < sideSet.sides->GetNumberOfCells(); ++i) {
513  auto entity = sideSetExoId->GetValue(i);
514  exoSideSets[entity].emplace_back(i);
515  }
516  }
517 
518  // Make sure no empty node sets and no duplicate nodes
520  int numNodeSets = std::accumulate(
521  _nodeSets.begin(), _nodeSets.end(), 0,
522  [](const int &a, const std::pair<const int, nodeSet> &b) {
523  return a + (!b.second.nodes.empty());
524  });
525 
526  auto err = ex_put_init(exoid, _title.c_str(), geoMesh.getDimension(),
527  mesh->GetNumberOfPoints(), mesh->GetNumberOfCells(),
528  elemBlocks.size(), numNodeSets, exoSideSets.size());
529  checkExodusErr(err);
530  if (numElemVars > 0) {
531  err = ex_put_variable_param(exoid, EX_ELEM_BLOCK, numElemVars);
532  checkExodusErr(err);
533  }
534  if (numNodeVars > 0) {
535  err = ex_put_variable_param(exoid, EX_NODAL, numNodeVars);
536  checkExodusErr(err);
537  }
538  if (numGlobalVars > 0) {
539  err = ex_put_variable_param(exoid, EX_GLOBAL, numGlobalVars);
540  checkExodusErr(err);
541  }
542  if (numElemVars > 0 || numNodeVars > 0 || numGlobalVars > 0) {
543  double time = 0;
544  err = ex_put_time(exoid, timeStep, &time);
545  checkExodusErr(err);
546  }
547 
548  std::vector<double> x_coord;
549  std::vector<double> y_coord;
550  std::vector<double> z_coord;
551  x_coord.resize(mesh->GetNumberOfPoints(), 0);
552  y_coord.resize(mesh->GetNumberOfPoints(), 0);
553  z_coord.resize(mesh->GetNumberOfPoints(), 0);
554  auto coord = mesh->GetPoints()->GetData();
555  for (vtkIdType i = 0; i < mesh->GetNumberOfPoints(); ++i) {
556  x_coord[i] = coord->GetComponent(i, 0);
557  y_coord[i] = coord->GetComponent(i, 1);
558  z_coord[i] = coord->GetComponent(i, 2);
559  }
560  err = ex_put_coord(exoid, x_coord.data(), y_coord.data(), z_coord.data());
561  checkExodusErr(err);
562 
563  // map from index in mesh to implicit index in exodus output
564  std::vector<vtkIdType> vtkIdMap(mesh->GetNumberOfCells(), -1);
565  int lastElemIdx = 0;
566  for (const auto &elemBlock : elemBlocks) {
567  auto firstCell = mesh->GetCell(elemBlock.second[0]);
568  auto cellType = static_cast<VTKCellType>(firstCell->GetCellType());
569  err = ex_put_block(exoid, EX_ELEM_BLOCK, elemBlock.first,
570  vtkCellType2exoType(cellType), elemBlock.second.size(),
571  firstCell->GetNumberOfPoints(), 0, 0, 0);
572  checkExodusErr(err);
573  std::vector<int> conn;
574  conn.reserve(elemBlock.second.size() * firstCell->GetNumberOfPoints());
575  for (auto elem : elemBlock.second) {
576  auto cell = mesh->GetCell(elem);
577  vtkIdMap[elem] = ++lastElemIdx;
578  for (int i = 0; i < cell->GetNumberOfPoints(); ++i) {
579  // Exodus starts indexing from 1
580  conn.emplace_back(cell->GetPointId(i) + 1);
581  }
582  }
583  err = ex_put_conn(exoid, EX_ELEM_BLOCK, elemBlock.first, conn.data(),
584  nullptr, nullptr);
585  checkExodusErr(err);
586  if (!_elemBlocks.at(elemBlock.first).name.empty()) {
587  err = ex_put_name(exoid, EX_ELEM_BLOCK, elemBlock.first,
588  _elemBlocks.at(elemBlock.first).name.c_str());
589  checkExodusErr(err);
590  }
591  }
592 
593  if (sideSet.sides) {
594  auto sideSetOrigCellId = geoMesh.sideSet.getOrigCellArr();
595  auto sideSetCellFaceId = geoMesh.sideSet.getCellFaceArr();
596  for (const auto &exoSideSet : exoSideSets) {
597  err = ex_put_set_param(exoid, EX_SIDE_SET, exoSideSet.first,
598  exoSideSet.second.size(), 0);
599  checkExodusErr(err);
600  std::vector<int> sideSetElem, sideSetSide;
601  sideSetElem.reserve(exoSideSet.second.size());
602  sideSetSide.reserve(exoSideSet.second.size());
603  for (auto sideIdx : exoSideSet.second) {
604  auto parentCellIdx = sideSetOrigCellId->GetTypedComponent(sideIdx, 0);
605  sideSetElem.emplace_back(vtkIdMap[parentCellIdx]);
606  sideSetSide.emplace_back(
607  vtkSide2exoSide(sideSetCellFaceId->GetTypedComponent(sideIdx, 0),
608  mesh->GetCell(parentCellIdx)->GetCellType()));
609  }
610  err = ex_put_set(exoid, EX_SIDE_SET, exoSideSet.first,
611  sideSetElem.data(), sideSetSide.data());
612  checkExodusErr(err);
613  auto foundName = _sideSetNames.find(exoSideSet.first);
614  if (foundName != _sideSetNames.end()) {
615  err = ex_put_name(exoid, EX_SIDE_SET, foundName->first,
616  foundName->second.c_str());
617  checkExodusErr(err);
618  }
619  }
620  }
621 
622  for (const auto &nodeSet : _nodeSets) {
623  if (!nodeSet.second.nodes.empty()) {
624  err = ex_put_set_param(exoid, EX_NODE_SET, nodeSet.first,
625  nodeSet.second.nodes.size(), 0);
626  checkExodusErr(err);
627  std::vector<int> nodes; // Have to add 1
628  nodes.reserve(nodeSet.second.nodes.size());
629  std::transform(nodeSet.second.nodes.begin(), nodeSet.second.nodes.end(),
630  std::back_inserter(nodes), [](int x) { return x + 1; });
631  err = ex_put_set(exoid, EX_NODE_SET, nodeSet.first, nodes.data(),
632  nullptr);
633  checkExodusErr(err);
634  if (!nodeSet.second.name.empty()) {
635  err = ex_put_name(exoid, EX_NODE_SET, nodeSet.first,
636  nodeSet.second.name.c_str());
637  checkExodusErr(err);
638  }
639  }
640  }
641 
642  if (numElemVars > 0) {
643  int var_index = 1;
644  std::vector<double> vals(mesh->GetNumberOfCells());
645  for (int i = 0; i < mesh->GetCellData()->GetNumberOfArrays(); ++i) {
646  if (cellDataWriteFlag[i]) {
647  auto arr = mesh->GetCellData()->GetArray(i);
648  for (int j = 0; j < arr->GetNumberOfComponents(); ++j) {
649  for (vtkIdType k = 0; k < mesh->GetNumberOfCells(); ++k) {
650  vals[vtkIdMap[k] - 1] = arr->GetComponent(k, j);
651  }
652  auto name = getArrComponentName(arr, j);
653  if (name.empty()) {
654  name = "ElemBlockVar" + std::to_string(var_index);
655  }
656  err = ex_put_variable_name(exoid, EX_ELEM_BLOCK, var_index,
657  name.c_str());
658  checkExodusErr(err);
659  std::size_t varOffset = 0;
660  for (const auto &elemBlock : elemBlocks) {
661  err = ex_put_var(exoid, timeStep, EX_ELEM_BLOCK, var_index,
662  elemBlock.first, elemBlock.second.size(),
663  vals.data() + varOffset);
664  checkExodusErr(err);
665  varOffset += elemBlock.second.size();
666  }
667  ++var_index;
668  }
669  }
670  }
671  }
672 
673  if (numNodeVars > 0) {
674  int var_index = 1;
675  std::vector<double> vals(mesh->GetNumberOfPoints());
676  for (int i = 0; i < mesh->GetPointData()->GetNumberOfArrays(); ++i) {
677  if (pointDataWriteFlag[i]) {
678  auto arr = mesh->GetPointData()->GetArray(i);
679  for (int j = 0; j < arr->GetNumberOfComponents(); ++j) {
680  auto name = getArrComponentName(arr, j);
681  if (name.empty()) {
682  name = "NodalVar" + std::to_string(var_index);
683  }
684  err =
685  ex_put_variable_name(exoid, EX_NODAL, var_index, name.c_str());
686  checkExodusErr(err);
687  for (vtkIdType k = 0; k < mesh->GetNumberOfPoints(); ++k) {
688  vals[k] = arr->GetComponent(k, j);
689  }
690  err = ex_put_var(exoid, timeStep, EX_NODAL, var_index, 1,
691  mesh->GetNumberOfPoints(), vals.data());
692  checkExodusErr(err);
693  ++var_index;
694  }
695  }
696  }
697  }
698  if (numGlobalVars > 0) {
699  int var_index = 1;
700  std::vector<double> vals;
701  for (int i = 0; i < mesh->GetFieldData()->GetNumberOfArrays(); ++i) {
702  if (fieldDataWriteFlag[i]) {
703  auto arr = mesh->GetFieldData()->GetArray(i);
704  for (int j = 0; j < arr->GetNumberOfComponents(); ++j) {
705  vals.emplace_back(arr->GetComponent(0, j));
706  auto name = getArrComponentName(arr, j);
707  if (!name.empty()) {
708  err = ex_put_variable_name(exoid, EX_GLOBAL, var_index,
709  name.c_str());
710  checkExodusErr(err);
711  }
712  ++var_index;
713  }
714  }
715  }
716  err = ex_put_var(exoid, timeStep, EX_GLOBAL, 1, 0, numGlobalVars,
717  vals.data());
718  checkExodusErr(err);
719  }
720 
721  if (!_elemBlockPropNames.empty()) {
722  // Element block properties
723  std::vector<const char *> propNames;
724  propNames.reserve(_elemBlockPropNames.size());
725  std::vector<std::vector<int>> propVals;
726  propVals.resize(_elemBlockPropNames.size());
727  for (const auto &elemBlockProp : _elemBlockPropNames) {
728  propNames.emplace_back(elemBlockProp.c_str());
729  }
730  err = ex_put_prop_names(exoid, EX_ELEM_BLOCK, _elemBlockPropNames.size(),
731  const_cast<char **>(propNames.data()));
732  checkExodusErr(err);
733  // Use elemBlocks to verify non-empty
734  auto nonEmptyIt = elemBlocks.begin();
735  auto it = _elemBlocks.begin();
736  while (nonEmptyIt != elemBlocks.end()) {
737  if (it->first == nonEmptyIt->first) {
738  std::size_t propValsIdx = 0;
739  auto propNamesIt = propNames.begin();
740  auto propValsIt = it->second.properties.begin();
741  while (propNamesIt != propNames.end()) {
742  if (propValsIt != it->second.properties.end() &&
743  *propNamesIt == propValsIt->first) {
744  propVals[propValsIdx].emplace_back(propValsIt->second);
745  ++propValsIt;
746  } else {
747  propVals[propValsIdx].emplace_back(0);
748  }
749  ++propNamesIt;
750  ++propValsIdx;
751  }
752  ++nonEmptyIt;
753  }
754  ++it;
755  }
756  for (std::size_t i = 0; i < propNames.size(); ++i) {
757  err = ex_put_prop_array(exoid, EX_ELEM_BLOCK, propNames[i],
758  propVals[i].data());
759  checkExodusErr(err);
760  }
761  }
762  err = ex_close(exoid);
763  checkExodusErr(err);
764  } else {
765  std::cerr << "For exoGeoMesh, " << fileExt
766  << " format not currently supported." << std::endl;
767  }
768 }
std::string _title
Definition: exoGeoMesh.H:387
std::set< std::string > _elemBlockPropNames
Definition: exoGeoMesh.H:391
data_type data
Edge/face with sorted point ids (a, b, c, ...) is located at some index i in data[b], with data[b][i].first == [a, c] (for edges, third point id treated as -1).
std::vector< std::pair< vtkIdType, std::vector< double > > > nodes
Each entry stores (node ID in .inp file, coordinates)
Definition: inpGeoMesh.C:139
std::map< int, std::string > _sideSetNames
Definition: exoGeoMesh.H:389
std::string find_ext(const std::string &fname)
std::map< int, elemBlock > _elemBlocks
Definition: exoGeoMesh.H:388
std::map< int, nodeSet > _nodeSets
Definition: exoGeoMesh.H:390
VTKCellType cellType
Definition: inpGeoMesh.C:129
std::shared_ptr< meshBase > mesh
void resetNodeSetPoints(vtkIdTypeArray *nodeMap=nullptr)
Renumbers the nodes in all node sets based on nodeMap if provided.
Definition: exoGeoMesh.C:1699
static const char * getExoIdArrName()
Definition: exoGeoMesh.C:253
const GeoMesh & getGeoMesh() const
Get the underlying geometry object.
Definition: geoMeshBase.H:533

Member Data Documentation

◆ _elemBlockPropNames

std::set<std::string> NEM::MSH::exoGeoMesh::_elemBlockPropNames
private

◆ _elemBlocks

◆ _nodeSets

◆ _physGrpName

std::string NEM::MSH::exoGeoMesh::_physGrpName
private

◆ _sideSetNames

std::map<int, std::string> NEM::MSH::exoGeoMesh::_sideSetNames
private

◆ _title

std::string NEM::MSH::exoGeoMesh::_title
private

Definition at line 387 of file exoGeoMesh.H.

Referenced by exoGeoMesh(), getTitle(), report(), setTitle(), takeGeoMesh(), and write().

◆ GEO_ENT_DEFAULT_NAME

constexpr auto NEM::MSH::geoMeshBase::GEO_ENT_DEFAULT_NAME = "GeoEnt"
staticprotectedinherited

The documentation for this class was generated from the following files: