49 std::lock_guard<std::mutex> lock(m_mutex);
50 if (
id >= 0 && (
size_t)
id < m_transforms.size())
52 m_transforms.erase(m_transforms.begin() +
id);
60 std::lock_guard<std::mutex> lock(m_mutex);
61 for (
auto& m_transform : m_transforms)
64 if (m_transform.dst_frame_id ==
t.dst_frame_id && m_transform.src_frame_id ==
t.src_frame_id)
73 m_transforms.push_back(
t);
79 std::lock_guard<std::mutex> lock(m_mutex);
80 if (t1==
"*" && t2==
"*")
88 for (
size_t i = 0; i < m_transforms.size(); )
91 if (m_transforms[i].dst_frame_id == t2)
93 m_transforms.erase(m_transforms.begin() + i);
106 for (
size_t i = 0; i < m_transforms.size(); )
109 if (m_transforms[i].src_frame_id == t1)
111 m_transforms.erase(m_transforms.begin() + i);
123 for (
size_t i = 0; i < m_transforms.size(); i++)
125 if ((m_transforms[i].dst_frame_id == t1 && m_transforms[i].src_frame_id == t2) ||
126 (m_transforms[i].dst_frame_id == t2 && m_transforms[i].src_frame_id == t1) )
128 m_transforms.erase(m_transforms.begin() + i);
138 std::lock_guard<std::mutex> lock(m_mutex);
139 m_transforms.clear();
149 m_enable_publish_ros_tf =
false;
150 m_enable_subscribe_ros_tf =
false;
151 m_yarp_static_transform_storage =
nullptr;
152 m_yarp_timed_transform_storage =
nullptr;
153 m_ros_static_transform_storage =
nullptr;
154 m_ros_timed_transform_storage =
nullptr;
156 m_FrameTransformTimeout = 0.200;
162 if (m_yarp_static_transform_storage)
164 delete m_yarp_static_transform_storage;
165 m_yarp_static_transform_storage =
nullptr;
167 if (m_yarp_timed_transform_storage)
169 delete m_yarp_timed_transform_storage;
170 m_yarp_timed_transform_storage =
nullptr;
172 if (m_ros_timed_transform_storage)
174 delete m_ros_timed_transform_storage;
175 m_ros_timed_transform_storage =
nullptr;
177 if (m_ros_static_transform_storage)
179 delete m_ros_static_transform_storage;
180 m_ros_static_transform_storage =
nullptr;
186 std::vector<Transforms_server_storage*> storages;
187 std::vector<string> storageDescription;
188 storages.push_back(m_ros_timed_transform_storage);
189 storageDescription.emplace_back(
"ros timed transforms");
191 storages.push_back(m_ros_static_transform_storage);
192 storageDescription.emplace_back(
"ros static transforms");
194 storages.push_back(m_yarp_timed_transform_storage);
195 storageDescription.emplace_back(
"yarp timed transforms");
197 storages.push_back(m_yarp_static_transform_storage);
198 storageDescription.emplace_back(
"yarp static transforms");
200 if (storages[0]->size() == 0 &&
201 storages[1]->size() == 0 &&
202 storages[2]->size() == 0 &&
203 storages[3]->size() == 0)
209 for(
size_t s = 0; s < storages.size(); s++ )
216 std::string text_to_print = storageDescription[s] + std::string(
"(") +std::to_string(storages[s]->size())+ std::string(
"): ");
219 for(
size_t i = 0; i < storages[s]->size(); i++)
229 std::lock_guard<std::mutex> lock(m_mutex);
232 bool ok = in.
read(connection);
233 if (!ok)
return false;
247 yCError(FRAMETRANSFORMSERVER) <<
"read(): Protocol error";
284 yCError(FRAMETRANSFORMSERVER) <<
"read(): Something strange happened";
290 m_yarp_timed_transform_storage->
clear();
291 m_yarp_static_transform_storage->
clear();
292 m_ros_timed_transform_storage->
clear();
293 m_ros_static_transform_storage->
clear();
301 bool ret1 = m_yarp_timed_transform_storage->
delete_transform(frame1, frame2);
309 bool ret2 = m_yarp_static_transform_storage->
delete_transform(frame1, frame2);
320 yCError(FRAMETRANSFORMSERVER,
"Invalid vocab received");
325 else if(request ==
"help")
328 out.
addString(
"'list': get all transforms stored");
329 out.
addString(
"'delete_all': delete all transforms");
330 out.
addString(
"'set_static_transform <src> <dst> <x> <y> <z> <roll> <pitch> <yaw>': create a static transform");
331 out.
addString(
"'delete_static_transform <src> <dst>': delete a static transform");
333 else if (request ==
"set_static_transform")
346 yCInfo(FRAMETRANSFORMSERVER) <<
"set_static_transform done";
347 out.
addString(
"set_static_transform done");
351 yCError(FRAMETRANSFORMSERVER) <<
"read(): something strange happened";
354 else if(request ==
"delete_all")
356 m_yarp_timed_transform_storage->
clear();
357 m_yarp_static_transform_storage->
clear();
358 m_ros_timed_transform_storage->
clear();
359 m_ros_static_transform_storage->
clear();
360 yCInfo(FRAMETRANSFORMSERVER) <<
"delete_all done";
363 else if (request ==
"list")
368 else if (request ==
"delete_static_transform")
374 out.
addString(
"delete_static_transform done");
378 yCError(FRAMETRANSFORMSERVER,
"Invalid vocab received");
384 if (returnToSender !=
nullptr)
386 out.
write(*returnToSender);
390 yCError(FRAMETRANSFORMSERVER) <<
"Invalid return to sender";
398 if (!m_rpcPort.
open(m_rpcPortName))
400 yCError(FRAMETRANSFORMSERVER,
"Failed to open port %s", m_rpcPortName.c_str());
406 if (!m_streamingPort.
open(m_streamingPortName))
408 yCError(FRAMETRANSFORMSERVER,
"Failed to open port %s", m_streamingPortName.c_str());
413 if (m_enable_publish_ros_tf)
415 if (m_rosNode ==
nullptr)
421 yCError(FRAMETRANSFORMSERVER) <<
"Unable to publish data on " <<
ROSTOPICNAME_TF <<
" topic, check your yarp-ROS network configuration";
426 yCError(FRAMETRANSFORMSERVER) <<
"Unable to publish data on " <<
ROSTOPICNAME_TF_STATIC <<
" topic, check your yarp-ROS network configuration";
432 if (m_enable_subscribe_ros_tf)
434 if (m_rosNode ==
nullptr)
440 yCError(FRAMETRANSFORMSERVER) <<
"Unable to subscribe to " <<
ROSTOPICNAME_TF <<
" topic, check your yarp-ROS network configuration";
443 m_rosSubscriberPort_tf_timed.
setStrict();
449 m_rosSubscriberPort_tf_static.
setStrict();
458 yCInfo(FRAMETRANSFORMSERVER) <<
"Transform server started";
465 if (config.
check(
"USER_TF"))
470 for (
size_t i = 0; i < all_transforms_group.
size(); i++)
477 yCError(FRAMETRANSFORMSERVER) <<
"No entries in USER_TF group";
486 for(
int i = 0; i < 16; i++)
490 yCError(FRAMETRANSFORMSERVER) <<
"transformServer: element " << i <<
" is not a double.";
506 yCError(FRAMETRANSFORMSERVER) <<
"transformServer: param not correct.. for the 4x4 matrix mode" <<
507 "you must provide 18 parameter. the matrix, the source frame(string) and the destination frame(string)";
515 else if( b->
size() == 8 &&
532 yCError(FRAMETRANSFORMSERVER) <<
"transformServer: param not correct.. a tf requires 8 param in the format:" <<
533 "x(dbl) y(dbl) z(dbl) r(dbl) p(dbl) y(dbl) src(str) dst(str)";
539 yCInfo(FRAMETRANSFORMSERVER) <<
"Transform from" <<
t.src_frame_id <<
"to" <<
t.dst_frame_id <<
"successfully set";
543 yCInfo(FRAMETRANSFORMSERVER) <<
"Unbale to set transform from " <<
t.src_frame_id <<
"to" <<
t.dst_frame_id;
550 yCInfo(FRAMETRANSFORMSERVER) <<
"No starting tf found";
560 if (!config.
check(
"period"))
566 m_period = config.
find(
"period").
asInt32() / 1000.0;
567 yCInfo(FRAMETRANSFORMSERVER) <<
"Thread period set to:" << m_period;
570 if (config.
check(
"transforms_lifetime"))
572 m_FrameTransformTimeout = config.
find(
"transforms_lifetime").
asFloat64();
573 yCInfo(FRAMETRANSFORMSERVER) <<
"transforms_lifetime set to:" << m_FrameTransformTimeout;
577 if (!config.
check(
"name"))
579 name =
"transformServer";
585 m_streamingPortName =
"/"+ name +
"/transforms:o";
586 m_rpcPortName =
"/" + name +
"/rpc";
589 if (!config.
check(
"ROS"))
591 yCError(FRAMETRANSFORMSERVER) <<
"Missing ROS group";
595 if (ROS_config.
check(
"enable_ros_publisher") ==
false)
597 yCError(FRAMETRANSFORMSERVER) <<
"Missing 'enable_ros_publisher' in ROS group";
600 if (ROS_config.
find(
"enable_ros_publisher").
asInt32() == 1 || ROS_config.
find(
"enable_ros_publisher").
asString() ==
"true")
602 m_enable_publish_ros_tf =
true;
603 yCInfo(FRAMETRANSFORMSERVER) <<
"Enabled ROS publisher";
605 if (ROS_config.
check(
"enable_ros_subscriber") ==
false)
607 yCError(FRAMETRANSFORMSERVER) <<
"Missing 'enable_ros_subscriber' in ROS group";
610 if (ROS_config.
find(
"enable_ros_subscriber").
asInt32() == 1 || ROS_config.
find(
"enable_ros_subscriber").
asString() ==
"true")
612 m_enable_subscribe_ros_tf =
true;
613 yCInfo(FRAMETRANSFORMSERVER) <<
"Enabled ROS subscriber";
619 parseStartingTf(config);
627 m_streamingPort.
close();
630 if (m_enable_publish_ros_tf)
633 m_rosPublisherPort_tf_timed.
close();
635 if (m_enable_subscribe_ros_tf)
637 m_rosSubscriberPort_tf_timed.
interrupt();
638 m_rosSubscriberPort_tf_timed.
close();
640 if (m_enable_publish_ros_tf)
642 m_rosPublisherPort_tf_static.
interrupt();
643 m_rosPublisherPort_tf_static.
close();
645 if (m_enable_subscribe_ros_tf)
647 m_rosSubscriberPort_tf_static.
interrupt();
648 m_rosSubscriberPort_tf_static.
close();
660 std::lock_guard<std::mutex> lock(m_mutex);
669 repeat_check =
false;
670 size_t tfVecSize_timed_yarp = m_yarp_timed_transform_storage->
size();
671 for (
size_t i = 0; i < tfVecSize_timed_yarp; i++)
673 if (current_time - (*m_yarp_timed_transform_storage)[i].timestamp > m_FrameTransformTimeout)
681 while (repeat_check);
686 repeat_check =
false;
687 size_t tfVecSize_timed_ros = m_ros_timed_transform_storage->
size();
688 for (
size_t i = 0; i < tfVecSize_timed_ros; i++)
690 if (current_time - (*m_ros_timed_transform_storage)[i].timestamp > m_FrameTransformTimeout)
697 }
while (repeat_check);
700 if (m_enable_subscribe_ros_tf)
705 rosInData_timed = m_rosSubscriberPort_tf_timed.
read(
false);
706 if (rosInData_timed !=
nullptr)
708 std::vector <yarp::rosmsg::geometry_msgs::TransformStamped> tfs = rosInData_timed->
transforms;
709 size_t tfs_size = tfs.size();
710 for (
size_t i = 0; i < tfs_size; i++)
713 t.translation.tX = tfs[i].transform.translation.x;
714 t.translation.tY = tfs[i].transform.translation.y;
715 t.translation.tZ = tfs[i].transform.translation.z;
716 t.rotation.x() = tfs[i].transform.rotation.x;
717 t.rotation.y() = tfs[i].transform.rotation.y;
718 t.rotation.z() = tfs[i].transform.rotation.z;
719 t.rotation.w() = tfs[i].transform.rotation.w;
720 t.src_frame_id = tfs[i].header.frame_id;
721 t.dst_frame_id = tfs[i].child_frame_id;
725 (*m_ros_timed_transform_storage).set_transform(
t);
728 }
while (rosInData_timed !=
nullptr);
733 rosInData_static = m_rosSubscriberPort_tf_static.
read(
false);
734 if (rosInData_static !=
nullptr)
736 std::vector <yarp::rosmsg::geometry_msgs::TransformStamped> tfs = rosInData_static->
transforms;
737 size_t tfs_size = tfs.size();
738 for (
size_t i = 0; i < tfs_size; i++)
741 t.translation.tX = tfs[i].transform.translation.x;
742 t.translation.tY = tfs[i].transform.translation.y;
743 t.translation.tZ = tfs[i].transform.translation.z;
744 t.rotation.x() = tfs[i].transform.rotation.x;
745 t.rotation.y() = tfs[i].transform.rotation.y;
746 t.rotation.z() = tfs[i].transform.rotation.z;
747 t.rotation.w() = tfs[i].transform.rotation.w;
748 t.src_frame_id = tfs[i].header.frame_id;
749 t.dst_frame_id = tfs[i].child_frame_id;
753 (*m_ros_static_transform_storage).set_transform(
t);
756 }
while (rosInData_static !=
nullptr);
760 m_lastStateStamp.
update();
761 size_t tfVecSize_static_yarp = m_yarp_static_transform_storage->
size();
762 size_t tfVecSize_timed_yarp = m_yarp_timed_transform_storage->
size();
763 size_t tfVecSize_static_ros = m_ros_static_transform_storage->
size();
764 size_t tfVecSize_timed_ros = m_ros_timed_transform_storage->
size();
766 yCDebug(FRAMETRANSFORMSERVER) <<
"yarp size" << tfVecSize_yarp <<
"ros_size" << tfVecSize_ros;
771 for (
size_t i = 0; i < tfVecSize_static_yarp; i++)
774 transform.
addString((*m_yarp_static_transform_storage)[i].src_frame_id);
775 transform.
addString((*m_yarp_static_transform_storage)[i].dst_frame_id);
776 transform.
addFloat64((*m_yarp_static_transform_storage)[i].timestamp);
778 transform.
addFloat64((*m_yarp_static_transform_storage)[i].translation.tX);
779 transform.
addFloat64((*m_yarp_static_transform_storage)[i].translation.tY);
780 transform.
addFloat64((*m_yarp_static_transform_storage)[i].translation.tZ);
782 transform.
addFloat64((*m_yarp_static_transform_storage)[i].rotation.w());
783 transform.
addFloat64((*m_yarp_static_transform_storage)[i].rotation.x());
784 transform.
addFloat64((*m_yarp_static_transform_storage)[i].rotation.y());
785 transform.
addFloat64((*m_yarp_static_transform_storage)[i].rotation.z());
787 for (
size_t i = 0; i < tfVecSize_timed_yarp; i++)
790 transform.
addString((*m_yarp_timed_transform_storage)[i].src_frame_id);
791 transform.
addString((*m_yarp_timed_transform_storage)[i].dst_frame_id);
792 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].timestamp);
794 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].translation.tX);
795 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].translation.tY);
796 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].translation.tZ);
798 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].rotation.w());
799 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].rotation.x());
800 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].rotation.y());
801 transform.
addFloat64((*m_yarp_timed_transform_storage)[i].rotation.z());
803 for (
size_t i = 0; i < tfVecSize_timed_ros; i++)
806 transform.
addString((*m_ros_timed_transform_storage)[i].src_frame_id);
807 transform.
addString((*m_ros_timed_transform_storage)[i].dst_frame_id);
808 transform.
addFloat64((*m_ros_timed_transform_storage)[i].timestamp);
810 transform.
addFloat64((*m_ros_timed_transform_storage)[i].translation.tX);
811 transform.
addFloat64((*m_ros_timed_transform_storage)[i].translation.tY);
812 transform.
addFloat64((*m_ros_timed_transform_storage)[i].translation.tZ);
814 transform.
addFloat64((*m_ros_timed_transform_storage)[i].rotation.w());
815 transform.
addFloat64((*m_ros_timed_transform_storage)[i].rotation.x());
816 transform.
addFloat64((*m_ros_timed_transform_storage)[i].rotation.y());
817 transform.
addFloat64((*m_ros_timed_transform_storage)[i].rotation.z());
819 for (
size_t i = 0; i < tfVecSize_static_ros; i++)
822 transform.
addString((*m_ros_static_transform_storage)[i].src_frame_id);
823 transform.
addString((*m_ros_static_transform_storage)[i].dst_frame_id);
824 transform.
addFloat64((*m_ros_static_transform_storage)[i].timestamp);
826 transform.
addFloat64((*m_ros_static_transform_storage)[i].translation.tX);
827 transform.
addFloat64((*m_ros_static_transform_storage)[i].translation.tY);
828 transform.
addFloat64((*m_ros_static_transform_storage)[i].translation.tZ);
830 transform.
addFloat64((*m_ros_static_transform_storage)[i].rotation.w());
831 transform.
addFloat64((*m_ros_static_transform_storage)[i].rotation.x());
832 transform.
addFloat64((*m_ros_static_transform_storage)[i].rotation.y());
833 transform.
addFloat64((*m_ros_static_transform_storage)[i].rotation.z());
837 m_streamingPort.
write();
840 if (m_enable_publish_ros_tf)
842 static int rosMsgCounter = 0;
846 for (
size_t i = 0; i < tfVecSize_timed_yarp; i++)
848 transform_timed.
child_frame_id = (*m_yarp_timed_transform_storage)[i].dst_frame_id;
849 transform_timed.
header.
frame_id = (*m_yarp_timed_transform_storage)[i].src_frame_id;
850 transform_timed.
header.
seq = rosMsgCounter;
851 transform_timed.
header.
stamp = (*m_yarp_timed_transform_storage)[i].timestamp;
852 transform_timed.
transform.
rotation.
x = (*m_yarp_timed_transform_storage)[i].rotation.x();
853 transform_timed.
transform.
rotation.
y = (*m_yarp_timed_transform_storage)[i].rotation.y();
854 transform_timed.
transform.
rotation.
z = (*m_yarp_timed_transform_storage)[i].rotation.z();
855 transform_timed.
transform.
rotation.
w = (*m_yarp_timed_transform_storage)[i].rotation.w();
860 rosOutData_timed.
transforms.push_back(transform_timed);
862 m_rosPublisherPort_tf_timed.
write();
867 for (
size_t i = 0; i < tfVecSize_static_yarp; i++)
869 transform_static.
child_frame_id = (*m_yarp_static_transform_storage)[i].dst_frame_id;
870 transform_static.
header.
frame_id = (*m_yarp_static_transform_storage)[i].src_frame_id;
871 transform_static.
header.
seq = rosMsgCounter;
873 transform_static.
transform.
rotation.
x = (*m_yarp_static_transform_storage)[i].rotation.x();
874 transform_static.
transform.
rotation.
y = (*m_yarp_static_transform_storage)[i].rotation.y();
875 transform_static.
transform.
rotation.
z = (*m_yarp_static_transform_storage)[i].rotation.z();
876 transform_static.
transform.
rotation.
w = (*m_yarp_static_transform_storage)[i].rotation.w();
881 rosOutData_static.
transforms.push_back(transform_static);
883 m_rosPublisherPort_tf_static.
write();
891 yCError(FRAMETRANSFORMSERVER,
"Returned error");
897 yCTrace(FRAMETRANSFORMSERVER,
"Close");
898 if (PeriodicThread::isRunning())
900 PeriodicThread::stop();
#define DEFAULT_THREAD_PERIOD
define control board standard interfaces
constexpr yarp::conf::vocab32_t VOCAB_OK
constexpr yarp::conf::vocab32_t VOCAB_FAILED
constexpr yarp::conf::vocab32_t VOCAB_ERR
A simple collection of objects that can be described and transmitted in a portable way.
Bottle & addList()
Places an empty nested list in the bottle, at the end of the list.
size_type size() const
Gets the number of elements in the bottle.
bool read(ConnectionReader &reader) override
Set the bottle's value based on input from a network connection.
void addFloat64(yarp::conf::float64_t x)
Places a 64-bit floating point number in the bottle, at the end of the list.
void addVocab(int x)
Places a vocabulary item in the bottle, at the end of the list.
Value & get(size_type index) const
Reads a Value v from a certain part of the list.
bool check(const std::string &key) const override
Check if there exists a property of the given name.
Bottle tail() const
Get all but the first element of a bottle.
void clear()
Empties the bottle of any objects it contains.
bool write(ConnectionWriter &writer) const override
Output a representation of the bottle to a network connection.
void addString(const char *str)
Places a string in the bottle, at the end of the list.
std::string toString() const override
Gives a human-readable textual representation of the bottle.
Value & find(const std::string &key) const override
Gets a value corresponding to a given keyword.
void close() override
Stop port activity.
bool setEnvelope(PortWriter &envelope) override
Set an envelope (e.g., a timestamp) to the next message which will be sent.
bool open(const std::string &name) override
Start port operation, with a specific name, with automatically-chosen network parameters.
void interrupt() override
Interrupt any current reads or writes attached to the port.
void write(bool forceStrict=false)
Write the current object being returned by BufferedPort::prepare.
T & prepare()
Access the object which will be transmitted by the next call to yarp::os::BufferedPort::write.
An interface for reading from a network connection.
virtual ConnectionWriter * getWriter()=0
Gets a way to reply to the message, if possible.
An interface for writing to a network connection.
void interrupt()
interrupt delegates the call to the Node port interrupt.
An abstraction for a periodic thread.
bool start()
Call this to start the thread.
A class for storing options and configuration information.
void fromString(const std::string &txt, bool wipe=true)
Interprets a string as a list of properties.
void close() override
Stop port activity.
bool topic(const std::string &name)
Set topic to publish to.
T & prepare()
Access the object which will be transmitted by the next call to yarp::os::Publisher::write.
void interrupt() override
Interrupt any current reads or writes attached to the port.
void write(bool forceStrict=false)
Write the current object being returned by Publisher::prepare.
A base class for nested structures that can be searched.
virtual Value & find(const std::string &key) const =0
Gets a value corresponding to a given keyword.
virtual bool check(const std::string &key) const =0
Check if there exists a property of the given name.
virtual std::string toString() const =0
Return a standard text representation of the content of the object.
virtual Bottle & findGroup(const std::string &key) const =0
Gets a list corresponding to a given keyword.
void update()
Set the timestamp to the current time, and increment the sequence number (wrapping to 0 if the sequen...
void close() override
Stop port activity.
T * read(bool shouldWait=true)
Read a message from the port.
void setStrict(bool strict=true)
bool topic(const std::string &name)
Set topic to subscribe to.
void interrupt() override
Interrupt any current reads or writes attached to the port.
virtual yarp::conf::float64_t asFloat64() const
Get 64-bit floating point value.
virtual bool isString() const
Checks if value is a string.
virtual std::int32_t asInt32() const
Get 32-bit integer value.
virtual Bottle * asList() const
Get list value.
virtual bool isFloat64() const
Checks if value is a 64-bit floating point number.
virtual std::int32_t asVocab() const
Get vocabulary identifier as an integer.
virtual std::string asString() const
Get string value.
std::vector< yarp::rosmsg::geometry_msgs::TransformStamped > transforms
std::string toString(const T &value)
convert an arbitrary type to string.
#define yCInfo(component,...)
#define yCError(component,...)
#define yCTrace(component,...)
#define yCDebug(component,...)
#define YARP_LOG_COMPONENT(name,...)
An interface for the device drivers.
double now()
Return the current time in seconds, relative to an arbitrary starting point.
void delay(double seconds)
Wait for a certain number of seconds.
NetInt32 encode(const std::string &str)
Convert a string into a vocabulary identifier.
An interface to the operating system, including Port based communication.