/*========================================================================= Program: Visualization Toolkit Module: $RCSfile: vtkFieldDataToAttributeDataFilter.cxx,v $ Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen All rights reserved. See Copyright.txt or http://www.kitware.com/Copyright.htm for details. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the above copyright notice for more information. =========================================================================*/ #include "vtkFieldDataToAttributeDataFilter.h" #include "vtkCellData.h" #include "vtkDataArray.h" #include "vtkDataSet.h" #include "vtkInformation.h" #include "vtkInformationVector.h" #include "vtkObjectFactory.h" #include "vtkPointData.h" #include "vtkStreamingDemandDrivenPipeline.h" vtkCxxRevisionMacro(vtkFieldDataToAttributeDataFilter, "$Revision: 1.39 $"); vtkStandardNewMacro(vtkFieldDataToAttributeDataFilter); // Instantiate object with no input and no defined output. vtkFieldDataToAttributeDataFilter::vtkFieldDataToAttributeDataFilter() { int i; this->InputField = VTK_DATA_OBJECT_FIELD; this->OutputAttributeData = VTK_POINT_DATA; this->DefaultNormalize = 0; this->NumberOfScalarComponents = 0; for (i=0; i < 4; i++) { this->ScalarArrays[i] = NULL; this->ScalarArrayComponents[i] = -1; //uninitialized this->ScalarComponentRange[i][0] = this->ScalarComponentRange[i][1] = -1; this->ScalarNormalize[i] = 1; //yes, normalize } for (i=0; i < 3; i++) { this->VectorArrays[i] = NULL; this->VectorArrayComponents[i] = -1; //uninitialized this->VectorComponentRange[i][0] = this->VectorComponentRange[i][1] = -1; this->VectorNormalize[i] = 1; //yes, normalize } for (i=0; i < 3; i++) { this->NormalArrays[i] = NULL; this->NormalArrayComponents[i] = -1; //uninitialized this->NormalComponentRange[i][0] = this->NormalComponentRange[i][1] = -1; this->NormalNormalize[i] = 1; //yes, normalize } this->NumberOfTCoordComponents = 0; for (i=0; i < 3; i++) { this->TCoordArrays[i] = NULL; this->TCoordArrayComponents[i] = -1; //uninitialized this->TCoordComponentRange[i][0] = this->TCoordComponentRange[i][1] = -1; this->TCoordNormalize[i] = 1; //yes, normalize } for (i=0; i < 9; i++) { this->TensorArrays[i] = NULL; this->TensorArrayComponents[i] = -1; //uninitialized this->TensorComponentRange[i][0] = this->TensorComponentRange[i][1] = -1; this->TensorNormalize[i] = 1; //yes, normalize } } vtkFieldDataToAttributeDataFilter::~vtkFieldDataToAttributeDataFilter() { int i; for (i=0; i<4; i++) { if ( this->ScalarArrays[i] != NULL ) { delete [] this->ScalarArrays[i]; } } for (i=0; i<3; i++) { if ( this->VectorArrays[i] != NULL ) { delete [] this->VectorArrays[i]; } } for (i=0; i<3; i++) { if ( this->NormalArrays[i] != NULL ) { delete [] this->NormalArrays[i]; } } for (i=0; i<3; i++) { if ( this->TCoordArrays[i] != NULL ) { delete [] this->TCoordArrays[i]; } } for (i=0; i<9; i++) { if ( this->TensorArrays[i] != NULL ) { delete [] this->TensorArrays[i]; } } } // Stuff related to filter interface------------------------------------------ // int vtkFieldDataToAttributeDataFilter::RequestData( vtkInformation *vtkNotUsed(request), vtkInformationVector **inputVector, vtkInformationVector *outputVector) { // get the info objects vtkInformation *inInfo = inputVector[0]->GetInformationObject(0); vtkInformation *outInfo = outputVector->GetInformationObject(0); // get the input and ouptut vtkDataSet *input = vtkDataSet::SafeDownCast( inInfo->Get(vtkDataObject::DATA_OBJECT())); vtkDataSet *output = vtkDataSet::SafeDownCast( outInfo->Get(vtkDataObject::DATA_OBJECT())); vtkIdType num; vtkDataSetAttributes *attr; vtkFieldData *fd; vtkDebugMacro(<<"Generating attribute data from field data"); // First, copy the input to the output as a starting point output->CopyStructure( input ); // Pass here so that the attributes/fields can be over-written later output->GetPointData()->PassData(input->GetPointData()); output->GetCellData()->PassData(input->GetCellData()); if ( this->OutputAttributeData == VTK_CELL_DATA ) { attr = output->GetCellData(); num = input->GetNumberOfCells(); } else { attr = output->GetPointData(); num = input->GetNumberOfPoints(); } if ( num < 1 ) { vtkDebugMacro(<<"No input points/cells to create attribute data for"); return 1; } fd = NULL; if ( this->InputField == VTK_DATA_OBJECT_FIELD ) { fd = input->GetFieldData(); } else if ( this->InputField == VTK_POINT_DATA_FIELD ) { fd = input->GetPointData(); } else if ( this->InputField == VTK_CELL_DATA_FIELD ) { fd = input->GetCellData(); } if ( fd == NULL ) { vtkErrorMacro(<<"No field data available"); return 1; } this->ConstructScalars(num, fd, attr, this->ScalarComponentRange, this->ScalarArrays, this->ScalarArrayComponents, this->ScalarNormalize,this->NumberOfScalarComponents); this->ConstructVectors(num, fd, attr, this->VectorComponentRange, this->VectorArrays, this->VectorArrayComponents, this->VectorNormalize); this->ConstructTensors(num, fd, attr, this->TensorComponentRange, this->TensorArrays, this->TensorArrayComponents, this->TensorNormalize); this->ConstructTCoords(num, fd, attr, this->TCoordComponentRange, this->TCoordArrays, this->TCoordArrayComponents, this->TCoordNormalize,this->NumberOfTCoordComponents); this->ConstructNormals(num, fd, attr, this->NormalComponentRange, this->NormalArrays, this->NormalArrayComponents, this->NormalNormalize); this->ConstructFieldData(num, attr); return 1; } void vtkFieldDataToAttributeDataFilter::PrintSelf(ostream& os, vtkIndent indent) { this->Superclass::PrintSelf(os,indent); os << indent << "Input Field: "; if ( this->InputField == VTK_DATA_OBJECT_FIELD ) { os << "DataObjectField\n"; } else if ( this->InputField == VTK_POINT_DATA_FIELD ) { os << "PointDataField\n"; } else //if ( this->InputField == VTK_CELL_DATA_FIELD ) { os << "CellDataField\n"; } os << indent << "Default Normalize: " << (this->DefaultNormalize ? "On\n" : "Off\n"); os << indent << "Output Attribute Data: "; if ( this->OutputAttributeData == VTK_CELL_DATA ) { os << "CellData\n"; } else //if ( this->OutputAttributeData == VTK_POINT_DATA ) { os << "PointData\n"; } } // Stuff related to scalars -------------------------------------------- // void vtkFieldDataToAttributeDataFilter::SetScalarComponent(int comp, const char *arrayName, int arrayComp, int min, int max, int normalize) { if ( comp < 0 || comp > 3 ) { vtkErrorMacro(<<"Scalar component must be between (0,3)"); return; } if ( comp >= this->NumberOfScalarComponents ) { this->NumberOfScalarComponents = comp + 1; } this->SetArrayName(this, this->ScalarArrays[comp], arrayName); if ( this->ScalarArrayComponents[comp] != arrayComp ) { this->ScalarArrayComponents[comp] = arrayComp; this->Modified(); } if ( this->ScalarComponentRange[comp][0] != min ) { this->ScalarComponentRange[comp][0] = min; this->Modified(); } if ( this->ScalarComponentRange[comp][1] != max ) { this->ScalarComponentRange[comp][1] = max; this->Modified(); } if ( this->ScalarNormalize[comp] != normalize ) { this->ScalarNormalize[comp] = normalize; this->Modified(); } } const char *vtkFieldDataToAttributeDataFilter::GetScalarComponentArrayName(int comp) { comp = (comp < 0 ? 0 : (comp > 3 ? 3 : comp)); return this->ScalarArrays[comp]; } int vtkFieldDataToAttributeDataFilter::GetScalarComponentArrayComponent(int comp) { comp = (comp < 0 ? 0 : (comp > 3 ? 3 : comp)); return this->ScalarArrayComponents[comp]; } int vtkFieldDataToAttributeDataFilter::GetScalarComponentMinRange(int comp) { comp = (comp < 0 ? 0 : (comp > 3 ? 3 : comp)); return this->ScalarComponentRange[comp][0]; } int vtkFieldDataToAttributeDataFilter::GetScalarComponentMaxRange(int comp) { comp = (comp < 0 ? 0 : (comp > 3 ? 3 : comp)); return this->ScalarComponentRange[comp][1]; } int vtkFieldDataToAttributeDataFilter::GetScalarComponentNormalizeFlag(int comp) { comp = (comp < 0 ? 0 : (comp > 3 ? 3 : comp)); return this->ScalarNormalize[comp]; } void vtkFieldDataToAttributeDataFilter::ConstructScalars(int num, vtkFieldData *fd, vtkDataSetAttributes *attr, vtkIdType componentRange[4][2], char *arrays[4], int arrayComp[4], int normalize[4], int numComp) { int i, normalizeAny, updated=0; vtkDataArray *fieldArray[4]; if ( numComp < 1 ) { return; } for (i=0; iGetFieldArray(fd, arrays[i], arrayComp[i]); if ( fieldArray[i] == NULL ) { vtkErrorMacro(<<"Can't find array/component requested"); return; } } for (normalizeAny=i=0; i < numComp; i++) { updated |= this->UpdateComponentRange(fieldArray[i], componentRange[i]); if ( num != (componentRange[i][1] - componentRange[i][0] + 1) ) { vtkErrorMacro(<<"Number of scalars not consistent"); return; } normalizeAny |= normalize[i]; } vtkDataArray *newScalars; for (i=1; i < numComp; i++) //see whether all the data is from the same array { if ( fieldArray[i] != fieldArray[i-1] ) { break; } } // see whether we can reuse the data array from the field if ( i >= numComp && fieldArray[0]->GetNumberOfComponents() == numComp && fieldArray[0]->GetNumberOfTuples() == num && !normalizeAny ) { newScalars = fieldArray[0]; newScalars->Register(0); } else //have to copy data into created array { newScalars = vtkDataArray::CreateDataArray(this->GetComponentsType(numComp, fieldArray)); newScalars->SetNumberOfTuples(num); for ( i=0; i < numComp; i++ ) { if ( this->ConstructArray(newScalars, i, fieldArray[i], arrayComp[i], componentRange[i][0], componentRange[i][1], normalize[i]) == 0 ) { newScalars->Delete(); return; } } } attr->SetScalars(newScalars); newScalars->Delete(); if ( updated ) //reset for next execution pass { for (i=0; i < numComp; i++) { componentRange[i][0] = componentRange[i][1] = -1; } } } // Stuff related to vectors -------------------------------------------- // void vtkFieldDataToAttributeDataFilter::SetVectorComponent(int comp, const char *arrayName, int arrayComp, int min, int max, int normalize) { if ( comp < 0 || comp > 2 ) { vtkErrorMacro(<<"Vector component must be between (0,2)"); return; } this->SetArrayName(this, this->VectorArrays[comp], arrayName); if ( this->VectorArrayComponents[comp] != arrayComp ) { this->VectorArrayComponents[comp] = arrayComp; this->Modified(); } if ( this->VectorComponentRange[comp][0] != min ) { this->VectorComponentRange[comp][0] = min; this->Modified(); } if ( this->VectorComponentRange[comp][1] != max ) { this->VectorComponentRange[comp][1] = max; this->Modified(); } if ( this->VectorNormalize[comp] != normalize ) { this->VectorNormalize[comp] = normalize; this->Modified(); } } const char *vtkFieldDataToAttributeDataFilter::GetVectorComponentArrayName(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->VectorArrays[comp]; } int vtkFieldDataToAttributeDataFilter::GetVectorComponentArrayComponent(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->VectorArrayComponents[comp]; } int vtkFieldDataToAttributeDataFilter::GetVectorComponentMinRange(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->VectorComponentRange[comp][0]; } int vtkFieldDataToAttributeDataFilter::GetVectorComponentMaxRange(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->VectorComponentRange[comp][1]; } int vtkFieldDataToAttributeDataFilter::GetVectorComponentNormalizeFlag(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->VectorNormalize[comp]; } void vtkFieldDataToAttributeDataFilter::ConstructVectors(int num, vtkFieldData *fd, vtkDataSetAttributes *attr, vtkIdType componentRange[3][2], char *arrays[3], int arrayComp[3], int normalize[3]) { int i, updated; vtkDataArray *fieldArray[3]; for (i=0; i<3; i++) { if ( arrays[i] == NULL ) { return; } } for ( i=0; i < 3; i++ ) { fieldArray[i] = this->GetFieldArray(fd, arrays[i], arrayComp[i]); if ( fieldArray[i] == NULL ) { vtkErrorMacro(<<"Can't find array requested"); return; } } updated = this->UpdateComponentRange(fieldArray[0], componentRange[0]); updated |= this->UpdateComponentRange(fieldArray[1], componentRange[1]); updated |= this->UpdateComponentRange(fieldArray[2], componentRange[2]); if ( num != (componentRange[0][1] - componentRange[0][0] + 1) || num != (componentRange[1][1] - componentRange[1][0] + 1) || num != (componentRange[2][1] - componentRange[2][0] + 1) ) { vtkErrorMacro(<<"Number of vectors not consistent"); return; } vtkDataArray *newVectors; if ( fieldArray[0]->GetNumberOfComponents() == 3 && fieldArray[0] == fieldArray[1] && fieldArray[1] == fieldArray[2] && fieldArray[0]->GetNumberOfTuples() == num && !normalize[0] && !normalize[1] && !normalize[2] ) { newVectors = fieldArray[0]; newVectors->Register(0); } else //have to copy data into created array { newVectors = vtkDataArray::CreateDataArray(this->GetComponentsType(3,fieldArray)); newVectors->SetNumberOfComponents(3); newVectors->SetNumberOfTuples(num); for ( i=0; i < 3; i++ ) { if ( this->ConstructArray(newVectors, i, fieldArray[i], arrayComp[i], componentRange[i][0], componentRange[i][1], normalize[i]) == 0 ) { newVectors->Delete(); return; } } } attr->SetVectors(newVectors); newVectors->Delete(); if ( updated ) //reset for next execution pass { for (i=0; i < 3; i++) { componentRange[i][0] = componentRange[i][1] = -1; } } } // Stuff related to normals -------------------------------------------- // void vtkFieldDataToAttributeDataFilter::SetNormalComponent(int comp, const char *arrayName, int arrayComp, int min, int max, int normalize) { if ( comp < 0 || comp > 2 ) { vtkErrorMacro(<<"Normal component must be between (0,2)"); return; } this->SetArrayName(this, this->NormalArrays[comp], arrayName); if ( this->NormalArrayComponents[comp] != arrayComp ) { this->NormalArrayComponents[comp] = arrayComp; this->Modified(); } if ( this->NormalComponentRange[comp][0] != min ) { this->NormalComponentRange[comp][0] = min; this->Modified(); } if ( this->NormalComponentRange[comp][1] != max ) { this->NormalComponentRange[comp][1] = max; this->Modified(); } if ( this->NormalNormalize[comp] != normalize ) { this->NormalNormalize[comp] = normalize; this->Modified(); } } const char *vtkFieldDataToAttributeDataFilter::GetNormalComponentArrayName(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->NormalArrays[comp]; } int vtkFieldDataToAttributeDataFilter::GetNormalComponentArrayComponent(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->NormalArrayComponents[comp]; } int vtkFieldDataToAttributeDataFilter::GetNormalComponentMinRange(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->NormalComponentRange[comp][0]; } int vtkFieldDataToAttributeDataFilter::GetNormalComponentMaxRange(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->NormalComponentRange[comp][1]; } int vtkFieldDataToAttributeDataFilter::GetNormalComponentNormalizeFlag(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->NormalNormalize[comp]; } void vtkFieldDataToAttributeDataFilter::ConstructNormals(int num, vtkFieldData *fd, vtkDataSetAttributes *attr, vtkIdType componentRange[3][2], char *arrays[3], int arrayComp[3], int normalize[3]) { int i, updated; vtkDataArray *fieldArray[3]; for (i=0; i<3; i++) { if ( arrays[i] == NULL ) { return; } } for ( i=0; i < 3; i++ ) { fieldArray[i] = this->GetFieldArray(fd, arrays[i], arrayComp[i]); if ( fieldArray[i] == NULL ) { vtkErrorMacro(<<"Can't find array requested"); return; } } updated = this->UpdateComponentRange(fieldArray[0], componentRange[0]); updated |= this->UpdateComponentRange(fieldArray[1], componentRange[1]); updated |= this->UpdateComponentRange(fieldArray[2], componentRange[2]); if ( num != (componentRange[0][1] - componentRange[0][0] + 1) || num != (componentRange[1][1] - componentRange[1][0] + 1) || num != (componentRange[2][1] - componentRange[2][0] + 1) ) { vtkErrorMacro(<<"Number of normals not consistent"); return; } vtkDataArray *newNormals; if ( fieldArray[0]->GetNumberOfComponents() == 3 && fieldArray[0] == fieldArray[1] && fieldArray[1] == fieldArray[2] && fieldArray[0]->GetNumberOfTuples() == num && !normalize[0] && !normalize[1] && !normalize[2] ) { newNormals = fieldArray[0]; newNormals->Register(0); } else //have to copy data into created array { newNormals = vtkDataArray::CreateDataArray(this->GetComponentsType(3, fieldArray)); newNormals->SetNumberOfComponents(3); newNormals->SetNumberOfTuples(num); for ( i=0; i < 3; i++ ) { if ( this->ConstructArray(newNormals, i, fieldArray[i], arrayComp[i], componentRange[i][0], componentRange[i][1], normalize[i]) == 0 ) { newNormals->Delete(); return; } } } attr->SetNormals(newNormals); newNormals->Delete(); if ( updated ) //reset for next execution pass { for (i=0; i < 3; i++) { componentRange[i][0] = componentRange[i][1] = -1; } } } // Stuff related to texture coords -------------------------------------------- // void vtkFieldDataToAttributeDataFilter::SetTCoordComponent(int comp, const char *arrayName, int arrayComp, int min, int max, int normalize) { if ( comp < 0 || comp > 2 ) { vtkErrorMacro(<<"TCoord component must be between (0,2)"); return; } if ( comp >= this->NumberOfTCoordComponents ) { this->NumberOfTCoordComponents = comp + 1; } this->SetArrayName(this, this->TCoordArrays[comp], arrayName); if ( this->TCoordArrayComponents[comp] != arrayComp ) { this->TCoordArrayComponents[comp] = arrayComp; this->Modified(); } if ( this->TCoordComponentRange[comp][0] != min ) { this->TCoordComponentRange[comp][0] = min; this->Modified(); } if ( this->TCoordComponentRange[comp][1] != max ) { this->TCoordComponentRange[comp][1] = max; this->Modified(); } if ( this->TCoordNormalize[comp] != normalize ) { this->TCoordNormalize[comp] = normalize; this->Modified(); } } const char *vtkFieldDataToAttributeDataFilter::GetTCoordComponentArrayName(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->TCoordArrays[comp]; } int vtkFieldDataToAttributeDataFilter::GetTCoordComponentArrayComponent(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->TCoordArrayComponents[comp]; } int vtkFieldDataToAttributeDataFilter::GetTCoordComponentMinRange(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->TCoordComponentRange[comp][0]; } int vtkFieldDataToAttributeDataFilter::GetTCoordComponentMaxRange(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->TCoordComponentRange[comp][1]; } int vtkFieldDataToAttributeDataFilter::GetTCoordComponentNormalizeFlag(int comp) { comp = (comp < 0 ? 0 : (comp > 2 ? 2 : comp)); return this->TCoordNormalize[comp]; } void vtkFieldDataToAttributeDataFilter::ConstructTCoords(int num, vtkFieldData *fd, vtkDataSetAttributes *attr, vtkIdType componentRange[3][2], char *arrays[3], int arrayComp[3], int normalize[3], int numComp) { int i, normalizeAny, updated=0; vtkDataArray *fieldArray[3]; if ( numComp < 1 ) { return; } for (i=0; iGetFieldArray(fd, arrays[i], arrayComp[i]); if ( fieldArray[i] == NULL ) { vtkErrorMacro(<<"Can't find array/component requested"); return; } normalizeAny |= normalize[i]; } for (i=0; i < numComp; i++) { updated |= this->UpdateComponentRange(fieldArray[i], componentRange[i]); if ( num != (componentRange[i][1] - componentRange[i][0] + 1) ) { vtkErrorMacro(<<"Number of texture coords not consistent"); return; } } vtkDataArray *newTCoords; for (i=1; i < numComp; i++) //see whether all the data is from the same array { if ( fieldArray[i] != fieldArray[i-1] ) { break; } } // see whether we can reuse the data array from the field if ( i >= numComp && fieldArray[0]->GetNumberOfComponents() == numComp && fieldArray[0]->GetNumberOfTuples() == num && !normalizeAny ) { newTCoords = fieldArray[0]; newTCoords->Register(0); } else //have to copy data into created array { newTCoords = vtkDataArray::CreateDataArray(this->GetComponentsType(numComp, fieldArray)); newTCoords->SetNumberOfComponents(numComp); newTCoords->SetNumberOfTuples(num); for ( i=0; i < numComp; i++ ) { if ( this->ConstructArray(newTCoords, i, fieldArray[i], arrayComp[i], componentRange[i][0], componentRange[i][1], normalize[i]) == 0 ) { newTCoords->Delete(); return; } } } attr->SetTCoords(newTCoords); newTCoords->Delete(); if ( updated ) //reset for next execution pass { for (i=0; i < numComp; i++) { componentRange[i][0] = componentRange[i][1] = -1; } } } // Stuff related to tensors -------------------------------------------- // void vtkFieldDataToAttributeDataFilter::SetTensorComponent(int comp, const char *arrayName, int arrayComp, int min, int max, int normalize) { if ( comp < 0 || comp > 8 ) { vtkErrorMacro(<<"Tensor component must be between (0,8)"); return; } this->SetArrayName(this, this->TensorArrays[comp], arrayName); if ( this->TensorArrayComponents[comp] != arrayComp ) { this->TensorArrayComponents[comp] = arrayComp; this->Modified(); } if ( this->TensorComponentRange[comp][0] != min ) { this->TensorComponentRange[comp][0] = min; this->Modified(); } if ( this->TensorComponentRange[comp][1] != max ) { this->TensorComponentRange[comp][1] = max; this->Modified(); } if ( this->TensorNormalize[comp] != normalize ) { this->TensorNormalize[comp] = normalize; this->Modified(); } } const char *vtkFieldDataToAttributeDataFilter::GetTensorComponentArrayName(int comp) { comp = (comp < 0 ? 0 : (comp > 8 ? 8 : comp)); return this->TensorArrays[comp]; } int vtkFieldDataToAttributeDataFilter::GetTensorComponentArrayComponent(int comp) { comp = (comp < 0 ? 0 : (comp > 8 ? 8 : comp)); return this->TensorArrayComponents[comp]; } int vtkFieldDataToAttributeDataFilter::GetTensorComponentMinRange(int comp) { comp = (comp < 0 ? 0 : (comp > 8 ? 8 : comp)); return this->TensorComponentRange[comp][0]; } int vtkFieldDataToAttributeDataFilter::GetTensorComponentMaxRange(int comp) { comp = (comp < 0 ? 0 : (comp > 8 ? 8 : comp)); return this->TensorComponentRange[comp][1]; } int vtkFieldDataToAttributeDataFilter::GetTensorComponentNormalizeFlag(int comp) { comp = (comp < 0 ? 0 : (comp > 8 ? 8 : comp)); return this->TensorNormalize[comp]; } void vtkFieldDataToAttributeDataFilter::ConstructTensors(int num, vtkFieldData *fd, vtkDataSetAttributes *attr, vtkIdType componentRange[9][2], char *arrays[9], int arrayComp[9], int normalize[9]) { int i, normalizeAny, updated=0; vtkDataArray *fieldArray[9]; for (i=0; i<9; i++) { if ( arrays[i] == NULL ) { return; } } for ( i=0; i < 9; i++ ) { fieldArray[i] = this->GetFieldArray(fd, arrays[i], arrayComp[i]); if ( fieldArray[i] == NULL ) { vtkErrorMacro(<<"Can't find array requested"); return; } } for (normalizeAny=i=0; i < 9; i++) { updated |= this->UpdateComponentRange(fieldArray[i], componentRange[i]); if ( num != (componentRange[i][1] - componentRange[i][0] + 1) ) { vtkErrorMacro(<<"Number of tensors not consistent"); return; } normalizeAny |= normalize[i]; } vtkDataArray *newTensors; for (i=1; i < 9; i++) //see whether all the data is from the same array { if ( fieldArray[i] != fieldArray[i-1] ) { break; } } // see whether we can reuse the data array from the field if ( i >= 9 && fieldArray[0]->GetNumberOfComponents() == 9 && fieldArray[0]->GetNumberOfTuples() == num && !normalizeAny ) { newTensors = fieldArray[0]; newTensors->Register(0); } else //have to copy data into created array { newTensors = vtkDataArray::CreateDataArray(this->GetComponentsType(9, fieldArray)); newTensors->SetNumberOfComponents(9); newTensors->SetNumberOfTuples(num); for ( i=0; i < 9; i++ ) { if ( this->ConstructArray(newTensors, i, fieldArray[i], arrayComp[i], componentRange[i][0], componentRange[i][1], normalize[i]) == 0 ) { newTensors->Delete(); return; } } } attr->SetTensors(newTensors); newTensors->Delete(); if ( updated ) //reset for next execution pass { for (i=0; i < 9; i++) { componentRange[i][0] = componentRange[i][1] = -1; } } } // Stuff related to fields -------------------------------------------- // void vtkFieldDataToAttributeDataFilter::ConstructFieldData(int vtkNotUsed(num), vtkDataSetAttributes *vtkNotUsed(attr)) { } // Stuff related to helper methods --------------------------------------- // int vtkFieldDataToAttributeDataFilter::ConstructArray(vtkDataArray *da, int comp, vtkDataArray *fieldArray, int fieldComp, vtkIdType min, vtkIdType max, int normalize) { vtkIdType i, n=max-min+1; float minValue=VTK_LARGE_FLOAT; float maxValue= -VTK_LARGE_FLOAT; float compRange, compValue; if ( fieldComp >= fieldArray->GetNumberOfComponents() ) { vtkGenericWarningMacro(<<"Trying to access component out of range"); return 0; } for (i=0; i < n; i++) { compValue = fieldArray->GetComponent(min+i, fieldComp); if ( compValue < minValue ) { minValue = compValue; } if ( compValue > maxValue ) { maxValue = compValue; } da->SetComponent(i, comp, compValue); } if ( normalize ) { compRange = maxValue - minValue; if ( compRange != 0.0 ) { for (i=0; i < n; i++) { compValue = da->GetComponent(i, comp); compValue = (compValue - minValue) / compRange; da->SetComponent(i, comp, compValue); } } } return 1; } int vtkFieldDataToAttributeDataFilter::GetComponentsType(int numComp, vtkDataArray **arrays) { int type, mostComplexType=VTK_VOID; for (int i=0; i < numComp; i++) { type = arrays[i]->GetDataType(); if ( type > mostComplexType ) { mostComplexType = type; } } return mostComplexType; } vtkDataArray *vtkFieldDataToAttributeDataFilter::GetFieldArray(vtkFieldData *fd, char *name, int comp) { vtkDataArray *da = NULL; int numComp; int found=0; if ( name != NULL ) { vtkDataSetAttributes* dsa; if ((dsa=vtkDataSetAttributes::SafeDownCast(fd))) { found=1; if(!strcmp("PointScalars", name) || !strcmp("CellScalars", name)) { da = dsa->GetScalars(); } else if(!strcmp("PointVectors", name) || !strcmp("CellVectors", name)) { da = dsa->GetVectors(); } else if(!strcmp("PointTensors", name) || !strcmp("CellTensors", name)) { da = dsa->GetTensors(); } else if(!strcmp("PointNormals", name) || !strcmp("CellNormals", name)) { da = dsa->GetNormals(); } else if(!strcmp("PointTCoords", name) || !strcmp("CellTCoords", name)) { da = dsa->GetTCoords(); } else { found=0; } } if (!found || !da) { da = fd->GetArray(name); } if ( da == NULL ) { return NULL; } numComp = da->GetNumberOfComponents(); if ( comp < 0 || comp >= numComp ) { return NULL; } else { return da; } } return NULL; } void vtkFieldDataToAttributeDataFilter::SetArrayName(vtkObject *self, char* &name, const char *newName) { if ( name && newName && (!strcmp(name,newName))) { return; } if (name) { delete [] name; } if (newName) { name = new char[strlen(newName)+1]; strcpy(name,newName); } else { name = NULL; } self->Modified(); } int vtkFieldDataToAttributeDataFilter::UpdateComponentRange(vtkDataArray *da, vtkIdType compRange[2]) { if ( compRange[0] == -1 ) { compRange[0] = 0; compRange[1] = da->GetNumberOfTuples() - 1; return 1; } else { return 0; } } //---------------------------------------------------------------------------- int vtkFieldDataToAttributeDataFilter::RequestUpdateExtent( vtkInformation *vtkNotUsed(request), vtkInformationVector **inputVector, vtkInformationVector *outputVector) { // get the info objects vtkInformation *inInfo = inputVector[0]->GetInformationObject(0); vtkInformation *outInfo = outputVector->GetInformationObject(0); inInfo->Set(vtkStreamingDemandDrivenPipeline::UPDATE_PIECE_NUMBER(), outInfo->Get(vtkStreamingDemandDrivenPipeline::UPDATE_PIECE_NUMBER())); inInfo->Set(vtkStreamingDemandDrivenPipeline::UPDATE_NUMBER_OF_PIECES(), outInfo->Get(vtkStreamingDemandDrivenPipeline::UPDATE_NUMBER_OF_PIECES())); inInfo->Set(vtkStreamingDemandDrivenPipeline::UPDATE_NUMBER_OF_GHOST_LEVELS(), outInfo->Get(vtkStreamingDemandDrivenPipeline::UPDATE_NUMBER_OF_GHOST_LEVELS())); inInfo->Set(vtkStreamingDemandDrivenPipeline::UPDATE_EXTENT(), outInfo->Get(vtkStreamingDemandDrivenPipeline::UPDATE_EXTENT()), 6); inInfo->Set(vtkStreamingDemandDrivenPipeline::EXACT_EXTENT(), outInfo->Get(vtkStreamingDemandDrivenPipeline::EXACT_EXTENT())); return 1; }