-
Notifications
You must be signed in to change notification settings - Fork 373
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Simulation time for message headers #91
Comments
Hi @samiamlabs ! Very nice videos! Would you like to drop some lines on what you are working on here #20 , togehter with your video links? I'd like to learn more about what improvement you suggest / what you want to achieve:
|
I will probably have some videos that make easier to understand what I'm trying to at the end of this week. I can post them at that time. I'm referring to ROS simulation time in the title, not Unity simulation time. The concepts are very similar though. You can read about ROS simulation time here: http://wiki.ros.org/Clock. The basic idea is to enable you to speed up or slow down your entire ROS system. In the case of using a source for /clock in ROS (not Unity Simulation Time) you would need to keep track of the slow-down/speed-up factor and update https://docs.unity3d.com/ScriptReference/Time-timeScale.html accordingly. ROS nodes will use simulation time if the rosparam /use_sim_time parameter is set. For real robots, wall time should be used so you should synchronize all computers the same time server if possible. I will be putting vive trackers on real robots for localization and visualization at some point. Will probably need wall-time header stamps in message headers then. The reason I need accurate headers for sensor data is that I make pretty heavy use of tf (http://wiki.ros.org/tf) in order to do things like track objects in the world/map frame while the robot is moving. For this reason, i need accurate timestamps and appropriate frame_id:s. Rosbridge_suit just sets the fame_id filed to "" if I understand correctly. I don't know how often rosbrigde drops messages when under heavy load (several simulated 3d cameras for example). All the ROS nodes will freeze up (get stuck in sleep functions) if they don't receive times on the /clock topic (and /use_sim_time is set). I also have some concerns about shifting ping between simulation computer and ROS computer causing problems with tf. I would be less concerned about publishing /clock from Unity if ros-sharp was using DDS (https://en.wikipedia.org/wiki/Data_Distribution_Service) instead of websockets. Possibly https://github.com/ros2/ros1_bridge and https://github.com/firesurfer/rclcs could be an option, but I think they are still fairly experimental. I guess it might be smart to try to publish /clock from Unity in FixedUpdate and determine if it works for my applications before implementing more complicated time synchronization. As for implementation, here is how they solved it for SIGVerse: https://github.com/PartnerRobotChallengeVirtual/common-unity/blob/master/Assets/SIGVerse/Common/ROSBridge/SIGVerseRosBridgeTimeSynchronizer.cs I think the best solution I thought of so far is make something like a get_current_unity_time service provider/server in Unity and have a ros node request time at set intervals (measuring roundtrip). The ROS node can then publish the synchronized time on the ROS computer. In that case the StandardHeaderExtension should work as is for simulation time and only need to be updated to support wall time for real robots. It would also make it easy to implement a slider for speeding up and slowing down the simulation in Unity and ROS simultaneously. |
Upon further reflection, I think I will implement this on my own fork and make a pull request if I want it on the main master branch. If implemented as I suggested at the end of the last comment, there should not be any breaking changes. Should I close the issue? |
That's a good @samiamlabs . We should refer to this discussion in your pull reqest. Fell free to close it or to keep it open for further discussions in the meantime. |
Some updates on this issue:I wanted a replacement for gazebos planar move plugin that works with the navigation stack and SLAM (TEB and cartographer in my case), so I implemented a general purpose rigidbody based twist subscriber and odom publisher in Unity. As I expected, both cartographer and the local planner were very sensitive to correct timestamps. Was not able to get it working by publishing /clock directly from unity. The approach I used for the forklift, where i subscribed to /clock from ROS for timestamps did not work either because of complications related to publishing odom from Unity. I implemented a sync node in ROS and finally got it working:(https://github.com/samiamlabs/dyno/blob/master/dyno_unity/src/clock_sync.cpp) I used i simplified version the approach I mentioned at the end of my last comment with unity time from UnityEngine.Time.realtimeSinceStartup. Unfortunately, ROS simulation time can't move backwards without all ROS nodes that use ROS-based sleep() methods throwing exceptions. This means that if you restart Unity you have to wait for simulation time to reach its previous largest value before ROS starts working again. I was enjoying the ability to restart Unity without restarting ROS so I think I will try to find a way to properly sync Unity time with /clock published by ROS instead after all... at some point... |
Thank you again for the impressive videos about your ROS# application and also for your initiative to improve the timing between ROS and Unity! It is possible to implement an own timer in Unity e.g. by using Physics.Simulate() and Physics.autoSimulation(). This will solve the problem you reported above. How shall we proceed with this issue? Are you planning to work on this topic in the future? In case you consider your work done (for the time being), I'd suggest to close the issue. |
The main problem is that nodes that use TF can be very sensitive when it comes to timestamps. I found that it is pretty difficult to keep ROS and Unity properly synchronized so that all the navigation and localization systems work as they should I made enough progress so that it is usable for my purposes with my on clock-sync-system, but it is far from perfect. I have some more advanced simulation scenarios that I am planning to implement, but I think I will attempt to use ROS2 and https://github.com/firesurfer/rclcs for most of that. My attempt at clock-sync can be found in the links below in case anyone is interested: Closing the issue is fine with me :) |
Thank you for the update and for sharing these infos and your work. |
I have a feature request!
I want to do this:
Have a standard way of updating message headers with correct timestamps.
For being able to do it, I wish ROS# had the following feature:
Possibly a RosBridgeClient.time.now() or an improvement of StandardHeaderExtensions that uses a clock synchronized with the /clock topic (published by a ROS node).
Alternatively, ros-sharp should publish its own clock on /clock. I have some concerns about the stability of this though...
I implemented a ClockSubscriber in order to get a laser scan from Unity to work with Cartographer:
It seems to me that it would be good to have this as standard functionality in ros-sharp.
I currently set the roundtrip delay manually, but it would be better to measure it...
Here is a bonus video of the ROS navigation stack and Cartograper working with ros-sharp.
The text was updated successfully, but these errors were encountered: