3#include <vtkInformation.h>
5#include <vtkDoubleArray.h>
6#include <vtkFloatArray.h>
7#include <vtkIdTypeArray.h>
8#include <vtkIntArray.h>
10#include <vtkPointData.h>
11#include <vtkPolyData.h>
12#include <vtkSignedCharArray.h>
22ttkScalarFieldCriticalPoints::ttkScalarFieldCriticalPoints() {
24 this->SetNumberOfInputPorts(1);
25 this->SetNumberOfOutputPorts(1);
28ttkScalarFieldCriticalPoints::~ttkScalarFieldCriticalPoints() =
default;
30int ttkScalarFieldCriticalPoints::FillInputPortInformation(
31 int port, vtkInformation *info) {
33 info->Set(vtkAlgorithm::INPUT_REQUIRED_DATA_TYPE(),
"vtkDataSet");
40int ttkScalarFieldCriticalPoints::FillOutputPortInformation(
41 int port, vtkInformation *info) {
43 info->Set(vtkDataObject::DATA_TYPE_NAME(),
"vtkPolyData");
50int ttkScalarFieldCriticalPoints::RequestData(
52 vtkInformationVector **inputVector,
53 vtkInformationVector *outputVector) {
55 vtkDataSet *input = vtkDataSet::GetData(inputVector[0]);
56 vtkPolyData *output = vtkPolyData::GetData(outputVector, 0);
60 int const keepGoing = checkEmptyMPIInput<Triangulation>(triangulation);
73 vtkDataArray *inputScalarField = this->GetInputArrayToProcess(0, inputVector);
77 vtkDataArray *offsetField = this->GetOrderArray(
78 input, 0, triangulation,
false, 1, ForceInputOffsetScalarField);
82 this->setOutput(&criticalPoints_);
84#ifdef TTK_ENABLE_MPI_TIME
90 printMsg({{
" Scalar Array", inputScalarField->GetName()},
91 {
" Offset Array", offsetField ? offsetField->GetName() :
"None"}});
96 (status = this->execute(
98 (TTK_TT *)triangulation->
getData())));
103#ifdef TTK_ENABLE_MPI_TIME
107 +
" MPI processes lasted: " + std::to_string(elapsedTime));
112 vtkNew<vtkSignedCharArray> vertexTypes{};
113 vertexTypes->SetNumberOfComponents(1);
114 vertexTypes->SetNumberOfTuples(criticalPoints_.size());
115 vertexTypes->SetName(
"CriticalType");
117 vtkNew<vtkPoints> pointSet{};
118 pointSet->SetNumberOfPoints(criticalPoints_.size());
120#ifdef TTK_ENABLE_OPENMP
121#pragma omp parallel for num_threads(this->threadNumber_)
123 for(
size_t i = 0; i < criticalPoints_.size(); i++) {
124 std::array<double, 3> p{};
125 input->GetPoint(criticalPoints_[i].first, p.data());
126 pointSet->SetPoint(i, p.data());
127 vertexTypes->SetTuple1(i, (
float)criticalPoints_[i].second);
131 output->GetPointData()->AddArray(vertexTypes);
134 vtkNew<vtkSignedCharArray> vertexBoundary{};
135 vertexBoundary->SetNumberOfComponents(1);
136 vertexBoundary->SetNumberOfTuples(criticalPoints_.size());
137 vertexBoundary->SetName(
"IsOnBoundary");
139#ifdef TTK_ENABLE_OPENMP
140#pragma omp parallel for num_threads(threadNumber_)
142 for(
size_t i = 0; i < criticalPoints_.size(); i++) {
143 vertexBoundary->SetTuple1(
145 criticalPoints_[i].first));
148 output->GetPointData()->AddArray(vertexBoundary);
150 output->GetPointData()->RemoveArray(
"IsOnBoundary");
154 vtkNew<ttkSimplexIdTypeArray> vertexIds{};
155 vertexIds->SetNumberOfComponents(1);
156 vertexIds->SetNumberOfTuples(criticalPoints_.size());
158 for(
size_t i = 0; i < criticalPoints_.size(); i++) {
160 if(hasInitializedMPI()) {
161 vertexIds->SetTuple1(
162 i, triangulation->getVertexGlobalId(criticalPoints_[i].first));
166 vertexIds->SetTuple1(i, criticalPoints_[i].first);
170 output->GetPointData()->AddArray(vertexIds);
176 for(
SimplexId i = 0; i < input->GetPointData()->GetNumberOfArrays(); i++) {
178 vtkDataArray *scalarField = input->GetPointData()->GetArray(i);
180 scalarField->NewInstance()};
182 scalarArray->SetNumberOfComponents(scalarField->GetNumberOfComponents());
183 scalarArray->SetNumberOfTuples(criticalPoints_.size());
184 scalarArray->SetName(scalarField->GetName());
185 std::vector<double> value(scalarField->GetNumberOfComponents());
186 for(
size_t j = 0; j < criticalPoints_.size(); j++) {
187 scalarField->GetTuple(criticalPoints_[j].first, value.data());
188 scalarArray->SetTuple(j, value.data());
190 output->GetPointData()->AddArray(scalarArray);
193 for(
SimplexId i = 0; i < input->GetPointData()->GetNumberOfArrays(); i++) {
194 output->GetPointData()->RemoveArray(
195 input->GetPointData()->GetArray(i)->GetName());
#define ttkTemplateMacro(triangulationType, call)
#define ttkNotUsed(x)
Mark function/method parameters that are not used in the function body at all.
ttk::Triangulation * GetTriangulation(vtkDataSet *dataSet)
static void * GetVoidPointer(vtkDataArray *array, vtkIdType start=0)
static int CellVertexFromPoints(vtkDataSet *const dataSet, vtkPoints *const points)
Triangulation is a class that provides time and memory efficient traversal methods on triangulations ...
AbstractTriangulation * getData()
bool isVertexOnBoundary(const SimplexId &vertexId) const override
Triangulation::Type getType() const
int preconditionBoundaryVertices() override
void preconditionTriangulation(AbstractTriangulation &triangulation)
Triangulation precondition function.
TTK base package defining the standard types.
COMMON_EXPORTS int MPIsize_
int SimplexId
Identifier type for simplices of any dimension.
COMMON_EXPORTS int MPIrank_
const char VertexScalarFieldName[]
default name for vertex scalar field
vtkStandardNewMacro(ttkScalarFieldCriticalPoints)
printMsg(debug::output::BOLD+" | | | | | . \\ | | (__| | / __/| |_| / __/| (_) |"+debug::output::ENDCOLOR, debug::Priority::PERFORMANCE, debug::LineMode::NEW, stream)