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.
525 lines
17 KiB
525 lines
17 KiB
/*=========================================================================
|
|
|
|
Program: Visualization Toolkit
|
|
Module: $RCSfile: vtkGenericAttributeCollection.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 "vtkGenericAttributeCollection.h"
|
|
|
|
#include "vtkObjectFactory.h"
|
|
#include "vtkGenericAttribute.h"
|
|
|
|
|
|
#include <vtkstd/vector>
|
|
#include <assert.h>
|
|
|
|
vtkCxxRevisionMacro(vtkGenericAttributeCollection,"$Revision: 1.9 $");
|
|
vtkStandardNewMacro(vtkGenericAttributeCollection);
|
|
|
|
class vtkGenericAttributeInternalVector
|
|
{
|
|
public:
|
|
typedef vtkstd::vector<vtkGenericAttribute* > VectorType;
|
|
VectorType Vector;
|
|
};
|
|
|
|
class vtkIntInternalVector
|
|
{
|
|
public:
|
|
typedef vtkstd::vector<int> VectorType;
|
|
VectorType Vector;
|
|
};
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Default constructor: empty collection
|
|
vtkGenericAttributeCollection::vtkGenericAttributeCollection()
|
|
{
|
|
this->AttributeInternalVector = new vtkGenericAttributeInternalVector;
|
|
this->AttributeIndices = new vtkIntInternalVector;
|
|
this->ActiveAttribute = 0;
|
|
this->ActiveComponent = 0;
|
|
this->NumberOfAttributesToInterpolate = 0;
|
|
this->NumberOfComponents = 0;
|
|
this->NumberOfPointCenteredComponents = 0;
|
|
this->MaxNumberOfComponents = 0; // cache
|
|
this->ActualMemorySize = 0;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
vtkGenericAttributeCollection::~vtkGenericAttributeCollection()
|
|
{
|
|
for(unsigned int i=0; i < this->AttributeInternalVector->Vector.size(); ++i)
|
|
{
|
|
this->AttributeInternalVector->Vector[i]->Delete();
|
|
}
|
|
delete this->AttributeInternalVector;
|
|
delete this->AttributeIndices;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
void vtkGenericAttributeCollection::PrintSelf(ostream& os, vtkIndent indent)
|
|
{
|
|
this->Superclass::PrintSelf(os,indent);
|
|
|
|
int i;
|
|
int c = this->GetNumberOfAttributes();
|
|
|
|
os << indent << "Number Of Attributes: " << this->GetNumberOfAttributes() << "\n";
|
|
for(i=0; i<c; ++i)
|
|
{
|
|
os << indent << "Attribute #"<<i<<":\n";
|
|
this->GetAttribute(i)->PrintSelf(os,indent.GetNextIndent());
|
|
}
|
|
|
|
c=this->GetNumberOfAttributesToInterpolate();
|
|
os << indent << "Number Of Attributes to interpolate: " << c << endl;
|
|
|
|
os << indent << "Attributes to interpolate:";
|
|
|
|
for(i=0; i<c; ++i)
|
|
{
|
|
os << ' ' << this->AttributesToInterpolate[i];
|
|
}
|
|
os << endl;
|
|
|
|
os << indent << "Active Attribute: " << this->ActiveAttribute << endl;
|
|
|
|
os << indent << "Active Component" << this->ActiveComponent << endl;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Number of attributes.
|
|
int vtkGenericAttributeCollection::GetNumberOfAttributes()
|
|
{
|
|
int result = this->AttributeInternalVector->Vector.size();
|
|
//assert("post: positive_result" && result>=0); size() is an unsigned type according to STL vector definition
|
|
return result;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
int vtkGenericAttributeCollection::GetNumberOfComponents()
|
|
{
|
|
this->ComputeNumbers();
|
|
|
|
return this->NumberOfComponents;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Return the number of components. This is the sum of all components
|
|
// found in all point centered attributes.
|
|
// \post positive_result: result>=0
|
|
int vtkGenericAttributeCollection::GetNumberOfPointCenteredComponents()
|
|
{
|
|
this->ComputeNumbers();
|
|
|
|
return this->NumberOfPointCenteredComponents;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Maximum number of components encountered among all attributes.
|
|
// \post positive_result: result>=0
|
|
// \post valid_result: result<=GetNumberOfComponents()
|
|
int vtkGenericAttributeCollection::GetMaxNumberOfComponents()
|
|
{
|
|
this->ComputeNumbers();
|
|
|
|
assert("post: positive_result" && this->MaxNumberOfComponents>=0);
|
|
assert("post: valid_result" && this->MaxNumberOfComponents<=GetNumberOfComponents());
|
|
return this->MaxNumberOfComponents;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Actual size of the data in kilobytes; only valid after the pipeline has
|
|
// updated. It is guaranteed to be greater than or equal to the memory
|
|
// required to represent the data.
|
|
unsigned long vtkGenericAttributeCollection::GetActualMemorySize()
|
|
{
|
|
this->ComputeNumbers();
|
|
return this->ActualMemorySize;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Does `this' have no attribute?
|
|
int vtkGenericAttributeCollection::IsEmpty()
|
|
{
|
|
return this->GetNumberOfAttributes()==0;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Attribute `i'.
|
|
vtkGenericAttribute *vtkGenericAttributeCollection::GetAttribute(int i)
|
|
{
|
|
assert("pre: not_empty" && !IsEmpty());
|
|
assert("pre: valid_i" && (i>=0)&&(i<this->GetNumberOfAttributes()));
|
|
vtkGenericAttribute *result=this->AttributeInternalVector->Vector[i];
|
|
assert("post: result_exists" && result!=0);
|
|
return result;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Return the index of attribute `name', if found. Return -1 otherwise.
|
|
int vtkGenericAttributeCollection::FindAttribute(const char *name)
|
|
{
|
|
assert("pre: name_exists:" && name!=0);
|
|
|
|
int result=-1;
|
|
|
|
const char *attributeName;
|
|
int numAtt = this->GetNumberOfAttributes();
|
|
int i=0;
|
|
|
|
while((i<numAtt)&&(result==-1))
|
|
{
|
|
attributeName=this->GetAttribute(i)->GetName();
|
|
if(attributeName!=0)
|
|
{
|
|
if(strcmp( attributeName, name ) == 0)
|
|
{
|
|
result=i;
|
|
}
|
|
}
|
|
++i;
|
|
}
|
|
|
|
assert("post: valid_result" && ((result==-1) ||
|
|
((result>=0) &&
|
|
(result<=this->GetNumberOfAttributes()))));
|
|
|
|
return result;
|
|
}
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Return the index of the first component of attribute `i' in an array of
|
|
// format attrib0comp0 attrib0comp1 ... attrib4comp0 ...
|
|
// \pre valid_i: i>=0 && i<GetNumberOfAttributes()
|
|
// \pre is_point_centered: GetAttribute(i)->GetCentering()==vtkPointCentered
|
|
int vtkGenericAttributeCollection::GetAttributeIndex(int i)
|
|
{
|
|
assert("pre: valid_i" && i>=0 && i<this->GetNumberOfAttributes());
|
|
assert("pre: is_point_centered" && this->GetAttribute(i)->GetCentering()==vtkPointCentered);
|
|
this->ComputeNumbers();
|
|
return this->AttributeIndices->Vector[i];
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Add attribute `a' at the end.
|
|
void vtkGenericAttributeCollection::InsertNextAttribute(vtkGenericAttribute *a)
|
|
{
|
|
assert("pre: a_exists" && a!=0);
|
|
#ifndef NDEBUG
|
|
int oldnumber=this->GetNumberOfAttributes();
|
|
#endif
|
|
|
|
this->AttributeInternalVector->Vector.push_back(a);
|
|
this->AttributeIndices->Vector.push_back(0); // a dummy default value
|
|
a->Register( this );
|
|
this->Modified();
|
|
|
|
assert("post: more_items" && this->GetNumberOfAttributes()==oldnumber+1);
|
|
assert("post: a_is_set" && this->GetAttribute(this->GetNumberOfAttributes()-1)==a);
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Replace attribute at index `i' by `a'.
|
|
void vtkGenericAttributeCollection::InsertAttribute(int i, vtkGenericAttribute *a)
|
|
{
|
|
assert("pre: not_empty" && !this->IsEmpty());
|
|
assert("pre: a_exists" && a!=0);
|
|
assert("pre: valid_i" && (i>=0)&&(i<this->GetNumberOfAttributes()));
|
|
|
|
#ifndef NDEBUG
|
|
int oldnumber = this->GetNumberOfAttributes();
|
|
#endif
|
|
|
|
if(this->AttributeInternalVector->Vector[i]!=0)
|
|
{
|
|
this->AttributeInternalVector->Vector[i]->Delete();
|
|
}
|
|
this->AttributeInternalVector->Vector[i] = a;
|
|
a->Register( this );
|
|
this->Modified();
|
|
|
|
assert("post: more_items" && this->GetNumberOfAttributes()==oldnumber);
|
|
assert("post: a_is_set" && this->GetAttribute(i)==a);
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Remove Attribute at `i'.
|
|
void vtkGenericAttributeCollection::RemoveAttribute(int i)
|
|
{
|
|
assert("pre: not_empty" && !this->IsEmpty());
|
|
assert("pre: valid_i" && (i>=0)&&(i<this->GetNumberOfAttributes()));
|
|
|
|
#ifndef NDEBUG
|
|
int oldnumber=this->GetNumberOfAttributes();
|
|
#endif
|
|
|
|
this->AttributeInternalVector->Vector[i]->UnRegister( this );
|
|
this->AttributeInternalVector->Vector.erase(
|
|
this->AttributeInternalVector->Vector.begin()+i);
|
|
|
|
this->AttributeIndices->Vector.erase(
|
|
this->AttributeIndices->Vector.begin()+i);
|
|
|
|
this->Modified();
|
|
|
|
assert("post: fewer_items" && this->GetNumberOfAttributes()==(oldnumber-1));
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Remove all attributes.
|
|
void vtkGenericAttributeCollection::Reset()
|
|
{
|
|
for(unsigned int i = 0; i < this->AttributeInternalVector->Vector.size(); ++i)
|
|
{
|
|
this->AttributeInternalVector->Vector[i]->Delete();
|
|
}
|
|
this->AttributeInternalVector->Vector.clear();
|
|
this->AttributeIndices->Vector.clear();
|
|
this->Modified();
|
|
|
|
assert("post: is_empty" && this->IsEmpty());
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Recursive duplication of `other' in `this'.
|
|
void vtkGenericAttributeCollection::DeepCopy(vtkGenericAttributeCollection *other)
|
|
{
|
|
assert("pre: other_exists" && other!=0);
|
|
assert("pre: not_self" && other!=this);
|
|
|
|
this->AttributeInternalVector->Vector.resize(
|
|
other->AttributeInternalVector->Vector.size());
|
|
|
|
this->AttributeIndices->Vector.resize(
|
|
other->AttributeIndices->Vector.size());
|
|
|
|
int c = this->AttributeInternalVector->Vector.size();
|
|
for(int i=0; i<c; i++)
|
|
{
|
|
if(this->AttributeInternalVector->Vector[i] == 0)
|
|
{
|
|
this->AttributeInternalVector->Vector[i] =
|
|
other->AttributeInternalVector->Vector[i]->NewInstance();
|
|
}
|
|
this->AttributeInternalVector->Vector[i]->DeepCopy(
|
|
other->AttributeInternalVector->Vector[i]);
|
|
// Dont need to copy the contents of AttributeIndices: it will be
|
|
// recomputed because of the following Moditied call.
|
|
}
|
|
this->Modified();
|
|
|
|
assert("post: same_size" && this->GetNumberOfAttributes()==other->GetNumberOfAttributes());
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Update `this' using fields of `other'.
|
|
void vtkGenericAttributeCollection::ShallowCopy(vtkGenericAttributeCollection *other)
|
|
{
|
|
assert("pre: other_exists" && other!=0);
|
|
assert("pre: not_self" && other!=this);
|
|
|
|
this->AttributeInternalVector->Vector =
|
|
other->AttributeInternalVector->Vector;
|
|
this->AttributeIndices->Vector = other->AttributeIndices->Vector;
|
|
int c = this->AttributeInternalVector->Vector.size();
|
|
for (int i=0; i<c; ++i)
|
|
{
|
|
if (this->AttributeInternalVector->Vector[i] != 0)
|
|
{
|
|
this->AttributeInternalVector->Vector[i]->Register( this );
|
|
}
|
|
}
|
|
this->Modified();
|
|
|
|
assert("post: same_size" && this->GetNumberOfAttributes()==other->GetNumberOfAttributes());
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Collection is composite object and need to check each part for MTime.
|
|
unsigned long int vtkGenericAttributeCollection::GetMTime()
|
|
{
|
|
unsigned long result;
|
|
unsigned long mtime;
|
|
|
|
result = vtkObject::GetMTime();
|
|
|
|
for(int i = 0; i < this->GetNumberOfAttributes(); ++i)
|
|
{
|
|
mtime = this->GetAttribute(i)->GetMTime();
|
|
result = ( mtime > result ? mtime : result );
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Compute number of components, max number of components and actual memory
|
|
// size.
|
|
void vtkGenericAttributeCollection::ComputeNumbers()
|
|
{
|
|
if ( this->GetMTime() > this->ComputeTime )
|
|
{
|
|
int nb = 0;
|
|
int pnb = 0;
|
|
int count;
|
|
int maxNb = 0;
|
|
unsigned long memory=0;
|
|
int firstComponentIndex=0;
|
|
|
|
int c = this->GetNumberOfAttributes();
|
|
|
|
for(int i = 0; i < c; ++i)
|
|
{
|
|
count = this->GetAttribute(i)->GetNumberOfComponents();
|
|
memory=memory+this->GetAttribute(i)->GetActualMemorySize();
|
|
if(count > maxNb)
|
|
{
|
|
maxNb = count;
|
|
}
|
|
nb += count;
|
|
if(this->GetAttribute(i)->GetCentering()==vtkPointCentered)
|
|
{
|
|
pnb += count;
|
|
this->AttributeIndices->Vector[i]=firstComponentIndex;
|
|
firstComponentIndex=firstComponentIndex+count;
|
|
}
|
|
}
|
|
this->NumberOfComponents = nb;
|
|
this->NumberOfPointCenteredComponents = pnb;
|
|
this->MaxNumberOfComponents = maxNb;
|
|
this->ActualMemorySize = memory;
|
|
|
|
assert("check: positive_number" && this->NumberOfComponents>=0);
|
|
assert("check: positive_point_centered_number" && this->NumberOfPointCenteredComponents>=0);
|
|
assert("check: positiveMaxNumber" && this->MaxNumberOfComponents>=0);
|
|
assert("check: valid_number" && this->MaxNumberOfComponents<=this->NumberOfComponents);
|
|
this->ComputeTime.Modified();
|
|
}
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// *** ALL THE FOLLOWING METHODS SHOULD BE REMOVED WHEN vtkInformation
|
|
// will be ready.
|
|
// *** BEGIN
|
|
|
|
// Description:
|
|
// Set the scalar attribute to be processed. -1 means module.
|
|
void vtkGenericAttributeCollection::SetActiveAttribute(int attribute,
|
|
int component)
|
|
{
|
|
assert("pre: not_empty" && !IsEmpty());
|
|
assert("pre: valid_attribute" && (attribute>=0)&&(attribute<this->GetNumberOfAttributes()));
|
|
assert("pre: valid_component" && (component>=-1)&&(component<this->GetAttribute(attribute)->GetNumberOfComponents()));
|
|
|
|
this->ActiveAttribute = attribute;
|
|
this->ActiveComponent = component;
|
|
|
|
assert("post: is_set" && (this->GetActiveAttribute()==attribute) && (this->GetActiveComponent()==component));
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Indices of attributes to interpolate.
|
|
// \pre not_empty: !IsEmpty()
|
|
// \post valid_result: GetNumberOfAttributesToInterpolate()>0 implies
|
|
// result!=0
|
|
int *vtkGenericAttributeCollection::GetAttributesToInterpolate()
|
|
{
|
|
assert("pre: not_empty" && !IsEmpty());
|
|
|
|
assert("post: valid_result" && ((!(this->NumberOfAttributesToInterpolate>0))
|
|
|| this->AttributesToInterpolate!=0));
|
|
// A=>B !A||B
|
|
|
|
return this->AttributesToInterpolate;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description
|
|
// Does the array `attributes' of size `size' have `attribute'?
|
|
int vtkGenericAttributeCollection::HasAttribute(int size,
|
|
int *attributes,
|
|
int attribute)
|
|
{
|
|
assert("pre: positive_size" && size>=0);
|
|
assert("pre: valid_attributes" && ((!(size>0))||(attributes!=0))); // size>0 => attributes!=0 (A=>B: !A||B )
|
|
|
|
int result = 0; // false
|
|
int i;
|
|
|
|
if(size != 0)
|
|
{
|
|
i = 0;
|
|
while( !result && i++ < size )
|
|
{
|
|
result = attributes[i] == attribute;
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Set the attributes to interpolate.
|
|
void vtkGenericAttributeCollection::SetAttributesToInterpolate(int size,
|
|
int *attributes)
|
|
{
|
|
assert("pre: not_empty" && !this->IsEmpty());
|
|
assert("pre: positive_size" && size>=0);
|
|
assert("pre: magic_number" && size<=10);
|
|
assert("pre: valid_attributes" && ((!(size>0))||(attributes!=0))); // size>0 => attributes!=0 (A=>B: !A||B )
|
|
assert("pre: valid_attributes_contents" && (!(attributes!=0) || !(!this->HasAttribute(size,attributes,this->GetActiveAttribute())))); // attributes!=0 => !this->HasAttribute(size,attributes,this->GetActiveAttribute()) (A=>B: !A||B )
|
|
|
|
this->NumberOfAttributesToInterpolate = size;
|
|
for(int i=0; i<size; ++i)
|
|
{
|
|
this->AttributesToInterpolate[i] = attributes[i];
|
|
}
|
|
|
|
assert("post: is_set" && (this->GetNumberOfAttributesToInterpolate()==size));
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// Description:
|
|
// Set the attributes to interpolate.
|
|
void vtkGenericAttributeCollection::SetAttributesToInterpolateToAll()
|
|
{
|
|
assert("pre: not_empty" && !this->IsEmpty());
|
|
|
|
this->NumberOfAttributesToInterpolate = this->GetMaxNumberOfComponents();
|
|
for(int i=0; i<this->NumberOfAttributesToInterpolate; ++i)
|
|
{
|
|
this->AttributesToInterpolate[i] = i;
|
|
}
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
// *** ALL THE PREVIOUS METHODS SHOULD BE REMOVED WHEN vtkInformation
|
|
// will be ready.
|
|
// *** END
|
|
|