YARP
Yet Another Robot Platform
FrameTransformContainer.cpp
Go to the documentation of this file.
1 /*
2  * SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
3  * SPDX-License-Identifier: LGPL-2.1-or-later
4  */
5 
7 
8 #include <yarp/os/Log.h>
9 #include <yarp/os/LogComponent.h>
10 #include <yarp/os/LogStream.h>
11 #include <algorithm>
12 
13 using namespace yarp::dev;
14 using namespace yarp::os;
15 using namespace yarp::sig;
16 using namespace yarp::math;
17 
18 namespace {
19 YARP_LOG_COMPONENT(FRAMETRANSFORMCONTAINER, "yarp.device.frameTransformContainer")
20 
21 void invalidateTransform(yarp::math::FrameTransform& trf)
22 {
23  trf.timestamp = yarp::os::Time::now();
24  trf.isStatic = false;
25  trf.translation = { 0,0,0 };
26  trf.rotation = { 0,0,0,0 };
27 }
28 }
29 
30 //------------------------------------------------------------------------------------------------------------------------------
31 
32 bool FrameTransformContainer::getTransforms(std::vector<yarp::math::FrameTransform>& transforms) const
33 {
34  std::lock_guard<std::recursive_mutex> lock(m_trf_mutex);
35  std::copy_if (m_transforms.begin(), m_transforms.end(), std::back_inserter(transforms), [](const yarp::math::FrameTransform& trf){return trf.isValid();});
36  return true;
37 }
38 
39 bool FrameTransformContainer::setTransforms(const std::vector<yarp::math::FrameTransform>& transforms)
40 {
41  for (auto& it : transforms)
42  {
43  setTransform(it);
44  }
45  return true;
46 }
47 
49 {
50  if (new_tr.isValid()==false) return true;
51 
52  std::lock_guard<std::recursive_mutex> lock(m_trf_mutex);
53  for (auto& it : m_transforms)
54  {
55  //this linear search may require some optimization
56  if (it.dst_frame_id == new_tr.dst_frame_id && it.src_frame_id == new_tr.src_frame_id)
57  {
58  //if transform already exists and
59  //its timestamp is more recent than the currently stored transform
60  //than update it
61  if (it.isStatic == false)
62  {
63  if (new_tr.timestamp > it.timestamp)
64  {
65  it = new_tr;
66  return true;
67  }
68  else
69  {
70  //yCDebug(FRAMETRANSFORMCONTAINER) << "Received old transform" << it.dst_frame_id << it.src_frame_id << std::to_string(it.timestamp) << it.isStatic;
71  return true;
72  }
73  }
74  else
75  {
76  return true;
77  }
78  }
79  }
80 
81  //add a new transform
82  m_transforms.push_back(new_tr);
83  return true;
84 }
85 
86 bool FrameTransformContainer::deleteTransform(std::string t1, std::string t2)
87 {
88  std::lock_guard<std::recursive_mutex> lock(m_trf_mutex);
89  if (t1 == "*" && t2 == "*")
90  {
91  for (size_t i = 0; i < m_transforms.size(); i++)
92  {
93  invalidateTransform(m_transforms[i]);
94  }
95  return true;
96  }
97  else
98  {
99  if (t1 == "*")
100  {
101  for (size_t i = 0; i < m_transforms.size(); i++)
102  {
103  //source frame is jolly, thus delete all frames with destination == t2
104  if (m_transforms[i].dst_frame_id == t2)
105  {
106  invalidateTransform(m_transforms[i]);
107  }
108  }
109  return true;
110  }
111  else
112  {
113  if (t2 == "*")
114  {
115  for (size_t i = 0; i < m_transforms.size(); i++)
116  {
117  //destination frame is jolly, thus delete all frames with source == t1
118  if (m_transforms[i].src_frame_id == t1)
119  {
120  invalidateTransform(m_transforms[i]);
121  }
122  }
123  return true;
124  }
125  else
126  {
127  for (size_t i = 0; i < m_transforms.size(); i++)
128  {
129  if ((m_transforms[i].dst_frame_id == t1 && m_transforms[i].src_frame_id == t2) ||
130  (m_transforms[i].dst_frame_id == t2 && m_transforms[i].src_frame_id == t1))
131  {
132  invalidateTransform(m_transforms[i]);
133  return true;
134  }
135  }
136  }
137  }
138  }
139 
140  yCError(FRAMETRANSFORMCONTAINER) << "Transformation deletion not successful";
141  return false;
142 }
143 
145 {
146  std::lock_guard<std::recursive_mutex> lock(m_trf_mutex);
147  for (size_t i = 0; i < m_transforms.size(); i++)
148  {
149  invalidateTransform(m_transforms[i]);
150  }
151  return true;
152 }
153 
155 {
156  std::lock_guard<std::recursive_mutex> lock(m_trf_mutex);
157  double curr_t = yarp::os::Time::now();
158  check_vector:
159  for (auto it= m_transforms.begin(); it!= m_transforms.end(); it++)
160  {
161  if (curr_t - it->timestamp > m_timeout &&
162  it->isStatic == false)
163  {
164  m_transforms.erase(it);
165  goto check_vector;
166  }
167  }
168  return true;
169 }
170 
172 {
173  return const_cast<FrameTransformContainer*>(this)->checkAndRemoveExpired();
174 }
175 
176 bool FrameTransformContainer::size(size_t& size) const
177 {
178  std::lock_guard<std::recursive_mutex> lock(m_trf_mutex);
179  size = m_transforms.size();
180  return true;
181 }
FrameTransformContainer: A class that contains a vector of frame transformations and exposes yarp::de...
bool setTransform(const yarp::math::FrameTransform &transform) override
Save a frame transform in a storage.
bool getTransforms(std::vector< yarp::math::FrameTransform > &transforms) const override
Obtains all frame transforms saved in a storage.
bool size(size_t &size) const
bool setTransforms(const std::vector< yarp::math::FrameTransform > &transforms) override
Save some frame transforms in a storage.
bool deleteTransform(std::string t1, std::string t2) override
Delete a single transform in the storage.
bool clearAll() override
Delete all transforms in a storage.
#define yCError(component,...)
Definition: LogComponent.h:154
#define YARP_LOG_COMPONENT(name,...)
Definition: LogComponent.h:77
An interface for the device drivers.
double now()
Return the current time in seconds, relative to an arbitrary starting point.
Definition: Time.cpp:121
An interface to the operating system, including Port based communication.
Signal processing.
Definition: Image.h:22
The main, catch-all namespace for YARP.
Definition: dirs.h:16