1 /* 2 * Copyright 2020 Google LLC. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8 #ifndef SKSL_NODEARRAYWRAPPER 9 #define SKSL_NODEARRAYWRAPPER 10 11 #include "include/private/SkTArray.h" 12 13 namespace SkSL { 14 15 class IRNode; 16 17 // Wraps an SkTArray<std::unique_ptr<Base>> and presents it as a collection of <T> 18 // Once the rearchitecture is complete, Base will always be IRNode and thus we can remove that 19 // parameter, but right now we have to worry about wrapping both ExpressionArray and StatementArray 20 template<typename T, typename Base> 21 class NodeArrayWrapper { 22 public: 23 class iterator { 24 public: 25 T& operator*() { 26 return static_cast<T&>(**fBase); 27 } 28 29 T* operator->() { 30 return static_cast<T*>(fBase->get()); 31 } 32 33 iterator& operator++() { 34 ++fBase; 35 return *this; 36 } 37 38 bool operator==(const iterator& other) const { 39 return fBase == other.fBase; 40 } 41 42 bool operator!=(const iterator& other) const { 43 return fBase != other.fBase; 44 } 45 46 private: iterator(const std::unique_ptr<Base> * base)47 iterator(const std::unique_ptr<Base>* base) 48 : fBase(base) {} 49 50 const std::unique_ptr<Base>* fBase; 51 52 friend class NodeArrayWrapper; 53 }; 54 55 class const_iterator { 56 public: 57 const T& operator*() { 58 return static_cast<const T&>(**fBase); 59 } 60 61 const T* operator->() { 62 return static_cast<const T*>(fBase->get()); 63 } 64 65 const_iterator& operator++() { 66 ++fBase; 67 return *this; 68 } 69 70 bool operator==(const const_iterator& other) const { 71 return fBase == other.fBase; 72 } 73 74 bool operator!=(const const_iterator& other) const { 75 return fBase != other.fBase; 76 } 77 78 private: const_iterator(const std::unique_ptr<Base> * base)79 const_iterator(const std::unique_ptr<Base>* base) 80 : fBase(base) {} 81 82 const std::unique_ptr<Base>* fBase; 83 84 friend class NodeArrayWrapper; 85 }; 86 NodeArrayWrapper(SkTArray<std::unique_ptr<Base>> * contents)87 NodeArrayWrapper(SkTArray<std::unique_ptr<Base>>* contents) 88 : fContents(contents) {} 89 NodeArrayWrapper(const NodeArrayWrapper & other)90 NodeArrayWrapper(const NodeArrayWrapper& other) 91 : fContents(other.fContents) {} 92 93 NodeArrayWrapper& operator=(const NodeArrayWrapper& other) { 94 fContents = other.fContents; 95 } 96 reset()97 void reset() { 98 fContents->reset(); 99 } 100 reserve_back(int n)101 void reserve_back(int n) { 102 fContents->reserve_back(n); 103 } 104 count()105 int count() const { 106 return fContents->count(); 107 } 108 empty()109 bool empty() const { 110 return fContents->empty(); 111 } 112 113 push_back(T * t)114 T& push_back(T* t) { 115 return static_cast<T&>(*fContents->emplace_back(t)); 116 } 117 emplace_back(Args &&...args)118 template<class... Args> T& emplace_back(Args&&... args) { 119 return static_cast<T&>(*fContents->emplace_back(new T(std::forward<Args>(args)...))); 120 } 121 pop_back()122 void pop_back() { 123 fContents->pop_back(); 124 } 125 begin()126 iterator begin() { 127 return iterator(fContents->begin()); 128 } 129 end()130 iterator end() { 131 return iterator(fContents->end()); 132 } 133 begin()134 const_iterator begin() const { 135 return const_iterator(fContents->begin()); 136 } 137 end()138 const_iterator end() const { 139 return const_iterator(fContents->end()); 140 } 141 142 T& operator[](int i) { 143 SkASSERT(fContents->at(i)); 144 return fContents->at(i)->template as<T>(); 145 } 146 147 const T& operator[](int i) const { 148 SkASSERT(fContents->at(i)); 149 return fContents->at(i)->template as<T>(); 150 } 151 front()152 T& front() { 153 return fContents->front()->template as<T>(); 154 } 155 front()156 const T& front() const { 157 return fContents->front()->template as<T>(); 158 } 159 back()160 T& back() { 161 return fContents->back()->template as<T>(); 162 } 163 back()164 const T& back() const { 165 return fContents->back()->template as<T>(); 166 } 167 capacity()168 int capacity() const { 169 return fContents->capacity(); 170 } 171 172 private: 173 SkTArray<std::unique_ptr<Base>>* fContents; 174 }; 175 176 template<typename T, typename Base> 177 class ConstNodeArrayWrapper { 178 public: 179 class iterator { 180 public: 181 const T& operator*() { 182 return static_cast<T&>(**fBase); 183 } 184 185 const T* operator->() { 186 return static_cast<T*>(fBase->get()); 187 } 188 189 iterator& operator++() { 190 ++fBase; 191 return *this; 192 } 193 194 bool operator==(const iterator& other) const { 195 return fBase == other.fBase; 196 } 197 198 bool operator!=(const iterator& other) const { 199 return fBase != other.fBase; 200 } 201 202 private: iterator(const std::unique_ptr<Base> * base)203 iterator(const std::unique_ptr<Base>* base) 204 : fBase(base) {} 205 206 const std::unique_ptr<Base>* fBase; 207 208 friend class ConstNodeArrayWrapper; 209 }; 210 ConstNodeArrayWrapper(const SkTArray<std::unique_ptr<Base>> * contents)211 ConstNodeArrayWrapper(const SkTArray<std::unique_ptr<Base>>* contents) 212 : fContents(contents) {} 213 ConstNodeArrayWrapper(const ConstNodeArrayWrapper & other)214 ConstNodeArrayWrapper(const ConstNodeArrayWrapper& other) 215 : fContents(other.fContents) {} 216 count()217 int count() const { 218 return fContents->count(); 219 } 220 empty()221 bool empty() const { 222 return fContents->empty(); 223 } 224 begin()225 iterator begin() const { 226 return iterator(fContents->begin()); 227 } 228 end()229 iterator end() const { 230 return iterator(fContents->end()); 231 } 232 233 T& operator[](int i) { 234 return fContents->at(i)->template as<T>(); 235 } 236 237 const T& operator[](int i) const { 238 return fContents->at(i)->template as<T>(); 239 } 240 front()241 T& front() { 242 return fContents->front()->template as<T>(); 243 } 244 front()245 const T& front() const { 246 return fContents->front()->template as<T>(); 247 } 248 back()249 T& back() { return fContents->back()->template as<T>(); } 250 back()251 const T& back() const { return fContents->back()->template as<T>(); } 252 253 private: 254 const SkTArray<std::unique_ptr<Base>>* fContents; 255 }; 256 257 } // namespace SkSL 258 259 #endif 260