00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
#ifndef VTK_UNIQUE_COLLECTION_H_
00017
# define VTK_UNIQUE_COLLECTION_H_
00018
# include "vtkExtensionsCommonConfigure.h"
00019
00020
# include "vtkCollection.h"
00021
00022
VTK_EXTENSIONS_NAMESPACE_BEGIN
00023
00041 class VTK_EXTENSIONS_COMMON_EXPORT vtkUniqueCollection
00042 :
public vtkCollection
00043 {
00044
public:
00045
static vtkUniqueCollection*
New (
void);
00046 vtkTypeRevisionMacro (vtkUniqueCollection,
vtkCollection);
00047
void PrintSelf (ostream&,
vtkIndent);
00048
00051 vtkSetMacro (CheckUnique,
int);
00052 vtkGetMacro (CheckUnique,
int);
00053 vtkBooleanMacro (CheckUnique,
int);
00057
void AddItem (
vtkObject* item);
00058
00065
00066
void ReplaceItem (
int i,
vtkObject* item,
vtkObject** ret);
00067
00068 void ReplaceItem (
int i,
vtkObject* item)
00069 { this->ReplaceItem(i, item, NULL); }
00082
00083
void RemoveItem (
int i,
vtkObject** ret);
00084
00085 void RemoveItem (
int i)
00086 { this->RemoveItem(i, NULL); }
00099
00100
void RemoveItem (
vtkObject* item,
vtkObject** ret);
00101
00102 void RemoveItem (
vtkObject* item)
00103 { this->RemoveItem(item, NULL); }
00107
int IndexOf (
vtkObject* item);
00108
00114
vtkObject* GetNextItem (
void);
00115
00121
vtkObject* GetItem (
int i);
00122
00124
vtkObject* GetFirstItem (
void);
00125
00127
vtkObject* GetLastItem (
void);
00128
00135
00136
void RemoveLastItem (
vtkObject** removed);
00137
00138 void RemoveLastItem (
void)
00139 { this->RemoveLastItem(NULL); }
00143
int PrependItem (
vtkObject* item);
00144
00146
int AppendItem (
vtkObject* item);
00147
00149
int InsertItemAt (
vtkObject* item,
int i);
00150
00152
int GetNumberOfItemsByType (
const char* type);
00153
00155
vtkObject* InitTraversalByType (
const char* type);
00156
00158
vtkObject* GetNthItemByType (
int n,
const char* type);
00159
00161
vtkObject* GetNextItemByType (
const char* type);
00162
00164
virtual unsigned long GetMTime (
void);
00165
00166
protected:
00167 vtkUniqueCollection (
void) : CheckUnique(1) {}
00168 ~vtkUniqueCollection() {}
00169
00170 int CheckUnique;
00171
00178
vtkCollectionElement* FindCollectionElementAt (
int i);
00179
00180
private:
00186 vtkUniqueCollection (
const vtkUniqueCollection&);
00187
void operator= (
const vtkUniqueCollection&);
00189 };
00190
00191
00192
inline void
00193 vtkUniqueCollection::AddItem (
vtkObject* aItem)
00194 {
00195
if (!this->
CheckUnique || !this->IsItemPresent(aItem))
00196 {
00197 this->vtkCollection::AddItem(aItem);
00198 }
00199 }
00200
00201
00202
inline void
00203 vtkUniqueCollection::ReplaceItem (
int aIndex,
00204
vtkObject* aNewItem,
00205
vtkObject** aReturn)
00206 {
00207
vtkObject* oldItem = this->GetItemAsObject(aIndex);
00208
vtkObject* newItem = aNewItem;
00209
00210
if (oldItem == NULL || oldItem == aNewItem)
00211 {
00212
return;
00213 }
00214
00215
if (aReturn != NULL)
00216 {
00217
00218 *aReturn = oldItem;
00219 (*aReturn)->
Register(
this);
00220 }
00221
00222
int existingLocation = this->IsItemPresent(aNewItem);
00223
00224 this->vtkCollection::ReplaceItem(aIndex, aNewItem);
00225
00226
if (this->
CheckUnique && existingLocation != 0)
00227 {
00228 this->vtkCollection::RemoveItem(existingLocation - 1);
00229 }
00230 }
00231
00232
00233
inline void
00234 vtkUniqueCollection::RemoveItem (
int aIndex,
vtkObject** aReturn)
00235 {
00236
vtkObject* item;
00237
00238
if (aReturn != NULL && (item = this->
GetItem(aIndex)) != NULL)
00239 {
00240
00241 *aReturn = item;
00242 (*aReturn)->
Register(
this);
00243 }
00244
00245 this->vtkCollection::RemoveItem(aIndex);
00246 }
00247
00248
00249
inline void
00250 vtkUniqueCollection::RemoveItem (
vtkObject* aItem,
vtkObject** aReturn)
00251 {
00252
if (aReturn != NULL && this->IsItemPresent(aItem))
00253 {
00254
00255 *aReturn = aItem;
00256 (*aReturn)->
Register(
this);
00257 }
00258
00259 this->vtkCollection::RemoveItem(aItem);
00260 }
00261
00262
00263
inline int
00264 vtkUniqueCollection::IndexOf (
vtkObject* aItem)
00265 {
return this->IsItemPresent(aItem) - 1; }
00266
00267
00268
inline vtkObject*
00269 vtkUniqueCollection::GetNextItem (
void)
00270 {
return this->
GetNextItemAsObject(); }
00271
00272
00273
inline vtkObject*
00274 vtkUniqueCollection::GetItem (
int aIndex)
00275 {
return this->GetItemAsObject(aIndex); }
00276
00277
00278
inline vtkObject*
00279 vtkUniqueCollection::GetFirstItem (
void)
00280 {
return (this->Top != NULL ? this->Top->
Item : NULL); }
00281
00282
00283
inline vtkObject*
00284 vtkUniqueCollection::GetLastItem (
void)
00285 {
return (this->Bottom != NULL ? this->Bottom->
Item : NULL); }
00286
00287
00288
inline void
00289 vtkUniqueCollection::RemoveLastItem (
vtkObject** aReturn)
00290 { this->
RemoveItem(this->GetLastItem(), aReturn); }
00291
00292
00293
inline int
00294 vtkUniqueCollection::PrependItem (
vtkObject* aItem)
00295 {
00296
if (aItem == NULL)
00297 {
00298 vtkErrorMacro(<<
"PrependItem() called with NULL node pointer.");
00299
return VTK_ERROR;
00300 }
00301
00302
int index = this->
IndexOf(aItem);
00303
00304
if (index == 0)
00305 {
00306
return VTK_OK;
00307 }
00308
else if (index > 0)
00309 {
00310 this->
RemoveItem(index, &aItem);
00311 }
00312
00313
vtkCollectionElement* newElem;
00314
00315
try
00316 {
00317 newElem =
new vtkCollectionElement;
00318 }
00319
catch (...)
00320 {
00321
delete newElem;
00322
return VTK_ERROR;
00323 }
00324
00325 newElem->
Item = aItem;
00326
00327
if (index < 0)
00328 {
00329 newElem->
Item->
Register(
this);
00330 }
00331
00332 newElem->
Next = this->Top;
00333 this->Top = newElem;
00334
00335
if (this->Bottom == NULL)
00336 {
00337 this->Bottom = this->Top;
00338 }
00339
00340 this->NumberOfItems++;
00341 this->
Modified();
00342
00343
return VTK_OK;
00344 }
00345
00346
00347
inline int
00348 vtkUniqueCollection::AppendItem (
vtkObject* aItem)
00349 {
00350
if (aItem == NULL)
00351 {
00352 vtkErrorMacro(<<
"AppendItem() called with NULL node pointer.");
00353
return VTK_ERROR;
00354 }
00355
00356
if (this->Bottom == NULL)
00357 {
00358
return this->
PrependItem(aItem);
00359 }
00360
00361
int index = this->
IndexOf(aItem);
00362
00363
if (index == (this->NumberOfItems - 1))
00364 {
00365
return VTK_OK;
00366 }
00367
else if (index >= 0)
00368 {
00369 this->
RemoveItem(index, &aItem);
00370 }
00371
00372
vtkCollectionElement* newElem;
00373
00374
try
00375 {
00376 newElem =
new vtkCollectionElement;
00377 }
00378
catch (...)
00379 {
00380
delete newElem;
00381
return VTK_ERROR;
00382 }
00383
00384 newElem->
Item = aItem;
00385
00386
if (index < 0)
00387 {
00388 newElem->
Item->
Register(
this);
00389 }
00390
00391 this->Bottom->
Next = newElem;
00392 this->Bottom = newElem;
00393
00394 this->NumberOfItems++;
00395 this->
Modified();
00396
00397
return VTK_OK;
00398 }
00399
00400
00401
inline vtkCollectionElement*
00402 vtkUniqueCollection::FindCollectionElementAt (
int aIndex)
00403 {
00404
int i = 0;
00405
00406
for (
vtkCollectionElement* elem = this->Top; elem != NULL; elem = elem->
Next)
00407 {
00408
if (i == aIndex)
00409 {
00410
return elem;
00411 }
00412 i++;
00413 }
00414
00415
return NULL;
00416 }
00417
00418
00419
inline int
00420 vtkUniqueCollection::InsertItemAt (
vtkObject* aItem,
int aIndex)
00421 {
00422
if (aItem == NULL)
00423 {
00424 vtkWarningMacro(<<
"InsertItemAt() called with NULL node pointer.");
00425
return VTK_ERROR;
00426 }
00427
00428
if (aIndex < 0 || aIndex > this->NumberOfItems)
00429 {
00430 vtkWarningMacro(<<
"InsertItemAt() called with invalid index.");
00431
return VTK_ERROR;
00432 }
00433
00434
if (aIndex == 0)
00435 {
00436
return this->
PrependItem(aItem);
00437 }
00438
else if (aIndex == this->NumberOfItems)
00439 {
00440
return this->
AppendItem(aItem);
00441 }
00442
00443
int index = this->
IndexOf(aItem);
00444
00445
if (index == aIndex)
00446 {
00447
return VTK_OK;
00448 }
00449
else if (index >= 0)
00450 {
00451 this->
RemoveItem(index, &aItem);
00452 }
00453
00454
vtkCollectionElement* currElem;
00455
00456
if ((currElem = this->
FindCollectionElementAt(aIndex-1)) != NULL)
00457 {
00458
vtkCollectionElement* newElem;
00459
00460
try
00461 {
00462 newElem =
new vtkCollectionElement;
00463 }
00464
catch (...)
00465 {
00466
delete newElem;
00467
return VTK_ERROR;
00468 }
00469
00470 newElem->
Next = currElem->
Next;
00471 newElem->
Item = aItem;
00472
00473
if (index < 0)
00474 {
00475 newElem->
Item->
Register(
this);
00476 }
00477
00478 currElem->
Next = newElem;
00479
00480 this->NumberOfItems++;
00481 this->
Modified();
00482
00483
return VTK_OK;
00484 }
00485
00486
return VTK_ERROR;
00487 }
00488
00489
00490
inline int
00491 vtkUniqueCollection::GetNumberOfItemsByType (
const char* aType)
00492 {
00493
vtkCollectionElement* elem = this->Top;
00494
int num = 0;
00495
00496
while (elem != NULL)
00497 {
00498
if (elem->
Item->
IsA(aType)) num++;
00499 elem = elem->
Next;
00500 }
00501
00502
return num;
00503 }
00504
00505
inline vtkObject*
00506 vtkUniqueCollection::GetNextItemByType (
const char* aType)
00507 {
00508
vtkCollectionElement* elem = this->Current;
00509
00510
if (elem != NULL) elem = elem->
Next;
00511
00512
while (elem != NULL && !elem->
Item->
IsA(aType)) elem = elem->
Next;
00513
00514
if (elem != NULL)
00515 {
00516 this->Current = elem;
00517
return this->Current->
Item;
00518 }
00519
00520
return NULL;
00521 }
00522
00523
inline vtkObject*
00524 vtkUniqueCollection::InitTraversalByType (
const char* aType)
00525 {
00526
vtkCollectionElement* elem = this->Top;
00527
00528
while (elem != NULL && !elem->
Item->
IsA(aType)) elem = elem->
Next;
00529
00530
if (elem != NULL)
00531 {
00532 this->Current = elem;
00533
return this->Current->
Item;
00534 }
00535
00536
return NULL;
00537 }
00538
00539
inline vtkObject*
00540 vtkUniqueCollection::GetNthItemByType (
int aIndex,
const char* aType)
00541 {
00542
vtkCollectionElement* elem = this->Top;
00543
int j = 0;
00544
00545
while (elem != NULL)
00546 {
00547
if (elem->
Item->
IsA(aType))
00548
if (aIndex == j++)
00549
return elem->
Item;
00550
00551 elem = elem->
Next;
00552 }
00553
00554
return NULL;
00555 }
00556
00557
00558
inline unsigned long
00559 vtkUniqueCollection::GetMTime (
void)
00560 {
00561
vtkObject* item;
00562
unsigned long itemMTime;
00563
unsigned long mtime = this->
vtkCollection::GetMTime();
00564
00565
for (this->
InitTraversal(); (item = this->
GetNextItem()) != NULL; )
00566 {
00567
if ((itemMTime = item->
GetMTime()) > mtime)
00568 {
00569 mtime = itemMTime;
00570 }
00571 }
00572
00573
return mtime;
00574 }
00575
00576
VTK_EXTENSIONS_NAMESPACE_END
00577
00578
#endif
00579
00580
00581
00582