You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
259 lines
7.5 KiB
259 lines
7.5 KiB
/*=========================================================================
|
|
|
|
Program: Visualization Toolkit
|
|
Module: $RCSfile: vtkRotationFilter.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 "vtkRotationFilter.h"
|
|
|
|
#include "vtkCellData.h"
|
|
#include "vtkGenericCell.h"
|
|
#include "vtkIdList.h"
|
|
#include "vtkInformation.h"
|
|
#include "vtkInformationVector.h"
|
|
#include "vtkObjectFactory.h"
|
|
#include "vtkPointData.h"
|
|
#include "vtkUnstructuredGrid.h"
|
|
#include "vtkMath.h"
|
|
#include "vtkTransform.h"
|
|
|
|
vtkCxxRevisionMacro(vtkRotationFilter, "$Revision: 1.9 $");
|
|
vtkStandardNewMacro(vtkRotationFilter);
|
|
|
|
//---------------------------------------------------------------------------
|
|
vtkRotationFilter::vtkRotationFilter()
|
|
{
|
|
this->Axis = 2;
|
|
this->CopyInput = 0;
|
|
this->Center[0] = this->Center[1] = this->Center[2] = 0;
|
|
this->NumberOfCopies = 0;
|
|
this->Angle = 0;
|
|
}
|
|
|
|
//---------------------------------------------------------------------------
|
|
vtkRotationFilter::~vtkRotationFilter()
|
|
{
|
|
}
|
|
|
|
//---------------------------------------------------------------------------
|
|
void vtkRotationFilter::PrintSelf(ostream &os, vtkIndent indent)
|
|
{
|
|
this->Superclass::PrintSelf(os, indent);
|
|
|
|
os << indent << "Axis: " << this->Axis << endl;
|
|
os << indent << "CopyInput: " << this->CopyInput << endl;
|
|
os << indent << "Center: (" << this->Center[0] << "," << this->Center[1]
|
|
<< "," << this->Center[2] << ")" << endl;
|
|
os << indent << "NumberOfCopies: " << this->NumberOfCopies << endl;
|
|
os << indent << "Angle: " << this->Angle << endl;
|
|
}
|
|
|
|
//---------------------------------------------------------------------------
|
|
int vtkRotationFilter::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()));
|
|
vtkUnstructuredGrid *output = vtkUnstructuredGrid::SafeDownCast(
|
|
outInfo->Get(vtkDataObject::DATA_OBJECT()));
|
|
|
|
vtkIdType i;
|
|
vtkPointData *inPD = input->GetPointData();
|
|
vtkPointData *outPD = output->GetPointData();
|
|
vtkCellData *inCD = input->GetCellData();
|
|
vtkCellData *outCD = output->GetCellData();
|
|
|
|
if (!this->GetNumberOfCopies())
|
|
{
|
|
vtkErrorMacro("No number of copy set!");
|
|
return 1;
|
|
}
|
|
|
|
double tuple[3];
|
|
vtkPoints *outPoints;
|
|
double point[3], center[3], negativCenter[3];
|
|
int ptId, cellId, j, k;
|
|
vtkGenericCell *cell = vtkGenericCell::New();
|
|
vtkIdList *ptIds = vtkIdList::New();
|
|
|
|
outPoints = vtkPoints::New();
|
|
|
|
vtkIdType numPts = input->GetNumberOfPoints();
|
|
vtkIdType numCells = input->GetNumberOfCells();
|
|
|
|
if (this->CopyInput)
|
|
{
|
|
outPoints->Allocate((this->CopyInput + this->GetNumberOfCopies()) * numPts);
|
|
output->Allocate((this->CopyInput + this->GetNumberOfCopies()) * numPts);
|
|
}
|
|
else
|
|
{
|
|
outPoints->Allocate( this->GetNumberOfCopies() * numPts);
|
|
output->Allocate( this->GetNumberOfCopies() * numPts);
|
|
}
|
|
|
|
outPD->CopyAllocate(inPD);
|
|
outCD->CopyAllocate(inCD);
|
|
|
|
vtkDataArray *inPtVectors, *outPtVectors, *inPtNormals;
|
|
vtkDataArray *inCellVectors, *outCellVectors, *inCellNormals;
|
|
|
|
inPtVectors = inPD->GetVectors();
|
|
outPtVectors = outPD->GetVectors();
|
|
inPtNormals = inPD->GetNormals();
|
|
inCellVectors = inCD->GetVectors();
|
|
outCellVectors = outCD->GetVectors();
|
|
inCellNormals = inCD->GetNormals();
|
|
|
|
// Copy first points.
|
|
if (this->CopyInput)
|
|
{
|
|
for (i = 0; i < numPts; i++)
|
|
{
|
|
input->GetPoint(i, point);
|
|
ptId = outPoints->InsertNextPoint(point);
|
|
outPD->CopyData(inPD, i, ptId);
|
|
}
|
|
}
|
|
vtkTransform *localTransform = vtkTransform::New();
|
|
// Rotate points.
|
|
// double angle = this->GetAngle()*vtkMath::DegreesToRadians();
|
|
this->GetCenter(center);
|
|
negativCenter[0] = -center[0];
|
|
negativCenter[1] = -center[1];
|
|
negativCenter[2] = -center[2];
|
|
|
|
for (k = 0; k < this->GetNumberOfCopies(); k++)
|
|
{
|
|
localTransform->Identity();
|
|
localTransform->Translate(center);
|
|
switch (this->Axis)
|
|
{
|
|
case USE_X:
|
|
localTransform->RotateX((k+1)*this->GetAngle());
|
|
break;
|
|
|
|
case USE_Y:
|
|
localTransform->RotateY((k+1)*this->GetAngle());
|
|
break;
|
|
|
|
case USE_Z:
|
|
localTransform->RotateZ((k+1)*this->GetAngle());
|
|
break;
|
|
}
|
|
localTransform->Translate(negativCenter);
|
|
for (i = 0; i < numPts; i++)
|
|
{
|
|
input->GetPoint(i, point);
|
|
localTransform->TransformPoint(point, point);
|
|
ptId = outPoints->InsertNextPoint(point);
|
|
outPD->CopyData(inPD, i, ptId);
|
|
if (inPtVectors)
|
|
{
|
|
inPtVectors->GetTuple(i, tuple);
|
|
outPtVectors->SetTuple(ptId, tuple);
|
|
}
|
|
if (inPtNormals)
|
|
{
|
|
//inPtNormals->GetTuple(i, tuple);
|
|
//outPtNormals->SetTuple(ptId, tuple);
|
|
}
|
|
}
|
|
}
|
|
|
|
localTransform->Delete();
|
|
|
|
int numCellPts, cellType;
|
|
vtkIdType *newCellPts;
|
|
vtkIdList *cellPts;
|
|
|
|
// Copy original cells.
|
|
if (this->CopyInput)
|
|
{
|
|
for (i = 0; i < numCells; i++)
|
|
{
|
|
input->GetCellPoints(i, ptIds);
|
|
output->InsertNextCell(input->GetCellType(i), ptIds);
|
|
outCD->CopyData(inCD, i, i);
|
|
}
|
|
}
|
|
|
|
// Generate rotated cells.
|
|
for (k = 0; k < this->GetNumberOfCopies(); k++)
|
|
{
|
|
for (i = 0; i < numCells; i++)
|
|
{
|
|
input->GetCellPoints(i, ptIds);
|
|
input->GetCell(i, cell);
|
|
numCellPts = cell->GetNumberOfPoints();
|
|
cellType = cell->GetCellType();
|
|
cellPts = cell->GetPointIds();
|
|
// Triangle strips with even number of triangles have
|
|
// to be handled specially. A degenerate triangle is
|
|
// introduce to flip all the triangles properly.
|
|
if (cellType == VTK_TRIANGLE_STRIP && numCellPts % 2 == 0)
|
|
{
|
|
vtkErrorMacro(<< "Triangles with bad points");
|
|
return 0;
|
|
}
|
|
else
|
|
{
|
|
vtkDebugMacro(<< "celltype " << cellType << " numCellPts " << numCellPts);
|
|
newCellPts = new vtkIdType[numCellPts];
|
|
//for (j = numCellPts-1; j >= 0; j--)
|
|
for (j = 0; j < numCellPts; j++)
|
|
{
|
|
//newCellPts[numCellPts-1-j] = cellPts->GetId(j) + numPts*k;
|
|
newCellPts[j] = cellPts->GetId(j) + numPts*k;
|
|
if (this->CopyInput)
|
|
{
|
|
//newCellPts[numCellPts-1-j] += numPts;
|
|
newCellPts[j] += numPts;
|
|
}
|
|
}
|
|
}
|
|
cellId = output->InsertNextCell(cellType, numCellPts, newCellPts);
|
|
delete [] newCellPts;
|
|
outCD->CopyData(inCD, i, cellId);
|
|
if (inCellVectors)
|
|
{
|
|
inCellVectors->GetTuple(i, tuple);
|
|
outCellVectors->SetTuple(cellId, tuple);
|
|
}
|
|
if (inCellNormals)
|
|
{
|
|
//inCellNormals->GetTuple(i, tuple);
|
|
//outCellNormals->SetTuple(cellId, tuple);
|
|
}
|
|
}
|
|
}
|
|
|
|
cell->Delete();
|
|
ptIds->Delete();
|
|
output->SetPoints(outPoints);
|
|
outPoints->Delete();
|
|
output->CheckAttributes();
|
|
|
|
return 1;
|
|
}
|
|
|
|
int vtkRotationFilter::FillInputPortInformation(int, vtkInformation *info)
|
|
{
|
|
info->Set(vtkAlgorithm::INPUT_REQUIRED_DATA_TYPE(), "vtkDataSet");
|
|
return 1;
|
|
}
|
|
|