40 vtkInformationVector **inputVector,
41 vtkInformationVector *outputVector) {
46 auto input = vtkUnstructuredGrid::GetData(inputVector[0]);
47 auto output = vtkUnstructuredGrid::GetData(outputVector);
49 vtkNew<vtkUnstructuredGrid> tmpGrid{};
51 output->DeepCopy(input);
52 tmpGrid->DeepCopy(input);
54 for(
int i = 0; i < IterationNumber; i++) {
56 std::vector<std::vector<vtkNew<vtkIdList>>> newCells(
57 tmpGrid->GetNumberOfCells());
58 std::vector<std::vector<std::vector<double>>> newPoints(
59 tmpGrid->GetNumberOfCells());
62 std::vector<std::vector<std::vector<double>>> newPointData(
63 tmpGrid->GetNumberOfCells());
64 std::vector<std::vector<std::vector<double>>> newCellData(
65 tmpGrid->GetNumberOfCells());
68 vtkNew<vtkGenericCell>
const threadCell{};
69 tmpGrid->GetCell(0, threadCell);
71 for(
int j = 0; j < tmpGrid->GetPointData()->GetNumberOfArrays(); j++) {
72 if(tmpGrid->GetPointData()->GetArray(j)->GetNumberOfComponents() == 1) {
73 tmpGrid->GetPointData()->GetArray(j)->GetTuple(0, &value);
76 for(
int j = 0; j < tmpGrid->GetCellData()->GetNumberOfArrays(); j++) {
77 if(tmpGrid->GetCellData()->GetArray(j)->GetNumberOfComponents() == 1) {
78 tmpGrid->GetCellData()->GetArray(j)->GetTuple(0, &value);
82#ifdef TTK_ENABLE_OPENMP
83#pragma omp parallel for num_threads(threadNumber_)
85 for(SimplexId j = 0; j < tmpGrid->GetNumberOfCells(); j++) {
87 vtkNew<vtkGenericCell> cell{};
88 tmpGrid->GetCell(j, cell);
90 std::vector<double> cellValues(
91 tmpGrid->GetCellData()->GetNumberOfArrays());
92 for(
int k = 0; k < (int)cellValues.size(); k++) {
93 if(tmpGrid->GetCellData()->GetArray(k)->GetNumberOfComponents() == 1) {
94 tmpGrid->GetCellData()->GetArray(k)->GetTuple(j, &(cellValues[k]));
98 newCells[j].resize(cell->GetNumberOfPoints());
99 newCellData[j].resize(cell->GetNumberOfPoints());
100 for(
int k = 0; k < (int)newCellData[j].size(); k++) {
101 newCellData[j][k] = cellValues;
104 newPoints[j].resize(cell->GetNumberOfPoints() + cell->GetNumberOfEdges()
105 + cell->GetNumberOfFaces() + 1);
106 newPointData[j].resize(cell->GetNumberOfPoints()
107 + cell->GetNumberOfEdges()
108 + cell->GetNumberOfFaces() + 1);
109 for(
int k = 0; k < (int)newPointData[j].size(); k++) {
110 newPointData[j][k].resize(tmpGrid->GetPointData()->GetNumberOfArrays());
113 SimplexId pointCounter = 0;
114 SimplexId globalPointCounter
116 * (cell->GetNumberOfPoints() + cell->GetNumberOfEdges()
117 + cell->GetNumberOfFaces() + 1);
120 std::vector<SimplexId> vertexMap(cell->GetNumberOfPoints());
121 for(
int k = 0; k < (int)cell->GetNumberOfPoints(); k++) {
123 tmpGrid->GetPoint(cell->GetPointId(k), p);
124 newPoints[j][pointCounter].resize(3, 0);
125 for(
int l = 0; l < 3; l++)
126 newPoints[j][pointCounter][l] = p[l];
130 for(
int l = 0; l < tmpGrid->GetPointData()->GetNumberOfArrays(); l++) {
131 if(tmpGrid->GetPointData()->GetArray(l)->GetNumberOfComponents()
133 tmpGrid->GetPointData()->GetArray(l)->GetTuple(
134 cell->GetPointId(k), &val);
135 newPointData[j][pointCounter][l] = val;
139 vertexMap[k] = globalPointCounter;
141 globalPointCounter++;
144 std::vector<SimplexId> edgeMap(cell->GetNumberOfEdges());
146 for(
int k = 0; k < cell->GetNumberOfEdges(); k++) {
148 vtkCell *edge = cell->GetEdge(k);
150 tmpGrid->GetPoint(edge->GetPointId(0), p0);
151 tmpGrid->GetPoint(edge->GetPointId(1), p1);
153 edgeMap[k] = globalPointCounter;
155 newPoints[j][pointCounter].resize(3);
156 for(
int l = 0; l < 3; l++)
157 newPoints[j][pointCounter][l] = 0.5 * (p0[l] + p1[l]);
160 double value0 = 0, value1 = 0;
161 for(
int l = 0; l < tmpGrid->GetPointData()->GetNumberOfArrays(); l++) {
162 if(tmpGrid->GetPointData()->GetArray(l)->GetNumberOfComponents()
164 tmpGrid->GetPointData()->GetArray(l)->GetTuple(
165 edge->GetPointId(0), &value0);
166 tmpGrid->GetPointData()->GetArray(l)->GetTuple(
167 edge->GetPointId(1), &value1);
168 newPointData[j][pointCounter][l] = 0.5 * value0 + 0.5 * value1;
173 globalPointCounter++;
177 std::vector<SimplexId> faceMap(cell->GetNumberOfFaces());
178 for(
int k = 0; k < cell->GetNumberOfFaces(); k++) {
180 vtkCell *face = cell->GetFace(k);
181 newPoints[j][pointCounter].resize(3, 0);
183 for(
int l = 0; l < face->GetNumberOfPoints(); l++) {
185 tmpGrid->GetPoint(face->GetPointId(l), p);
186 for(
int m = 0; m < 3; m++) {
187 newPoints[j][pointCounter][m] += p[m];
192 for(
int m = 0; m < tmpGrid->GetPointData()->GetNumberOfArrays();
195 if(tmpGrid->GetPointData()->GetArray(m)->GetNumberOfComponents()
197 tmpGrid->GetPointData()->GetArray(m)->GetTuple(
198 face->GetPointId(l), &val);
199 newPointData[j][pointCounter][m]
200 += (1 / ((double)face->GetNumberOfPoints())) * val;
205 faceMap[k] = globalPointCounter;
207 for(
int l = 0; l < 3; l++)
208 newPoints[j][pointCounter][l] /= (
double)face->GetNumberOfPoints();
211 globalPointCounter++;
215 for(
int k = 0; k < (int)cell->GetNumberOfPoints(); k++) {
217 tmpGrid->GetPoint(cell->GetPointId(k), p);
218 newPoints[j][pointCounter].resize(3, 0);
219 for(
int l = 0; l < 3; l++)
220 newPoints[j][pointCounter][l] += p[l];
224 for(
int l = 0; l < tmpGrid->GetPointData()->GetNumberOfArrays(); l++) {
226 if(tmpGrid->GetPointData()->GetArray(l)->GetNumberOfComponents()
228 tmpGrid->GetPointData()->GetArray(l)->GetTuple(
229 cell->GetPointId(k), &val);
230 newPointData[j][pointCounter][l]
231 += (1 / ((double)cell->GetNumberOfPoints())) * val;
235 for(
int k = 0; k < 3; k++)
236 newPoints[j][pointCounter][k] /= (
double)cell->GetNumberOfPoints();
242 for(
int k = 0; k < (int)cell->GetNumberOfPoints(); k++) {
244 SimplexId
const vertexId = cell->GetPointId(k);
246 if(cell->GetCellDimension() == 2) {
248 newCells[j][k]->InsertNextId(vertexMap[k]);
251 SimplexId firstEdge = -1;
252 for(
size_t l = 0; l < edgeMap.size(); l++) {
254 vtkCell *edge = cell->GetEdge(l);
255 SimplexId
const vertexId0 = edge->GetPointId(0);
256 SimplexId
const vertexId1 = edge->GetPointId(1);
258 if((vertexId == vertexId0) || (vertexId == vertexId1)) {
260 newCells[j][k]->InsertNextId(edgeMap[l]);
267 newCells[j][k]->InsertNextId(globalPointCounter);
270 for(SimplexId l = 0; l < static_cast<SimplexId>(edgeMap.size());
273 vtkCell *edge = cell->GetEdge(l);
274 SimplexId
const vertexId0 = edge->GetPointId(0);
275 SimplexId
const vertexId1 = edge->GetPointId(1);
278 && ((vertexId == vertexId0) || (vertexId == vertexId1))) {
280 newCells[j][k]->InsertNextId(edgeMap[l]);
284 }
else if(cell->GetCellDimension() == 3) {
287 newCells[j][k]->InsertNextId(vertexMap[k]);
290 SimplexId firstEdge = -1;
291 std::pair<SimplexId, SimplexId> firstEdgeVertices;
292 for(
size_t l = 0; l < edgeMap.size(); l++) {
294 vtkCell *edge = cell->GetEdge(l);
295 SimplexId
const vertexId0 = edge->GetPointId(0);
296 SimplexId
const vertexId1 = edge->GetPointId(1);
298 if((vertexId == vertexId0) || (vertexId == vertexId1)) {
300 newCells[j][k]->InsertNextId(edgeMap[l]);
301 firstEdgeVertices.first = vertexId0;
302 firstEdgeVertices.second = vertexId1;
308 std::vector<SimplexId> firstFaceVertices;
309 SimplexId firstFace = -1;
311 for(
size_t l = 0; l < faceMap.size(); l++) {
312 vtkCell *face = cell->GetFace(l);
315 bool vertex0In =
false;
316 bool vertex1In =
false;
317 for(
int m = 0; m < (int)face->GetNumberOfPoints(); m++) {
318 if(face->GetPointId(m) == firstEdgeVertices.first) {
321 if(face->GetPointId(m) == firstEdgeVertices.second) {
326 if((vertex0In) && (vertex1In)) {
327 newCells[j][k]->InsertNextId(faceMap[l]);
330 for(
int n = 0; n < face->GetNumberOfPoints(); n++) {
331 firstFaceVertices.push_back(face->GetPointId(n));
341 SimplexId secondEdge = -1;
342 for(SimplexId l = 0; l < static_cast<SimplexId>(edgeMap.size());
349 vtkCell *edge = cell->GetEdge(l);
350 SimplexId
const vertexId0 = edge->GetPointId(0);
351 SimplexId
const vertexId1 = edge->GetPointId(1);
354 bool vertex0In =
false;
355 bool vertex1In =
false;
356 for(
size_t m = 0; m < firstFaceVertices.size(); m++) {
357 if(firstFaceVertices[m] == vertexId0)
359 if(firstFaceVertices[m] == vertexId1)
363 if((l != firstEdge) && (vertex0In) && (vertex1In)
364 && ((vertexId == vertexId0) || (vertexId == vertexId1))) {
366 newCells[j][k]->InsertNextId(edgeMap[l]);
376 std::pair<SimplexId, SimplexId> thirdEdgeVertices;
377 for(SimplexId l = 0; l < static_cast<SimplexId>(edgeMap.size());
380 vtkCell *edge = cell->GetEdge(l);
381 SimplexId
const vertexId0 = edge->GetPointId(0);
382 SimplexId
const vertexId1 = edge->GetPointId(1);
384 if((l != firstEdge) && (l != secondEdge)
385 && ((vertexId == vertexId0) || (vertexId == vertexId1))) {
387 newCells[j][k]->InsertNextId(edgeMap[l]);
388 thirdEdgeVertices.first = vertexId0;
389 thirdEdgeVertices.second = vertexId1;
395 SimplexId secondFace = -1;
397 for(SimplexId l = faceMap.size() - 1; l >= 0; l--) {
398 vtkCell *face = cell->GetFace(l);
402 bool vertex0In =
false;
403 bool vertex1In =
false;
404 for(vtkIdType m = 0; m < face->GetNumberOfPoints(); m++) {
405 if(face->GetPointId(m) == thirdEdgeVertices.first) {
408 if(face->GetPointId(m) == thirdEdgeVertices.second) {
413 if((vertex0In) && (vertex1In)) {
414 newCells[j][k]->InsertNextId(faceMap[l]);
423 newCells[j][k]->InsertNextId(globalPointCounter);
426 SimplexId thirdFace = -1;
427 for(SimplexId l = 0; l < static_cast<SimplexId>(faceMap.size());
429 vtkCell *face = cell->GetFace(l);
431 if((l != firstFace) && (l != secondFace)) {
432 for(
int m = 0; m < (int)face->GetNumberOfPoints(); m++) {
433 if(face->GetPointId(m) == vertexId) {
434 newCells[j][k]->InsertNextId(faceMap[l]);
449 vtkNew<vtkPoints> pointSet{};
450 vtkNew<vtkCellArray> cellArray{};
452 std::vector<vtkNew<vtkDoubleArray>> pointData;
453 pointData.resize(tmpGrid->GetPointData()->GetNumberOfArrays());
454 for(
int j = 0; j < (int)pointData.size(); j++) {
455 pointData[j]->SetName(tmpGrid->GetPointData()->GetArray(j)->GetName());
458 std::vector<vtkNew<vtkDoubleArray>> cellData;
459 cellData.resize(tmpGrid->GetCellData()->GetNumberOfArrays());
460 for(
int j = 0; j < (int)cellData.size(); j++) {
461 cellData[j]->SetName(tmpGrid->GetCellData()->GetArray(j)->GetName());
465 for(
size_t j = 0; j < newPoints.size(); j++) {
466 for(
int k = 0; k < (int)newPoints[j].size(); k++) {
467 pointSet->InsertNextPoint(newPoints[j][k].data());
469 for(
int k = 0; k < (int)newPointData[j].size(); k++) {
470 for(
int l = 0; l < (int)newPointData[j][k].size(); l++) {
471 pointData[l]->InsertNextTuple1(newPointData[j][k][l]);
475 output->SetPoints(pointSet);
476 for(
int j = 0; j < (int)pointData.size(); j++) {
477 output->GetPointData()->AddArray(pointData[j]);
480 for(
size_t j = 0; j < newCells.size(); j++) {
481 for(
int k = 0; k < (int)newCells[j].size(); k++) {
482 cellArray->InsertNextCell(newCells[j][k]);
485 for(
int k = 0; k < (int)newCellData[j].size(); k++) {
486 for(
int l = 0; l < (int)newCellData[j][k].size(); l++) {
487 cellData[l]->InsertNextTuple1(newCellData[j][k][l]);
491 if(tmpGrid->GetCell(0)->GetCellDimension() == 3) {
492 output->SetCells(VTK_HEXAHEDRON, cellArray);
493 }
else if(tmpGrid->GetCell(0)->GetCellDimension() == 2) {
494 output->SetCells(VTK_POLYGON, cellArray);
496 for(
int j = 0; j < (int)cellData.size(); j++) {
497 output->GetCellData()->AddArray(cellData[j]);
500 if(i != IterationNumber - 1) {
501 tmpGrid->DeepCopy(output);
505 this->
printMsg(std::vector<std::vector<std::string>>{
506 {
"#OutputCells", std::to_string(output->GetNumberOfCells())}});
508 "Subdivision computed", 1.0, t.
getElapsedTime(), this->threadNumber_);