All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
childrenView.h
Go to the documentation of this file.
1 //
2 // Copyright 2016 Pixar
3 //
4 // Licensed under the Apache License, Version 2.0 (the "Apache License")
5 // with the following modification; you may not use this file except in
6 // compliance with the Apache License and the following modification to it:
7 // Section 6. Trademarks. is deleted and replaced with:
8 //
9 // 6. Trademarks. This License does not grant permission to use the trade
10 // names, trademarks, service marks, or product names of the Licensor
11 // and its affiliates, except as required to comply with Section 4(c) of
12 // the License and to reproduce the content of the NOTICE file.
13 //
14 // You may obtain a copy of the Apache License at
15 //
16 // http://www.apache.org/licenses/LICENSE-2.0
17 //
18 // Unless required by applicable law or agreed to in writing, software
19 // distributed under the Apache License with the above modification is
20 // distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
21 // KIND, either express or implied. See the Apache License for the specific
22 // language governing permissions and limitations under the Apache License.
23 //
24 #ifndef SDF_CHILDRENVIEW_H
25 #define SDF_CHILDRENVIEW_H
26 
28 
29 #include "pxr/pxr.h"
30 #include "pxr/usd/sdf/api.h"
31 #include "pxr/usd/sdf/children.h"
32 #include "pxr/base/tf/iterator.h"
33 
34 #include <boost/compressed_pair.hpp>
35 #include <boost/iterator/filter_iterator.hpp>
36 #include <boost/iterator/iterator_facade.hpp>
37 #include <boost/iterator/reverse_iterator.hpp>
38 #include <algorithm>
39 #include <vector>
40 
41 PXR_NAMESPACE_OPEN_SCOPE
42 
51 template <class T>
53 public:
54  bool operator()(const T& x) const { return true; }
55 };
56 
61 template <class T>
63 public:
64  typedef T PrivateType;
65  typedef T PublicType;
66  static const PublicType& Convert(const PrivateType& t) { return t; }
67 };
68 
76 template <typename _Owner, typename _InnerIterator, typename _DummyPredicate>
77 class Sdf_ChildrenViewTraits {
78 private:
79 
80  // Internal predicate object which will be passed to the filter
81  // iterator. This just calls through to the owner's predicate.
82  class _Predicate {
83  public:
84  typedef typename _Owner::value_type value_type;
85 
86  _Predicate() : _owner(NULL) { }
87  _Predicate(const _Owner* owner) : _owner(owner) { }
88 
89  bool operator()(const value_type& x) const
90  {
91  return _owner->GetPredicate()(
92  _Owner::Adapter::Convert(x));
93  }
94 
95  private:
96  const _Owner* _owner;
97  };
98 
99 public:
100  typedef boost::filter_iterator<_Predicate, _InnerIterator> const_iterator;
101 
102  // Convert from a private _InnerIterator to a public const_iterator.
103  // filter_iterator requires an end iterator, which is constructed using
104  // size.
105  static const_iterator GetIterator(const _Owner* owner,
106  const _InnerIterator& i,
107  size_t size)
108  {
109  _InnerIterator end(owner,size);
110  return const_iterator(_Predicate(owner), i, end);
111  }
112 
113  // Convert from a public const_iterator to a private _InnerIterator.
114  static const _InnerIterator& GetBase(const const_iterator& i)
115  {
116  return i.base();
117  }
118 };
119 
120 // Children view traits specialization for trivial predicates. This
121 // eliminates the predicate altogether and defines the public iterator type
122 // to be the same as the inner iterator type.
123 template <typename _Owner, typename _InnerIterator>
124 class Sdf_ChildrenViewTraits<_Owner, _InnerIterator,
125  SdfChildrenViewTrivialPredicate<typename _Owner::ChildPolicy::ValueType> > {
126 private:
127 
128 public:
129  typedef _InnerIterator const_iterator;
130 
131  static const const_iterator& GetIterator(const _Owner*,
132  const _InnerIterator& i, size_t size)
133  {
134  return i;
135  }
136 
137  static const _InnerIterator& GetBase(const const_iterator& i)
138  {
139  return i;
140  }
141 };
142 
164 template <typename _ChildPolicy,
165  typename _Predicate =
167  typename _ChildPolicy::ValueType>,
168  typename _Adapter =
170  typename _ChildPolicy::ValueType> >
172 public:
174 
175  typedef _Adapter Adapter;
176  typedef _Predicate Predicate;
177  typedef _ChildPolicy ChildPolicy;
178  typedef typename ChildPolicy::KeyPolicy KeyPolicy;
179  typedef Sdf_Children<ChildPolicy> ChildrenType;
180 
181  typedef typename ChildPolicy::KeyType key_type;
182  typedef typename Adapter::PublicType value_type;
183 
184 private:
185 
186  // An iterator type for the internal unfiltered data storage. This
187  // iterator holds a pointer to its owning object and an index into
188  // the owner's storage. That allows the iterator to operate without
189  // knowing anything about the specific data storage that's used,
190  // which is important for providing both Gd and Lsd backed storage.
191  class _InnerIterator :
192  public boost::iterator_facade<_InnerIterator,
193  value_type,
194  std::random_access_iterator_tag,
195  value_type> {
196  public:
197  typedef value_type reference;
198  typedef size_t size_type;
199  typedef ptrdiff_t difference_type;
200 
201  _InnerIterator() :
202  _owner(NULL), _pos(0) { }
203  _InnerIterator(const This* owner, const size_t& pos) :
204  _owner(owner), _pos(pos) { }
205 
206  private:
207  friend class boost::iterator_core_access;
208 
209  reference dereference() const
210  {
211  return _owner->_Get(_pos);
212  }
213 
214  bool equal(const _InnerIterator& other) const
215  {
216  return _pos == other._pos;
217  }
218 
219  void increment() {
220  ++_pos;
221  }
222 
223  void decrement() {
224  --_pos;
225  }
226 
227  void advance(difference_type n) {
228  _pos += n;
229  }
230 
231  difference_type distance_to(const _InnerIterator& other) const {
232  return other._pos-_pos;
233  }
234 
235  private:
236  const This* _owner;
237  size_t _pos;
238  };
239 
240 public:
241  typedef Sdf_ChildrenViewTraits<This, _InnerIterator, Predicate> _Traits;
242  typedef typename _Traits::const_iterator const_iterator;
243  typedef boost::reverse_iterator<const_iterator> const_reverse_iterator;
244  typedef size_t size_type;
245  typedef ptrdiff_t difference_type;
246 
248  {
249  }
250 
251  SdfChildrenView(const SdfLayerHandle &layer, const SdfPath &path,
252  const TfToken &childrenKey,
253  const KeyPolicy& keyPolicy = KeyPolicy()) :
254  _children(layer, path, childrenKey, keyPolicy)
255  {
256  }
257 
258  SdfChildrenView(const SdfLayerHandle &layer, const SdfPath &path,
259  const TfToken &childrenKey,
260  const Predicate& predicate,
261  const KeyPolicy& keyPolicy = KeyPolicy()) :
262  _children(layer, path, childrenKey, keyPolicy),
263  _predicate(predicate)
264  {
265  }
266 
267  SdfChildrenView(const SdfChildrenView &other) :
268  _children(other._children),
269  _predicate(other._predicate)
270  {
271  }
272 
273  template <class OtherAdapter>
274  SdfChildrenView(const SdfChildrenView<ChildPolicy, Predicate,
275  OtherAdapter> &other) :
276  _children(other._children),
277  _predicate(other._predicate)
278  {
279  }
280 
281  ~SdfChildrenView()
282  {
283  }
284 
285  SdfChildrenView& operator=(const SdfChildrenView &other)
286  {
287  _children= other._children;
288  _predicate = other._predicate;
289  return *this;
290  }
291 
293  const_iterator begin() const {
294  _InnerIterator i(this,0);
295  return _Traits::GetIterator(this, i, _GetSize());
296  }
297 
299  const_iterator end() const {
300  _InnerIterator i(this,_GetSize());
301  return _Traits::GetIterator(this, i, _GetSize());
302  }
303 
306  const_reverse_iterator rbegin() const {
307  return const_reverse_iterator(end());
308  }
309 
312  const_reverse_iterator rend() const {
313  return const_reverse_iterator(begin());
314  }
315 
317  size_type size() const {
318  return std::distance(begin(), end());
319  }
320 
322  bool empty() const {
323  return begin() == end();
324  }
325 
327  value_type operator[](size_type n) const {
328  const_iterator i = begin();
329  std::advance(i, n);
330  return *i;
331  }
332 
334  value_type front() const {
335  return *begin();
336  }
337 
339  value_type back() const {
340  return *rbegin();
341  }
342 
344  const_iterator find(const key_type& x) const {
345  _InnerIterator inner(this, _children.Find(x));
346  const_iterator iter = _Traits::GetIterator(this, inner, _GetSize());
347 
348  // _Traits::GetIterator may return a filtered iterator. We need to
349  // check that that iterator actually corresponds to the desired item.
350  // This ensures that we return end() in the case where the element being
351  // searched for is present in the children but filtered out by the
352  // view's predicate.
353  return _Traits::GetBase(iter) == inner ? iter : end();
354  }
355 
357  const_iterator find(const value_type& x) const {
358  const_iterator i = find(key(x));
359  return (i != end() && *i == x) ? i : end();
360  }
361 
363  key_type key(const const_iterator& x) const {
364  return key(*x);
365  }
366 
368  key_type key(const value_type& x) const {
369  return _children.FindKey(Adapter::Convert(x));
370  }
371 
373  std::vector<value_type> values() const {
374  return std::vector<value_type>(begin(), end());
375  }
376 
378  template <typename V>
379  V values_as() const {
380  V x;
381  std::copy(begin(), end(), std::inserter(x, x.begin()));
382  return x;
383  }
384 
386  std::vector<key_type> keys() const {
387  std::vector<key_type> result;
388  result.reserve(size());
389  for (const_iterator i = begin(), n = end(); i != n; ++i) {
390  result.push_back(key(i));
391  }
392  return result;
393  }
394 
396  template <typename V>
397  V keys_as() const {
398  std::vector<key_type> k = keys();
399  return V(k.begin(), k.end());
400  }
401 
403  template <typename Dict>
404  Dict items_as() const {
405  Dict result;
406  for (const_iterator i = begin(), n = end(); i != n; ++i) {
407  result.insert(std::make_pair(key(i), *i));
408  }
409  return result;
410  }
411 
413  bool has(const key_type& x) const {
414  return (_children.Find(x) != _GetSize());
415  }
416 
419  bool has(const value_type& x) const {
420  return has(key(Adapter::Convert(x)));
421  }
422 
424  size_type count(const key_type& x) const {
425  return has(x);
426  }
427 
430  value_type get(const key_type& x) const {
431  size_t index = _children.Find(x);
432  if (index == _GetSize()) {
433  return value_type();
434  }
435  return _Get(index);
436  }
437 
440  value_type get(const key_type& x, const value_type& fallback) const {
441  size_t index = _children.Find(x);
442  if (index == _GetSize()) {
443  return fallback;
444  }
445  return _Get(index);
446  }
447 
450  value_type operator[](const key_type& x) const {
451  return get(x);
452  }
453 
456  bool operator==(const This& other) const {
457  return _children.IsEqualTo(other._children);
458  }
459 
463  bool operator!=(const This& other) const {
464  return !_children.IsEqualTo(other._children);
465  }
466 
467  // Return true if this object is valid
468  bool IsValid() const {
469  return _children.IsValid();
470  }
471 
472  // Return the Sd_Children object that this view is holding.
473  ChildrenType &GetChildren() {
474  return _children;
475  }
476 
477  // Return this view's predicate.
478  const Predicate& GetPredicate() const {
479  return _predicate;
480  }
481 
482 private:
483  // Return the value that corresponds to the provided index.
484  value_type _Get(size_type index) const {
485  return Adapter::Convert(_children.GetChild(index));
486  }
487 
488  // Return the number of elements
489  size_t _GetSize() const {
490  return _children.GetSize();
491  }
492 
493 private:
494  template <class V, class P, class A> friend class SdfChildrenView;
495  ChildrenType _children;
496  Predicate _predicate;
497 };
498 
501 template <class _View, class _Adapter>
503 {
504  typedef _View OriginalView;
505  typedef SdfChildrenView<typename _View::ChildPolicy,
506  typename _View::Predicate,
507  _Adapter> AdaptedView;
508 
509  static AdaptedView Create(const OriginalView& view)
510  {
511  return AdaptedView(view);
512  }
513 };
514 
515 // Allow TfIteration over children views.
516 template <typename C, typename P, typename A>
517 struct Tf_ShouldIterateOverCopy<SdfChildrenView<C, P, A> > : boost::true_type
518 {
519 };
520 template <typename C, typename P, typename A>
521 struct Tf_IteratorInterface<SdfChildrenView<C, P, A>, false> {
522  typedef SdfChildrenView<C, P, A> Type;
523  typedef typename Type::const_iterator IteratorType;
524  static IteratorType Begin(Type const &c) { return c.begin(); }
525  static IteratorType End(Type const &c) { return c.end(); }
526 };
527 template <typename C, typename P, typename A>
528 struct Tf_IteratorInterface<SdfChildrenView<C, P, A>, true> {
529  typedef SdfChildrenView<C, P, A> Type;
530  typedef typename Type::const_reverse_iterator IteratorType;
531  static IteratorType Begin(Type const &c) { return c.rbegin(); }
532  static IteratorType End(Type const &c) { return c.rend(); }
533 };
534 
535 PXR_NAMESPACE_CLOSE_SCOPE
536 
537 #endif // SDF_CHILDRENVIEW_H
const_iterator find(const value_type &x) const
Finds element x, if present in this view.
Definition: childrenView.h:357
std::vector< value_type > values() const
Returns the elements, in order.
Definition: childrenView.h:373
Special case adapter that does no conversions.
Definition: childrenView.h:62
bool has(const key_type &x) const
Returns true if an element with key x is in the container.
Definition: childrenView.h:413
bool operator==(const This &other) const
Compares children for equality.
Definition: childrenView.h:456
size_type size() const
Returns the size of the vector.
Definition: childrenView.h:317
value_type back() const
Returns the last element.
Definition: childrenView.h:339
const_iterator end() const
Returns an const_iterator pointing to the end of the vector.
Definition: childrenView.h:299
bool operator!=(const This &other) const
Compares children for inequality.
Definition: childrenView.h:463
Dict items_as() const
Returns the elements as a dictionary.
Definition: childrenView.h:404
const_reverse_iterator rbegin() const
Returns an const_reverse_iterator pointing to the beginning of the reversed vector.
Definition: childrenView.h:306
value_type operator[](size_type n) const
Returns the n&#39;th element.
Definition: childrenView.h:327
value_type front() const
Returns the first element.
Definition: childrenView.h:334
Token for efficient comparison, assignment, and hashing of known strings.
Definition: token.h:89
const_iterator begin() const
Returns an const_iterator pointing to the beginning of the vector.
Definition: childrenView.h:293
bool has(const value_type &x) const
Returns true if an element with the same key as x is in the container.
Definition: childrenView.h:419
key_type key(const const_iterator &x) const
Returns the key for an element.
Definition: childrenView.h:363
const_iterator find(const key_type &x) const
Finds the element with key x.
Definition: childrenView.h:344
Helper class to convert a given view of type _View to an adapted view using _Adapter as the adapter c...
Definition: childrenView.h:502
size_type count(const key_type &x) const
Returns the number of elements with key x in the container.
Definition: childrenView.h:424
const_reverse_iterator rend() const
Returns an const_reverse_iterator pointing to the end of the reversed vector.
Definition: childrenView.h:312
A path value used to locate objects in layers or scenegraphs.
Definition: path.h:287
bool empty() const
Returns true if the vector is empty.
Definition: childrenView.h:322
V values_as() const
Returns the elements, in order.
Definition: childrenView.h:379
value_type operator[](const key_type &x) const
Returns the element with key x or a default constructed value if no such element exists.
Definition: childrenView.h:450
key_type key(const value_type &x) const
Returns the key for a value.
Definition: childrenView.h:368
V keys_as() const
Returns the keys for all elements, in order.
Definition: childrenView.h:397
Provides a view onto an object&#39;s children.
Definition: childrenView.h:171
std::vector< key_type > keys() const
Returns the keys for all elements, in order.
Definition: childrenView.h:386
Special case predicate that always passes.
Definition: childrenView.h:52