12#ifndef SCRIPTS_INCLUDE__MULTILIST_H_
13#define SCRIPTS_INCLUDE__MULTILIST_H_
15#include "engine_vector.h"
17class GenericMultiListClass;
18class MultiListObjectClass;
19class GenericMultiListIterator;
21class MultiListNodeClass :
public AutoPoolClass<MultiListNodeClass, 256>
26 Prev = Next = NextList = 0;
31 MultiListNodeClass* Prev;
32 MultiListNodeClass* Next;
33 MultiListNodeClass* NextList;
34 MultiListObjectClass* Object;
35 GenericMultiListClass* List;
38class MultiListObjectClass
41 MultiListNodeClass* ListNode;
44 MultiListObjectClass(): ListNode(NULL) {};
45 virtual ~MultiListObjectClass();
47 MultiListNodeClass* Get_List_Node()
const
52 void Set_List_Node(MultiListNodeClass *node)
59class GenericMultiListClass
62 MultiListNodeClass Head;
65 GenericMultiListClass(
const GenericMultiListClass&);
66 GenericMultiListClass& operator = (
const GenericMultiListClass&);
69 friend class GenericMultiListIterator;
70 friend class MultiListObjectClass;
71 SHARED_API
bool Internal_Add(MultiListObjectClass *obj,
bool onlyonce =
true);
72 SHARED_API
bool Internal_Add_Tail(MultiListObjectClass *obj,
bool onlyonce =
true);
73 SHARED_API
bool Internal_Add_After(MultiListObjectClass *obj,
const MultiListObjectClass* existing_list_member,
bool onlyonce =
true);
74 SHARED_API
bool Internal_Remove(MultiListObjectClass *obj);
75 SHARED_API MultiListObjectClass* Internal_Remove_List_Head();
77 inline MultiListObjectClass* Internal_Get_List_Head()
const
79 if (Is_Empty())
return 0;
80 TT_ASSERT(Head.Next->Object != NULL);
81 return Head.Next->Object;
85 GenericMultiListClass()
87 Head.Next = Head.Prev = &Head;
92 virtual ~GenericMultiListClass()
94 TT_ASSERT(Is_Empty());
97 inline bool Is_In_List(MultiListObjectClass *obj)
const
102 inline bool Is_Empty()
const
104 return (Head.Next == &Head);
107 bool Contains(MultiListObjectClass * obj)
const
110 for (MultiListNodeClass* node = obj->Get_List_Node(); node; node = node->NextList)
112 if (node->List ==
this)
123class GenericMultiListIterator
126 GenericMultiListIterator(
const GenericMultiListClass *list)
132 void First(
const GenericMultiListClass *list)
135 CurNode = List->Head.Next;
140 CurNode = List->Head.Next;
145 CurNode = CurNode->Next;
150 CurNode = CurNode->Prev;
155 return (CurNode == &(List->Head));
159 MultiListObjectClass* Current_Object()
const
161 return CurNode->Object;
164 const GenericMultiListClass* List;
165 const MultiListNodeClass* CurNode;
168template <
typename T>
class MultiListIterator;
169template <
typename T>
class MultiListClass :
public GenericMultiListClass
173 MultiListClass(
const MultiListClass & that);
174 MultiListClass & operator = (
const MultiListClass & that);
177 MultiListClass(): GenericMultiListClass() {};
179 virtual ~MultiListClass()
187 bool Add(T* obj,
bool onlyonce =
true)
189 return Internal_Add(obj, onlyonce);
192 bool Add_Tail(T* obj,
bool onlyonce =
true)
194 return Internal_Add_Tail(obj, onlyonce);
197 bool Add_After(T* obj,
const T* existing_list_member,
bool onlyonce =
true)
199 return Internal_Add_After(obj, existing_list_member, onlyonce);
204 return Internal_Remove(obj);
209 return (T*) Internal_Get_List_Head();
214 return (T*) Internal_Get_List_Head();
219 return (T*) Internal_Remove_List_Head();
224 while (Peek_Head() != NULL)
230 MultiListIterator<T> Iterator()
const;
233template <
typename T>
class MultiListIterator :
public GenericMultiListIterator
236 MultiListIterator(
const MultiListClass<T> *list) : GenericMultiListIterator(list) {};
238 T* Get_Obj(
void)
const
240 return (T*)Current_Object();
243 T* Peek_Obj(
void)
const
245 return (T*)Current_Object();
248 void Remove_Current_Object()
253 ((MultiListClass<T>*)List)->Remove(obj);
258 void operator++() { Next(); }
259 operator bool()
const {
return !Is_Done(); }
260 T* operator->() {
return Get_Obj(); }
261 T* operator*() {
return Get_Obj(); }
265template <
typename T> MultiListIterator<T> MultiListClass<T>::Iterator()
const
267 return MultiListIterator<T>(
this);
270template <
typename T>
class RefMultiListIterator;
271template <
typename T>
class RefMultiListClass:
public GenericMultiListClass
275 RefMultiListClass(
const RefMultiListClass&);
276 RefMultiListClass& operator = (
const RefMultiListClass&);
279 RefMultiListClass(): GenericMultiListClass() {};
281 virtual ~RefMultiListClass()
289 bool Add(T* obj,
bool onlyonce =
true)
291 bool res = Internal_Add(obj, onlyonce);
292 if (res ==
true) obj->Add_Ref();
296 bool Add_Tail(T* obj,
bool onlyonce =
true)
298 bool res = Internal_Add_Tail(obj, onlyonce);
299 if (res ==
true) obj->Add_Ref();
303 bool Add_After(T* obj,
const T* existing_list_member,
bool onlyonce =
true)
305 bool res = Internal_Add_After(obj, existing_list_member, onlyonce);
306 if (res ==
true) obj->Add_Ref();
312 bool res = Internal_Remove(obj);
313 if (res ==
true) obj->Release_Ref();
319 T* obj = (T*) Internal_Remove_List_Head();
330 T* obj = (T*) Internal_Get_List_Head();
331 if (obj) obj->Add_Ref();
337 return (T*) Internal_Get_List_Head();
342 return (T*) Internal_Remove_List_Head();
347 while (Peek_Head() != NULL)
353 RefMultiListIterator<T> Iterator()
const;
356template <
typename T>
class RefMultiListIterator :
public GenericMultiListIterator
359 RefMultiListIterator(
const RefMultiListClass<T> *list): GenericMultiListIterator(list) {};
363 T* obj = (T*)Current_Object();
364 if (obj != NULL) obj->Add_Ref();
370 return (T*)Current_Object();
373 void Remove_Current_Object()
378 ((RefMultiListClass<T> *)List)->Remove(obj);
382 void operator++() { Next(); }
383 operator bool()
const {
return !Is_Done(); }
384 T* operator->()
const {
return Peek_Obj(); }
388template <
typename T> RefMultiListIterator<T> RefMultiListClass<T>::Iterator()
const
390 return RefMultiListIterator<T>(
this);
393TT_INLINE MultiListObjectClass::~MultiListObjectClass()
397 ListNode->List->Internal_Remove(
this);
401TT_INLINE
int GenericMultiListClass::Count()
const
404 GenericMultiListIterator it(
this);
405 for (it.First(); !it.Is_Done(); it.Next())
413template<
class ObjectType>
class PriorityMultiListIterator :
414 public MultiListIterator<ObjectType>
417 PriorityMultiListIterator(MultiListClass<ObjectType>* list)
418 : OriginalHead (NULL),
419 MultiListIterator<ObjectType>(list)
424 bool Process_Head(ObjectType**
object)
430 if (CurNode != NULL && CurNode->Object != NULL && OriginalHead != CurNode) {
432 OriginalHead = CurNode;
433 *
object = (ObjectType*)CurNode->Object;
437 Remove_Current_Object();
438 ((MultiListClass<ObjectType> *)PriorityMultiListIterator::List)->Add_Tail ((*
object));
448 const MultiListNodeClass* OriginalHead;