OSVR Framework (Internal Development Docs)  0.6-1962-g59773924
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Modules Pages
GeneralizedTransform.cpp
Go to the documentation of this file.
1 
11 // Copyright 2015 Sensics, Inc.
12 //
13 // Licensed under the Apache License, Version 2.0 (the "License");
14 // you may not use this file except in compliance with the License.
15 // You may obtain a copy of the License at
16 //
17 // http://www.apache.org/licenses/LICENSE-2.0
18 //
19 // Unless required by applicable law or agreed to in writing, software
20 // distributed under the License is distributed on an "AS IS" BASIS,
21 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
22 // See the License for the specific language governing permissions and
23 // limitations under the License.
24 
25 // Internal Includes
28 
29 // Library/third-party includes
30 // - none
31 
32 // Standard includes
33 #include <utility>
34 
35 namespace osvr {
36 namespace common {
39  nest(transform);
40  }
41 
42  void GeneralizedTransform::nest(Json::Value const &transform) {
43  if (!transform.isObject()) {
45  return;
46  }
47  auto currentPtr = &transform;
48  while (currentPtr->isObject() &&
49  currentPtr->isMember(routing_keys::child())) {
50  auto const &current = *currentPtr;
51  pushLevelBack(current);
52  currentPtr = &(current[routing_keys::child()]);
53  }
54  }
55 
56  void GeneralizedTransform::wrap(Json::Value const &transform) {
57  Json::Value newLayer{transform};
58  if (newLayer.isObject()) {
59  container().insert(begin(), newLayer);
60  }
61  }
62 
63  bool GeneralizedTransform::empty() const { return container().empty(); }
64 
65  Json::Value GeneralizedTransform::get() const { return recompose(); }
66 
67  Json::Value GeneralizedTransform::get(std::string const &leaf) const {
68  return recompose(leaf.empty() ? Json::nullValue : Json::Value(leaf));
69  }
70 
71  void GeneralizedTransform::pushLevelBack(Json::Value level) {
72  if (level.isMember(routing_keys::child())) {
73  level.removeMember(routing_keys::child());
74  }
75  container().emplace_back(std::move(level));
76  }
77  namespace {
78  template <typename Container> class ReverseFacade {
79  public:
80  ReverseFacade(Container const &c) : m_container(c) {}
81  // nonassignable
82  ReverseFacade &operator=(ReverseFacade const &) = delete;
83 
84  using const_iterator = typename Container::const_reverse_iterator;
85  const_iterator begin() const { return m_container.rbegin(); }
86  const_iterator end() const { return m_container.rend(); }
87 
88  private:
89  Container const &m_container;
90  };
91  template <typename Container>
92  inline ReverseFacade<Container> reverse(Container const &c) {
93  return ReverseFacade<Container>(c);
94  }
95  } // namespace
96  Json::Value GeneralizedTransform::recompose(Json::Value leaf) const {
97  if (container().empty()) {
98  return leaf;
99  }
100  Json::Value state{leaf};
101  for (auto const &level : reverse(container())) {
102  Json::Value nextLevel{level};
103  if (!state.isNull()) {
104  nextLevel[routing_keys::child()] = state;
105  }
106  state = std::move(nextLevel);
107  }
108  return state;
109  }
110 } // namespace common
111 } // namespace osvr
bool empty() const
Is this an empty transform?
void nest(Json::Value const &transform)
Process the given transform as "inner" to any existing transform.
void wrap(Json::Value const &transform)
Wrap a single new layer of transform around the existing ones, if any.
t_< detail::transform_< List, Fun >> transform
Definition: Transform.h:54
Json::Value get() const
Get a "reconstituted" version of the transformation.
GeneralizedTransform()
Empty transformation.