1 /************************************************************************* 2 * * 3 * Tokamak Physics Engine, Copyright (C) 2002-2007 David Lam. * 4 * All rights reserved. Email: david@tokamakphysics.com * 5 * Web: www.tokamakphysics.com * 6 * * 7 * This library is distributed in the hope that it will be useful, * 8 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the files * 10 * LICENSE.TXT for more details. * 11 * * 12 *************************************************************************/ 13 14 #ifndef NE_STACK_H 15 #define NE_STACK_H 16 17 #define NE_MAX_REST_ON 3 18 19 class neStackHeader; 20 21 class neStackInfo 22 { 23 public: Init()24 void Init() 25 { 26 stackHeader = NULL; 27 body = NULL; 28 isTerminator = true; 29 isBroken = false; 30 } 31 void Resolve(); 32 33 void AddToSolver(neBool addCheader); 34 35 neStackHeader * CheckAcceptNewHeader(neStackHeader * newHeader); 36 37 void ForceAcceptNewHeader(neStackHeader * newHeader); 38 39 //void Break(); 40 41 void CheckHeader(neStackHeader * sh); 42 43 neBool isResolved; 44 neBool isTerminator; 45 neBool isBroken; 46 neStackHeader * stackHeader; 47 neRigidBody_ * body; 48 s32 startTime; 49 s32 endTime; 50 51 //neRestRecord restRecords[neRigidBody_::NE_RB_MAX_RESTON_RECORDS]; 52 }; 53 54 typedef neDLinkList<neStackInfo> neStackInfoHeap; 55 56 typedef neFreeListItem<neStackInfo> neStackInfoItem; 57 58 class neStackHeader 59 { 60 public: 61 neFixedTimeStepSimulator * sim; 62 63 neStackInfo * head; 64 neStackInfo * tail; 65 s32 infoCount; 66 neBool isHeaderX; 67 neBool isAllIdle; 68 static s32 golbalTime; 69 neBool dynamicSolved; 70 Null()71 void Null() 72 { 73 head = NULL; 74 75 tail = NULL; 76 77 infoCount = 0; 78 79 isHeaderX = false; 80 81 isAllIdle = false; 82 83 dynamicSolved = false; 84 } 85 86 //void Purge(); 87 88 void Resolve(); 89 CheckLength()90 void CheckLength() 91 { 92 s32 c = 0; 93 94 neStackInfoItem * item = (neStackInfoItem *) head; 95 96 while (item) 97 { 98 ASSERT(c < infoCount); 99 100 c++; 101 102 item = item->next; 103 } 104 } CheckHeader()105 void CheckHeader() 106 { 107 ASSERT(infoCount != 0); 108 109 s32 c = 0; 110 111 neStackInfoItem * item = (neStackInfoItem *) head; 112 113 while (item) 114 { 115 ASSERT(c < infoCount); 116 117 c++; 118 119 neStackInfo * sinfo = (neStackInfo*) item; 120 121 ASSERT(sinfo->stackHeader == this); 122 123 if (!sinfo->isTerminator) 124 sinfo->CheckHeader(this); 125 126 item = item->next; 127 } 128 ASSERT(c == infoCount); 129 } Add(neStackInfo * add)130 void Add(neStackInfo * add) 131 { 132 if (!head) 133 { 134 head = tail = add; 135 136 ASSERT(((neStackInfoItem*)add)->next == NULL); 137 } 138 else 139 { 140 ASSERT(add != tail); 141 142 ((neStackInfoItem*)tail)->Append((neStackInfoItem*)add); 143 144 tail = add; 145 } 146 infoCount++; 147 148 add->stackHeader = this; 149 } 150 void Remove(neStackInfo * add, s32 flag = 0) 151 { 152 /* if (infoCount == 1 && !isHeaderX && flag == 0) 153 ASSERT(0); 154 */ 155 neStackInfoItem * item = (neStackInfoItem *)add; 156 157 if (head == add) 158 head = (neStackInfo*)item->next; 159 160 if (tail == add) 161 tail = (neStackInfo*)item->prev; 162 163 item->Remove(); 164 165 infoCount--; 166 167 add->stackHeader = NULL; 168 } Check(neStackInfo * st)169 neBool Check(neStackInfo * st) 170 { 171 s32 c = 0; 172 173 neStackInfoItem * item = (neStackInfoItem *) head; 174 175 while (item) 176 { 177 ASSERT(c < infoCount); 178 179 c++; 180 181 neStackInfo * sinfo = (neStackInfo*) item; 182 183 ASSERT(sinfo->stackHeader == this); 184 185 if (st == sinfo) 186 { 187 return true; 188 } 189 item = item->next; 190 } 191 return false; 192 } 193 neBool CheckStackDisconnected(); 194 GetBottomStackBody()195 neRigidBody_ * GetBottomStackBody() 196 { 197 return NULL; 198 /* if (!head) 199 return NULL; 200 201 neStackInfoItem * item = (neStackInfoItem *) head; 202 203 while (item) 204 { 205 neStackInfo * sinfo = (neStackInfo *) item; 206 207 neRigidBody_ * body = sinfo->body; 208 209 neStackInfo * nextSinfo = NULL; 210 211 for (s32 i = 0; i < sinfo->restOnCount; i++) 212 { 213 ASSERT (sinfo->restOn[i].body); 214 215 if (sinfo->restOn[i].body->stackInfo) 216 { 217 if (sinfo->restOn[i].body->stackHeader == NULL) 218 { 219 220 } 221 else 222 { 223 nextSinfo = sinfo->restOn[i].body->stackInfo; 224 break; 225 } 226 } 227 else 228 { 229 //return sinfo->restOn[i].body; 230 } 231 } 232 if (nextSinfo != NULL) 233 { 234 item = (neStackInfoItem *)nextSinfo; 235 } 236 else 237 { 238 return sinfo->body; 239 } 240 } 241 ASSERT(0); 242 return NULL; 243 */ } 244 void ChangeHeader(neStackHeader * newHeader); 245 246 void AddToSolver(/*neBool withConstraint*/); 247 248 void AddToSolverNoConstraintHeader(); 249 250 void ResetRigidBodyFlag(); 251 }; 252 253 typedef neDLinkList<neStackHeader> neStackHeaderHeap; 254 255 typedef neFreeListItem<neStackHeader> neStackHeaderItem; 256 257 #endif //NE_STACK_H 258