/*========================================================================= Program: Visualization Toolkit Module: $RCSfile: vtkRectangularButtonSource.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 "vtkRectangularButtonSource.h" #include "vtkCellArray.h" #include "vtkFloatArray.h" #include "vtkInformation.h" #include "vtkInformationVector.h" #include "vtkMath.h" #include "vtkObjectFactory.h" #include "vtkPointData.h" #include "vtkPoints.h" #include "vtkPolyData.h" #include "vtkTransform.h" vtkCxxRevisionMacro(vtkRectangularButtonSource, "$Revision: 1.3 $"); vtkStandardNewMacro(vtkRectangularButtonSource); // Construct vtkRectangularButtonSource::vtkRectangularButtonSource() { this->Width = 0.5; this->Height = 0.5; this->Depth = 0.05; this->BoxRatio = 1.1; this->TextureRatio = 0.9; this->TextureHeightRatio = 0.95; } // One half of the button is made up of nine (quad) polygons. // static vtkIdType vtkRButtonPolys[72] = { 0,1,5,4, 1,2,6,5, 2,3,7,6, 3,0,4,7, 4,5,9,8, 5,6,10,9, 6,7,11,10, 7,4,8,11, 12,13,14,15, 1,0,16,17, 2,1,17,18, 3,2,18,19, 0,3,19,16, 17,16,20,21, 18,17,21,22, 19,18,22,23, 16,19,23,20, 25,24,27,26}; // Generate the button. // int vtkRectangularButtonSource::RequestData( vtkInformation *vtkNotUsed(request), vtkInformationVector **vtkNotUsed(inputVector), vtkInformationVector *outputVector) { vtkInformation *outInfo = outputVector->GetInformationObject(0); int i; vtkPolyData *output = vtkPolyData::SafeDownCast( outInfo->Get(vtkDataObject::DATA_OBJECT())); vtkDebugMacro(<<"Generating rectangular button"); // Check input if ( this->Width <= 0.0 || this->Height <= 0.0 ) { vtkErrorMacro(<<"Button must have non-zero height and width"); return 1; } // Create the button in several steps. First, create the button in // the x-y plane. After this, the z-depth is created. And if // it is a two-sided button, then a mirror reflection of the button // in the negative z-direction is created. int numPts = 16; int numCells = 9; if ( this->TwoSided ) { numPts *= 2; numCells *= 2; } // Allocate memory for everything vtkPoints *newPts = vtkPoints::New(); newPts->SetNumberOfPoints(numPts); vtkFloatArray *tcoords = vtkFloatArray::New(); tcoords->SetNumberOfComponents(2); tcoords->SetNumberOfTuples(numPts); vtkCellArray *newPolys = vtkCellArray::New(); newPolys->Allocate(numCells); // Generate the points and texture coordinates----------------------------- // double shoulderX = this->Width / 2.0; double boxX = this->BoxRatio * shoulderX; double textureX = this->TextureRatio * shoulderX; //may be adjusted later double shoulderY = this->Height / 2.0; double boxY = this->BoxRatio * shoulderY; double textureY = this->TextureRatio * shoulderY; //may be adjusted later double shoulderZ = this->Depth; double boxZ = 0.0; double textureZ = this->TextureHeightRatio * this->Depth; // Adjust the texture region if the texture region should be fit to the image if ( this->TextureStyle == VTK_TEXTURE_STYLE_FIT_IMAGE ) { double dX = (double)this->TextureDimensions[0]; double dY = (double)this->TextureDimensions[1]; double f1 = textureX/dX; double f2 = textureY/dY; if ( f1 < f2 ) { textureX = f1 * dX; textureY = f1 * dY; } else { textureX = f2 * dX; textureY = f2 * dY; } } // The first four points are around the base newPts->SetPoint(0, this->Center[0]-boxX, this->Center[1]-boxY, this->Center[2]+boxZ); newPts->SetPoint(1, this->Center[0]+boxX, this->Center[1]-boxY, this->Center[2]+boxZ); newPts->SetPoint(2, this->Center[0]+boxX, this->Center[1]+boxY, this->Center[2]+boxZ); newPts->SetPoint(3, this->Center[0]-boxX, this->Center[1]+boxY, this->Center[2]+boxZ); // The next four points are around the shoulder newPts->SetPoint(4, this->Center[0]-shoulderX, this->Center[1]-shoulderY, this->Center[2]+shoulderZ); newPts->SetPoint(5, this->Center[0]+shoulderX, this->Center[1]-shoulderY, this->Center[2]+shoulderZ); newPts->SetPoint(6, this->Center[0]+shoulderX, this->Center[1]+shoulderY, this->Center[2]+shoulderZ); newPts->SetPoint(7, this->Center[0]-shoulderX, this->Center[1]+shoulderY, this->Center[2]+shoulderZ); // The next four points are between the shoulder and texture region newPts->SetPoint(8, this->Center[0]-textureX, this->Center[1]-textureY, this->Center[2]+textureZ); newPts->SetPoint(9, this->Center[0]+textureX, this->Center[1]-textureY, this->Center[2]+textureZ); newPts->SetPoint(10,this->Center[0]+textureX, this->Center[1]+textureY, this->Center[2]+textureZ); newPts->SetPoint(11,this->Center[0]-textureX, this->Center[1]+textureY, this->Center[2]+textureZ); // The last four points define the texture region newPts->SetPoint(12, this->Center[0]-textureX, this->Center[1]-textureY, this->Center[2]+textureZ); newPts->SetPoint(13, this->Center[0]+textureX, this->Center[1]-textureY, this->Center[2]+textureZ); newPts->SetPoint(14, this->Center[0]+textureX, this->Center[1]+textureY, this->Center[2]+textureZ); newPts->SetPoint(15, this->Center[0]-textureX, this->Center[1]+textureY, this->Center[2]+textureZ); if ( this->TwoSided ) { // The next four points are around the shoulder newPts->SetPoint(16, this->Center[0]-shoulderX, this->Center[1]-shoulderY, this->Center[2]-shoulderZ); newPts->SetPoint(17, this->Center[0]+shoulderX, this->Center[1]-shoulderY, this->Center[2]-shoulderZ); newPts->SetPoint(18, this->Center[0]+shoulderX, this->Center[1]+shoulderY, this->Center[2]-shoulderZ); newPts->SetPoint(19, this->Center[0]-shoulderX, this->Center[1]+shoulderY, this->Center[2]-shoulderZ); // The next four points are between the shoulder and texture region newPts->SetPoint(20, this->Center[0]-textureX, this->Center[1]-textureY, this->Center[2]-textureZ); newPts->SetPoint(21, this->Center[0]+textureX, this->Center[1]-textureY, this->Center[2]-textureZ); newPts->SetPoint(22,this->Center[0]+textureX, this->Center[1]+textureY, this->Center[2]-textureZ); newPts->SetPoint(23,this->Center[0]-textureX, this->Center[1]+textureY, this->Center[2]-textureZ); // The last four points define the texture region newPts->SetPoint(24, this->Center[0]-textureX, this->Center[1]-textureY, this->Center[2]-textureZ); newPts->SetPoint(25, this->Center[0]+textureX, this->Center[1]-textureY, this->Center[2]-textureZ); newPts->SetPoint(26, this->Center[0]+textureX, this->Center[1]+textureY, this->Center[2]-textureZ); newPts->SetPoint(27, this->Center[0]-textureX, this->Center[1]+textureY, this->Center[2]-textureZ); } // Generate the texture coordinates----------------------------- // // The shoulder has the same value. for (i=0; i<12; i++) { tcoords->SetTuple(i,this->ShoulderTextureCoordinate); } // The texture region has just the four points tcoords->SetTuple2(12,0.0, 0.0); tcoords->SetTuple2(13,1.0, 0.0); tcoords->SetTuple2(14,1.0, 1.0); tcoords->SetTuple2(15,0.0, 1.0); if ( this->TwoSided ) { for (i=16; i<24; i++) { tcoords->SetTuple(i,this->ShoulderTextureCoordinate); } // The texture region has just the four points tcoords->SetTuple2(24,1.0, 0.0); tcoords->SetTuple2(25,0.0, 0.0); tcoords->SetTuple2(26,0.0, 1.0); tcoords->SetTuple2(27,1.0, 1.0); } // Create the polygons------------------------------------------------------ // vtkIdType *buttonPtr = vtkRButtonPolys; for (i=0; i<9; i++, buttonPtr+=4) { newPolys->InsertNextCell(4,buttonPtr); } // If two sided, create the opposite side. // Make sure that faces ordering is reversed. if ( this->TwoSided ) { for (i=0; i<9; i++, buttonPtr+=4) { newPolys->InsertNextCell(4,buttonPtr); } } // Clean up and get out output->SetPoints(newPts); output->GetPointData()->SetTCoords(tcoords); output->SetPolys(newPolys); newPts->Delete(); tcoords->Delete(); newPolys->Delete(); return 1; } void vtkRectangularButtonSource::PrintSelf(ostream& os, vtkIndent indent) { this->Superclass::PrintSelf(os,indent); os << indent << "Width: " << this->Width << "\n"; os << indent << "Height: " << this->Height << "\n"; os << indent << "Depth: " << this->Depth << "\n"; os << indent << "BoxRatio: " << this->BoxRatio << "\n"; os << indent << "TextureRatio: " << this->TextureRatio << "\n"; os << indent << "TextureHeightRatio: " << this->TextureHeightRatio << "\n"; }