int DecimateSolidMesh::updateNodesandTets(int currentTet, int killedNode, int newNode) { SolidMeshDataContainer* sm = getSolidMeshDataContainer(); StructArray<Node>& nodes = *(sm->getNodes()); StructArray<Tetrahedron>& tetrahedrons = *(sm->getTetrahedrons()); int numNodes = nodes.GetNumberOfTuples(); int numTets = tetrahedrons.GetNumberOfTuples(); int nodeId1, nodeId2, nodeId3, nodeId4; int counter = 0; int nodeCount = 0; newNodeIds.resize(numNodes, -1); for(int i=0;i<numNodes;i++) { if(i != killedNode) { nodes.CopyTuple(i, nodeCount); newNodeIds[i] = nodeCount; nodeEuclideanDistances[nodeCount] = nodeEuclideanDistances[i]; nodeCount++; } } nodes.Resize(nodeCount); nodeEuclideanDistances.resize(nodeCount); int tetCount = 0; for(int i=0;i<numTets;i++) { nodeId1 = tetrahedrons[i].node_id[0]; nodeId2 = tetrahedrons[i].node_id[1]; nodeId3 = tetrahedrons[i].node_id[2]; nodeId4 = tetrahedrons[i].node_id[3]; if((nodeId1 != killedNode && nodeId2 != killedNode && nodeId3 != killedNode && nodeId4 != killedNode) || (nodeId1 != newNode && nodeId2 != newNode && nodeId3 != newNode && nodeId4 != newNode)) { if(nodeId1 == killedNode) tetrahedrons[i].node_id[0] = newNodeIds[newNode]; else tetrahedrons[i].node_id[0] = newNodeIds[nodeId1]; if(nodeId2 == killedNode) tetrahedrons[i].node_id[1] = newNodeIds[newNode]; else tetrahedrons[i].node_id[1] = newNodeIds[nodeId2]; if(nodeId3 == killedNode) tetrahedrons[i].node_id[2] = newNodeIds[newNode]; else tetrahedrons[i].node_id[2] = newNodeIds[nodeId3]; if(nodeId4 == killedNode) tetrahedrons[i].node_id[3] = newNodeIds[newNode]; else tetrahedrons[i].node_id[3] = newNodeIds[nodeId4]; tetrahedrons.CopyTuple(i, tetCount); tetCount++; } else { if(i <= currentTet) counter++; } } tetrahedrons.Resize(tetCount); return (currentTet - counter); }
// ----------------------------------------------------------------------------- // // ----------------------------------------------------------------------------- void GenerateSurfaceMeshConnectivity::execute() { int err = 0; std::stringstream ss; setErrorCondition(err); VoxelDataContainer* m = getVoxelDataContainer(); if(NULL == m) { setErrorCondition(-999); notifyErrorMessage("The Voxel DataContainer Object was NULL", -999); return; } setErrorCondition(0); dataCheck(false, 1, 1, 1); if (getErrorCondition() < 0) { return; } // We need the vertex->Triangle Lists to build the Triangle Neighbor lists so if either // of those are true then build the vertex->triangle lists if (m_GenerateVertexTriangleLists == true || m_GenerateTriangleNeighbors == true) { notifyStatusMessage("Generating Vertex Triangle List"); getSurfaceMeshDataContainer()->buildMeshVertLinks(); } if (m_GenerateTriangleNeighbors == true) { notifyStatusMessage("Generating Face Neighbors List"); getSurfaceMeshDataContainer()->buildMeshFaceNeighborLists(); } if (m_GenerateEdgeIdList == true) { // There was no Edge connectivity before this filter so delete it when we are done with it GenerateUniqueEdges::Pointer conn = GenerateUniqueEdges::New(); ss.str(""); ss << getMessagePrefix() << " |->Generating Unique Edge Ids |->"; conn->setMessagePrefix(ss.str()); conn->setObservers(getObservers()); conn->setVoxelDataContainer(getVoxelDataContainer()); conn->setSurfaceMeshDataContainer(getSurfaceMeshDataContainer()); conn->setSolidMeshDataContainer(getSolidMeshDataContainer()); conn->execute(); if(conn->getErrorCondition() < 0) { setErrorCondition(conn->getErrorCondition()); return; } } /* Let the GUI know we are done with this filter */ notifyStatusMessage("Complete"); }
// ----------------------------------------------------------------------------- // // ----------------------------------------------------------------------------- void DecimateSolidMesh::dataCheck(bool preflight, size_t voxels, size_t fields, size_t ensembles) { setErrorCondition(0); std::stringstream ss; SolidMeshDataContainer* sm = getSolidMeshDataContainer(); if (NULL == sm) { addErrorMessage(getHumanLabel(), "SolidMeshDataContainer is missing", -383); setErrorCondition(-384); } }
// ----------------------------------------------------------------------------- // // ----------------------------------------------------------------------------- void QuickSolidMesh::dataCheck(bool preflight, size_t voxels, size_t fields, size_t ensembles) { setErrorCondition(0); std::stringstream ss; VoxelDataContainer* m = getVoxelDataContainer(); GET_PREREQ_DATA(m, DREAM3D, CellData, GrainIds, ss, -300, int32_t, Int32ArrayType, voxels, 1) SolidMeshDataContainer* sm = getSolidMeshDataContainer(); if (NULL == sm) { addErrorMessage(getHumanLabel(), "SolidMeshDataContainer is missing", -383); setErrorCondition(-384); } else { StructArray<Node>::Pointer vertices = StructArray<Node>::CreateArray(1, DREAM3D::CellData::SolidMeshNodes); StructArray<Tetrahedron>::Pointer tetrahedrons = StructArray<Tetrahedron>::CreateArray(1, DREAM3D::CellData::SolidMeshTetrahedrons); sm->setNodes(vertices); sm->setTetrahedrons(tetrahedrons); } }
// ----------------------------------------------------------------------------- // // ----------------------------------------------------------------------------- void QuickSolidMesh::execute() { setErrorCondition(0); VoxelDataContainer* m = getVoxelDataContainer(); SolidMeshDataContainer* sm = getSolidMeshDataContainer(); if(NULL == m) { setErrorCondition(-999); notifyErrorMessage("The DataContainer Object was NULL", -999); return; } setErrorCondition(0); int64_t totalPoints = m->getTotalPoints(); size_t totalFields = m->getNumFieldTuples(); size_t totalEnsembles = m->getNumEnsembleTuples(); dataCheck(false, totalPoints, totalFields, totalEnsembles); if (getErrorCondition() < 0) { return; } size_t udims[3] = {0,0,0}; m->getDimensions(udims); #if (CMP_SIZEOF_SIZE_T == 4) typedef int32_t DimType; #else typedef int64_t DimType; #endif DimType dims[3] = { static_cast<DimType>(udims[0]), static_cast<DimType>(udims[1]), static_cast<DimType>(udims[2]), }; size_t xP = dims[0]; size_t yP = dims[1]; size_t zP = dims[2]; float xRes = m->getXRes(); float yRes = m->getYRes(); float zRes = m->getZRes(); int numNodes = (xP+1)*(yP+1)*(zP+1); int numTetrahedrons = 6*(xP*yP*zP); size_t point; size_t nodeId1, nodeId2, nodeId3, nodeId4, nodeId5, nodeId6, nodeId7, nodeId8; StructArray<Node>::Pointer vertices = StructArray<Node>::CreateArray(numNodes, DREAM3D::CellData::SolidMeshNodes); StructArray<Tetrahedron>::Pointer tetrahedrons = StructArray<Tetrahedron>::CreateArray(numTetrahedrons, DREAM3D::CellData::SolidMeshTetrahedrons); Node* vertex = vertices.get()->GetPointer(0); Tetrahedron* tetrahedron = tetrahedrons.get()->GetPointer(0); for(size_t k = 0; k < zP; k++) { for(size_t j = 0; j < yP; j++) { for(size_t i = 0; i < xP; i++) { point = (k*xP*yP)+(j*xP)+i; nodeId1 = (k*(xP+1)*(yP+1)) + (j*(xP+1)) + i; vertex[nodeId1].coord[0] = (i*xRes) - (xRes/2.0); vertex[nodeId1].coord[1] = (j*yRes) - (yRes/2.0); vertex[nodeId1].coord[2] = (k*zRes) - (zRes/2.0); nodeId2 = (k*(xP+1)*(yP+1)) + (j*(xP+1)) + (i+1); vertex[nodeId2].coord[0] = ((i+1)*xRes) - (xRes/2.0); vertex[nodeId2].coord[1] = (j*yRes) - (yRes/2.0); vertex[nodeId2].coord[2] = (k*zRes) - (zRes/2.0); nodeId3 = (k*(xP+1)*(yP+1)) + ((j+1)*(xP+1)) + i; vertex[nodeId3].coord[0] = (i*xRes) - (xRes/2.0); vertex[nodeId3].coord[1] = ((j+1)*yRes) - (yRes/2.0); vertex[nodeId3].coord[2] = (k*zRes) - (zRes/2.0); nodeId4 = (k*(xP+1)*(yP+1)) + ((j+1)*(xP+1)) + (i+1); vertex[nodeId4].coord[0] = ((i+1)*xRes) - (xRes/2.0); vertex[nodeId4].coord[1] = ((j+1)*yRes) - (yRes/2.0); vertex[nodeId4].coord[2] = (k*zRes) - (zRes/2.0); nodeId5 = ((k+1)*(xP+1)*(yP+1)) + (j*(xP+1)) + i; vertex[nodeId5].coord[0] = (i*xRes) - (xRes/2.0); vertex[nodeId5].coord[1] = (j*yRes) - (yRes/2.0); vertex[nodeId5].coord[2] = ((k+1)*zRes) - (zRes/2.0); nodeId6 = ((k+1)*(xP+1)*(yP+1)) + (j*(xP+1)) + (i+1); vertex[nodeId6].coord[0] = ((i+1)*xRes) - (xRes/2.0); vertex[nodeId6].coord[1] = (j*yRes) - (yRes/2.0); vertex[nodeId6].coord[2] = ((k+1)*zRes) - (zRes/2.0); nodeId7 = ((k+1)*(xP+1)*(yP+1)) + ((j+1)*(xP+1)) + i; vertex[nodeId7].coord[0] = (i*xRes) - (xRes/2.0); vertex[nodeId7].coord[1] = ((j+1)*yRes) - (yRes/2.0); vertex[nodeId7].coord[2] = ((k+1)*zRes) - (zRes/2.0); nodeId8 = ((k+1)*(xP+1)*(yP+1)) + ((j+1)*(xP+1)) + (i+1); vertex[nodeId8].coord[0] = ((i+1)*xRes) - (xRes/2.0); vertex[nodeId8].coord[1] = ((j+1)*yRes) - (yRes/2.0); vertex[nodeId8].coord[2] = ((k+1)*zRes) - (zRes/2.0); tetrahedron[6*point].node_id[0] = nodeId1; tetrahedron[6*point].node_id[1] = nodeId2; tetrahedron[6*point].node_id[2] = nodeId3; tetrahedron[6*point].node_id[3] = nodeId7; tetrahedron[6*point].nSpin = m_GrainIds[point]; tetrahedron[6*point+1].node_id[0] = nodeId2; tetrahedron[6*point+1].node_id[1] = nodeId4; tetrahedron[6*point+1].node_id[2] = nodeId3; tetrahedron[6*point+1].node_id[3] = nodeId7; tetrahedron[6*point+1].nSpin = m_GrainIds[point]; tetrahedron[6*point+2].node_id[0] = nodeId1; tetrahedron[6*point+2].node_id[1] = nodeId2; tetrahedron[6*point+2].node_id[2] = nodeId7; tetrahedron[6*point+2].node_id[3] = nodeId5; tetrahedron[6*point+2].nSpin = m_GrainIds[point]; tetrahedron[6*point+3].node_id[0] = nodeId2; tetrahedron[6*point+3].node_id[1] = nodeId4; tetrahedron[6*point+3].node_id[2] = nodeId7; tetrahedron[6*point+3].node_id[3] = nodeId8; tetrahedron[6*point+3].nSpin = m_GrainIds[point]; tetrahedron[6*point+4].node_id[0] = nodeId2; tetrahedron[6*point+4].node_id[1] = nodeId5; tetrahedron[6*point+4].node_id[2] = nodeId6; tetrahedron[6*point+4].node_id[3] = nodeId7; tetrahedron[6*point+4].nSpin = m_GrainIds[point]; tetrahedron[6*point+5].node_id[0] = nodeId6; tetrahedron[6*point+5].node_id[1] = nodeId8; tetrahedron[6*point+5].node_id[2] = nodeId2; tetrahedron[6*point+5].node_id[3] = nodeId7; tetrahedron[6*point+5].nSpin = m_GrainIds[point]; } } } sm->setTetrahedrons(tetrahedrons); sm->setNodes(vertices); notifyStatusMessage("Complete"); }
// ----------------------------------------------------------------------------- // // ----------------------------------------------------------------------------- void RemoveArrays::dataCheck(bool preflight, size_t voxels, size_t fields, size_t ensembles) { setErrorCondition(0); typedef std::set<std::string> NameList_t; VoxelDataContainer* m = getVoxelDataContainer(); if (NULL != m) { for(NameList_t::iterator iter = m_SelectedVoxelCellArrays.begin(); iter != m_SelectedVoxelCellArrays.end(); ++iter) { m->removeCellData(*iter); } for(NameList_t::iterator iter = m_SelectedVoxelFieldArrays.begin(); iter != m_SelectedVoxelFieldArrays.end(); ++iter) { m->removeFieldData(*iter); } for(NameList_t::iterator iter = m_SelectedVoxelEnsembleArrays.begin(); iter != m_SelectedVoxelEnsembleArrays.end(); ++iter) { m->removeEnsembleData(*iter); } } SurfaceMeshDataContainer* sm = getSurfaceMeshDataContainer(); if (NULL != sm) { for(NameList_t::iterator iter = m_SelectedSurfaceVertexArrays.begin(); iter != m_SelectedSurfaceVertexArrays.end(); ++iter) { sm->removeVertexData(*iter); } for(NameList_t::iterator iter = m_SelectedSurfaceFaceArrays.begin(); iter != m_SelectedSurfaceFaceArrays.end(); ++iter) { sm->removeFaceData(*iter); } for(NameList_t::iterator iter = m_SelectedSurfaceEdgeArrays.begin(); iter != m_SelectedSurfaceEdgeArrays.end(); ++iter) { sm->removeEdgeData(*iter); } for(NameList_t::iterator iter = m_SelectedSurfaceFieldArrays.begin(); iter != m_SelectedSurfaceFieldArrays.end(); ++iter) { sm->removeFieldData(*iter); } for(NameList_t::iterator iter = m_SelectedSurfaceEnsembleArrays.begin(); iter != m_SelectedSurfaceEnsembleArrays.end(); ++iter) { sm->removeEnsembleData(*iter); } } SolidMeshDataContainer* sol = getSolidMeshDataContainer(); if (NULL != sol) { for(NameList_t::iterator iter = m_SelectedSolidMeshVertexArrays.begin(); iter != m_SelectedSolidMeshVertexArrays.end(); ++iter) { sol->removeVertexData(*iter); } for(NameList_t::iterator iter = m_SelectedSolidMeshFaceArrays.begin(); iter != m_SelectedSolidMeshFaceArrays.end(); ++iter) { sol->removeFaceData(*iter); } for(NameList_t::iterator iter = m_SelectedSolidMeshEdgeArrays.begin(); iter != m_SelectedSolidMeshEdgeArrays.end(); ++iter) { sol->removeEdgeData(*iter); } } }
// ----------------------------------------------------------------------------- // // ----------------------------------------------------------------------------- void DecimateSolidMesh::execute() { setErrorCondition(0); VoxelDataContainer* m = getVoxelDataContainer(); SolidMeshDataContainer* sm = getSolidMeshDataContainer(); int64_t totalPoints = m->getTotalPoints(); size_t totalFields = m->getNumFieldTuples(); size_t totalEnsembles = m->getNumEnsembleTuples(); dataCheck(false, totalPoints, totalFields, totalEnsembles); if (getErrorCondition() < 0) { return; } StructArray<Node>& nodes = *(sm->getNodes()); StructArray<Tetrahedron>& tetrahedrons = *(sm->getTetrahedrons()); int numNodes = nodes.GetNumberOfTuples(); int numTets = tetrahedrons.GetNumberOfTuples(); int gnum; size_t nodeId1, nodeId2, nodeId3, nodeId4; //Locate Boundary Nodes nodeGrainIds.resize(numNodes,-1); nodeEuclideanDistances.resize(numNodes,-1); for(int k = 0; k < numTets; k++) { gnum = tetrahedrons[k].nSpin; // float x = nodes[k].coord[0]; nodeId1 = tetrahedrons[k].node_id[0]; nodeId2 = tetrahedrons[k].node_id[1]; nodeId3 = tetrahedrons[k].node_id[2]; nodeId4 = tetrahedrons[k].node_id[3]; if(nodeGrainIds[nodeId1] == -1 || nodeGrainIds[nodeId1] == gnum) nodeGrainIds[nodeId1] = gnum; else { nodeGrainIds[nodeId1] = -1000; nodeEuclideanDistances[nodeId1] = 0; } if(nodeGrainIds[nodeId2] == -1 || nodeGrainIds[nodeId2] == gnum) nodeGrainIds[nodeId2] = gnum; else { nodeGrainIds[nodeId2] = -1000; nodeEuclideanDistances[nodeId2] = 0; } if(nodeGrainIds[nodeId3] == -1 || nodeGrainIds[nodeId3] == gnum) nodeGrainIds[nodeId3] = gnum; else { nodeGrainIds[nodeId3] = -1000; nodeEuclideanDistances[nodeId3] = 0; } if(nodeGrainIds[nodeId4] == -1 || nodeGrainIds[nodeId4] == gnum) nodeGrainIds[nodeId4] = gnum; else { nodeGrainIds[nodeId4] = -1000; nodeEuclideanDistances[nodeId4] = 0; } } nodeGrainIds.clear(); //Determine Node Euclidean Distance Map tetDone.resize(numTets,false); int tetsLeft = 1; int ED1, ED2, ED3, ED4; int currentED = 0; int maxGlobalED = 0; while(tetsLeft > 0) { tetsLeft = 0; currentED++; for(int k = 0; k < numTets; k++) { if(tetDone[k] == false) { nodeId1 = tetrahedrons[k].node_id[0]; nodeId2 = tetrahedrons[k].node_id[1]; nodeId3 = tetrahedrons[k].node_id[2]; nodeId4 = tetrahedrons[k].node_id[3]; ED1 = nodeEuclideanDistances[nodeId1]; ED2 = nodeEuclideanDistances[nodeId2]; ED3 = nodeEuclideanDistances[nodeId3]; ED4 = nodeEuclideanDistances[nodeId4]; if(ED1 == -1 || ED2 == -1 || ED3 == -1 || ED4 == -1) tetsLeft++; if(ED1 == (currentED-1) || ED2 == (currentED-1) || ED3 == (currentED-1) || ED4 == (currentED-1)) { if(ED1 == -1) nodeEuclideanDistances[nodeId1] = currentED; if(ED2 == -1) nodeEuclideanDistances[nodeId2] = currentED; if(ED3 == -1) nodeEuclideanDistances[nodeId3] = currentED; if(ED4 == -1) nodeEuclideanDistances[nodeId4] = currentED; tetDone[k] = true; } } } maxGlobalED = currentED; } tetDone.clear(); //Decimate Mesh // ED1, ED2, ED3, ED4; int removeED = maxGlobalED; // int secondLargestED = 0; int point; int otherPoint; while(numTets > m_GoalElementNumber && removeED > 1) { for(int k = 0; k < numTets; k++) { nodeId1 = tetrahedrons[k].node_id[0]; nodeId2 = tetrahedrons[k].node_id[1]; nodeId3 = tetrahedrons[k].node_id[2]; nodeId4 = tetrahedrons[k].node_id[3]; ED1 = nodeEuclideanDistances[nodeId1]; ED2 = nodeEuclideanDistances[nodeId2]; ED3 = nodeEuclideanDistances[nodeId3]; ED4 = nodeEuclideanDistances[nodeId4]; if(ED1 >= removeED) { point = nodeId1; // secondLargestED = ED2; otherPoint = nodeId2; // if(ED3 > secondLargestED) secondLargestED = ED3, otherPoint = nodeId3; // if(ED4 > secondLargestED) secondLargestED = ED4, otherPoint = nodeId4; k = updateNodesandTets(k, point, otherPoint); } else if(ED2 >= removeED) { point = nodeId2; // secondLargestED = ED1; otherPoint = nodeId3; // if(ED3 > secondLargestED) secondLargestED = ED3, otherPoint = nodeId3; // if(ED4 > secondLargestED) secondLargestED = ED4, otherPoint = nodeId4; k = updateNodesandTets(k, point, otherPoint); } else if(ED3 >= removeED) { point = nodeId3; // secondLargestED = ED1; otherPoint = nodeId4; // if(ED2 > secondLargestED) secondLargestED = ED2, otherPoint = nodeId2; // if(ED4 > secondLargestED) secondLargestED = ED4, otherPoint = nodeId4; k = updateNodesandTets(k, point, otherPoint); } else if(ED4 >= removeED) { point = nodeId4; // secondLargestED = ED1; otherPoint = nodeId1; // if(ED2 > secondLargestED) secondLargestED = ED2, otherPoint = nodeId2; // if(ED3 > secondLargestED) secondLargestED = ED3, otherPoint = nodeId3; k = updateNodesandTets(k, point, otherPoint); } numTets = tetrahedrons.GetNumberOfTuples(); StructArray<Node>& nodes = *(sm->getNodes()); StructArray<Tetrahedron>& tetrahedrons = *(sm->getTetrahedrons()); numNodes = nodes.GetNumberOfTuples(); numTets = tetrahedrons.GetNumberOfTuples(); } removeED = removeED-1; } notifyStatusMessage("Complete"); }