diff options
Diffstat (limited to 'skia/include/SkTDStack.h')
-rw-r--r-- | skia/include/SkTDStack.h | 121 |
1 files changed, 121 insertions, 0 deletions
diff --git a/skia/include/SkTDStack.h b/skia/include/SkTDStack.h new file mode 100644 index 0000000..e070cb9 --- /dev/null +++ b/skia/include/SkTDStack.h @@ -0,0 +1,121 @@ +/* include/graphics/SkTDStack.h +** +** Copyright 2006, Google Inc. +** +** Licensed under the Apache License, Version 2.0 (the "License"); +** you may not use this file except in compliance with the License. +** You may obtain a copy of the License at +** +** http://www.apache.org/licenses/LICENSE-2.0 +** +** Unless required by applicable law or agreed to in writing, software +** distributed under the License is distributed on an "AS IS" BASIS, +** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +** See the License for the specific language governing permissions and +** limitations under the License. +*/ + +#ifndef SkTDStack_DEFINED +#define SkTDStack_DEFINED + +#include "SkTypes.h" + +template <typename T> class SkTDStack : SkNoncopyable { +public: + SkTDStack() : fCount(0), fTotalCount(0) + { + fInitialRec.fNext = NULL; + fRec = &fInitialRec; + + // fCount = kSlotCount; + } + ~SkTDStack() + { + Rec* rec = fRec; + while (rec != &fInitialRec) + { + Rec* next = rec->fNext; + sk_free(rec); + rec = next; + } + } + + int count() const { return fTotalCount; } + + T* push() + { + SkASSERT(fCount <= kSlotCount); + if (fCount == kSlotCount) + { + Rec* rec = (Rec*)sk_malloc_throw(sizeof(Rec)); + rec->fNext = fRec; + fRec = rec; + fCount = 0; + } + ++fTotalCount; + return &fRec->fSlots[fCount++]; + } + void push(const T& elem) { *this->push() = elem; } + const T& index(int idx) const + { + SkASSERT(fRec && fCount > idx); + return fRec->fSlots[fCount - idx - 1]; + } + T& index(int idx) + { + SkASSERT(fRec && fCount > idx); + return fRec->fSlots[fCount - idx - 1]; + } + const T& top() const + { + SkASSERT(fRec && fCount > 0); + return fRec->fSlots[fCount - 1]; + } + T& top() + { + SkASSERT(fRec && fCount > 0); + return fRec->fSlots[fCount - 1]; + } + void pop(T* elem) + { + if (elem) + *elem = fRec->fSlots[fCount - 1]; + this->pop(); + } + void pop() + { + SkASSERT(fCount > 0 && fRec); + --fTotalCount; + if (--fCount == 0) + { + if (fRec != &fInitialRec) + { + Rec* rec = fRec->fNext; + sk_free(fRec); + fCount = kSlotCount; + fRec = rec; + } + else + SkASSERT(fTotalCount == 0); + } + } + +private: + enum { + kSlotCount = 8 + }; + + struct Rec; + friend struct Rec; + + struct Rec { + Rec* fNext; + T fSlots[kSlotCount]; + }; + Rec fInitialRec; + Rec* fRec; + int fCount, fTotalCount; +}; + +#endif + |