}
-#define DUMPSO(txt) \
+/*#define DUMPSO(txt) \
// cout << txt << endl;
//=============================================================================
-/*!
- *
- */
+//
+//
+//
//=============================================================================
static void swap( int i1, int i2, int idNodes[], gp_Pnt P[] )
{
// }
return true;
-}
+}*/
//=======================================================================
//function : laplacianSmooth
if ( theElems.find( elem ) == theElems.end() )
continue;
+ if (elem->IsPoly())
+ continue;
int i = 0, iNode = 0;
const SMDS_MeshNode* aNodes [4];
SMDS_ElemIteratorPtr itN = elem->nodesIterator();
for (int inode = 0; inode < nbPolygonNodes; inode++) {
polygon_nodes[inode] = nodes[inode];
}
- aMesh->AddPolygonalFace(polygon_nodes);
+ if (!hasFreeLinks || !aMesh->FindFace(polygon_nodes))
+ aMesh->AddPolygonalFace(polygon_nodes);
}
break;
}
int nbUniqueNodes = nodeSet.size();
if ( nbNodes != nbUniqueNodes ) // some nodes stick
{
+ // Polygons and Polyhedral volumes
+ if (elem->IsPoly()) {
+
+ if (elem->GetType() == SMDSAbs_Face) {
+ // Polygon
+ if (nbUniqueNodes < 3) {
+ isOk = false;
+ } else {
+ // get simple seq of nodes
+ const SMDS_MeshNode* simpleNodes[ nbNodes ];
+ int iSimple = 0;
+
+ simpleNodes[iSimple++] = curNodes[0];
+ for (iCur = 1; iCur < nbNodes; iCur++) {
+ if (curNodes[iCur] != simpleNodes[iSimple - 1]) {
+ simpleNodes[iSimple++] = curNodes[iCur];
+ }
+ }
+ int nbSimple = iSimple;
+ if (simpleNodes[nbSimple - 1] == simpleNodes[0]) {
+ nbSimple--;
+ }
+
+ // separate cycles
+ bool foundCycle = (nbSimple > nbUniqueNodes);
+ while (foundCycle) {
+ foundCycle = false;
+ set<const SMDS_MeshNode*> cycleSet;
+ for (iSimple = 0; iSimple < nbSimple && !foundCycle; iSimple++) {
+ const SMDS_MeshNode* n = simpleNodes[iSimple];
+ if (!cycleSet.insert( n ).second) {
+ foundCycle = true;
+
+ // separate cycle
+ int iC = 0, curLast = iSimple;
+ for (; iC < curLast; iC++) {
+ if (simpleNodes[iC] == n) break;
+ }
+ int cycleLen = curLast - iC;
+ if (cycleLen > 2) {
+ // create sub-element
+ vector<const SMDS_MeshNode *> poly_nodes (cycleLen);
+ for (int ii = 0; iC < curLast; iC++) {
+ poly_nodes[ii++] = simpleNodes[iC];
+ }
+ SMDS_MeshElement* newElem = aMesh->AddPolygonalFace(poly_nodes);
+ if (aShapeId)
+ aMesh->SetMeshElementOnShape(newElem, aShapeId);
+ }
+ // put the rest nodes from the first cycle position
+ for (iC = curLast + 1; iC < nbSimple; iC++) {
+ simpleNodes[iC - cycleLen] = simpleNodes[iC];
+ }
+ nbSimple -= cycleLen;
+ }
+ } // for (iSimple = 0; iSimple < nbSimple; iSimple++)
+ } // while (foundCycle)
+
+ if (iSimple > 2) {
+ aMesh->ChangeElementNodes(elem, simpleNodes, nbSimple);
+ } else {
+ isOk = false;
+ }
+ }
+
+ } else if (elem->GetType() == SMDSAbs_Volume) {
+ // Polyhedral volume
+ if (nbUniqueNodes < 4) {
+ isOk = false;
+ } else {
+ // each face has to be analized in order to check volume validity
+ //aMesh->ChangeElementNodes(elem, uniqueNodes, nbUniqueNodes);
+ isOk = false;
+ }
+
+ } else {
+ isOk = false;
+ }
+
+ if (!isOk)
+ rmElemIds.push_back(elem->GetID());
+
+ continue;
+ }
+
+ // Regular elements
switch ( nbNodes ) {
case 2: ///////////////////////////////////// EDGE
isOk = false; break;
LinkID_Gen aLinkID_Gen( GetMeshDS() );
set<long> foundSideLinkIDs, checkedLinkIDs;
SMDS_VolumeTool volume;
- const SMDS_MeshNode* faceNodes[ 4 ];
+ //const SMDS_MeshNode* faceNodes[ 4 ];
const SMDS_MeshNode* sideNode;
const SMDS_MeshElement* sideElem;
const SMDS_MeshElement* elem = invElemIt->next();
// prepare data for a loop on links, of a face or a volume
int iPrevNode, iNode = 0, nbNodes = elem->NbNodes();
+ const SMDS_MeshNode* faceNodes[ nbNodes ];
bool isVolume = volume.Set( elem );
const SMDS_MeshNode** nodes = isVolume ? volume.GetNodes() : faceNodes;
if ( isVolume ) // --volume
// find indices of 2 link nodes and of the rest nodes
int iNode = 0, il1, il2, i3, i4;
il1 = il2 = i3 = i4 = -1;
- const SMDS_MeshNode* nodes[ 8 ];
+ const SMDS_MeshNode* nodes[ theFace->NbNodes() ];
SMDS_ElemIteratorPtr nodeIt = theFace->nodesIterator();
while ( nodeIt->more() ) {
const SMDS_MeshNode* n = static_cast<const SMDS_MeshNode*>( nodeIt->next() );
// arrange link nodes to go one after another regarding the face orientation
bool reverse = ( Abs( il2 - il1 ) == 1 ? il2 < il1 : il1 < il2 );
+ list<const SMDS_MeshNode *> aNodesToInsert = theNodesToInsert;
if ( reverse ) {
iNode = il1;
il1 = il2;
il2 = iNode;
- theNodesToInsert.reverse();
+ aNodesToInsert.reverse();
}
// check that not link nodes of a quadrangles are in good order
int nbFaceNodes = theFace->NbNodes();
if (toCreatePoly || theFace->IsPoly()) {
iNode = 0;
- vector<const SMDS_MeshNode *> poly_nodes (nbFaceNodes + theNodesToInsert.size());
+ vector<const SMDS_MeshNode *> poly_nodes (nbFaceNodes + aNodesToInsert.size());
// add nodes of face up to first node of link
bool isFLN = false;
}
// add nodes to insert
- list<const SMDS_MeshNode*>::iterator nIt = theNodesToInsert.begin();
- for (; nIt != theNodesToInsert.end(); nIt++) {
+ list<const SMDS_MeshNode*>::iterator nIt = aNodesToInsert.begin();
+ for (; nIt != aNodesToInsert.end(); nIt++) {
poly_nodes[iNode++] = *nIt;
}
return;
}
- // put theNodesToInsert between theBetweenNode1 and theBetweenNode2
- int nbLinkNodes = 2 + theNodesToInsert.size();
+ // put aNodesToInsert between theBetweenNode1 and theBetweenNode2
+ int nbLinkNodes = 2 + aNodesToInsert.size();
const SMDS_MeshNode* linkNodes[ nbLinkNodes ];
linkNodes[ 0 ] = nodes[ il1 ];
linkNodes[ nbLinkNodes - 1 ] = nodes[ il2 ];
- list<const SMDS_MeshNode*>::iterator nIt = theNodesToInsert.begin();
- for ( iNode = 1; nIt != theNodesToInsert.end(); nIt++ ) {
+ list<const SMDS_MeshNode*>::iterator nIt = aNodesToInsert.begin();
+ for ( iNode = 1; nIt != aNodesToInsert.end(); nIt++ ) {
linkNodes[ iNode++ ] = *nIt;
}
// decide how to split a quadrangle: compare possible variants
bool isNewFace = setOfFaceNodeSet.insert( faceNodeSet ).second;
if ( isNewFace ) {
// no such a face is given but it still can exist, check it
- if ( nbNodes == 3 )
+ if ( nbNodes == 3 ) {
aFreeFace = aMesh->FindFace( fNodes[0],fNodes[1],fNodes[2] );
- else
+ } else if ( nbNodes == 4 ) {
aFreeFace = aMesh->FindFace( fNodes[0],fNodes[1],fNodes[2],fNodes[3] );
+ } else {
+ vector<const SMDS_MeshNode *> poly_nodes (nbNodes);
+ for (int inode = 0; inode < nbNodes; inode++) {
+ poly_nodes[inode] = fNodes[inode];
+ }
+ aFreeFace = aMesh->FindFace(poly_nodes);
+ }
}
if ( !aFreeFace ) {
// create a temporary face
- if ( nbNodes == 3 )
+ if ( nbNodes == 3 ) {
aFreeFace = aTmpFacesMesh.AddFace( fNodes[0],fNodes[1],fNodes[2] );
- else
+ } else if ( nbNodes == 4 ) {
aFreeFace = aTmpFacesMesh.AddFace( fNodes[0],fNodes[1],fNodes[2],fNodes[3] );
+ } else {
+ vector<const SMDS_MeshNode *> poly_nodes (nbNodes);
+ for (int inode = 0; inode < nbNodes; inode++) {
+ poly_nodes[inode] = fNodes[inode];
+ }
+ aFreeFace = aTmpFacesMesh.AddPolygonalFace(poly_nodes);
+ }
}
if ( aFreeFace )
freeFaceList.push_back( aFreeFace );