Merge lp:~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte into lp:sr-ros-interface/fuerte

Proposed by Toni Oliver
Status: Merged
Merged at revision: 397
Proposed branch: lp:~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte
Merge into: lp:sr-ros-interface/fuerte
Diff against target: 676 lines (+379/-39)
14 files modified
.bzrignore (+2/-0)
sr_hand/CMakeLists.txt (+12/-0)
sr_hand/include/sr_hand/hand_commander.h (+89/-0)
sr_hand/manifest.xml (+2/-1)
sr_hand/src/hand_commander.cpp (+121/-0)
sr_hand/test/hand_commander_test.cpp (+25/-0)
sr_hand/test/hand_commander_test.launch (+3/-0)
sr_move_arm/CMakeLists.txt (+2/-0)
sr_move_arm/bin/test/hand_posture_execution_test (+69/-0)
sr_move_arm/include/sr_move_arm/hand_posture_execution.hpp (+3/-4)
sr_move_arm/manifest.xml (+2/-0)
sr_move_arm/src/hand_posture_execution.cpp (+23/-15)
sr_move_arm/src/reactive_actions/reactive_grasp.py (+19/-19)
sr_move_arm/test/hand_posture_execution_test.launch (+7/-0)
To merge this branch: bzr merge lp:~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte
Reviewer Review Type Date Requested Status
Ugo Approve
markpitchless Pending
Review via email: mp+133688@code.launchpad.net

Commit message

Created a new cpp library to allow to send targets to both CAN and ethercat hand, with any controllers running. sr_move_arm/hand_posture_execution is now using this library. Adapted reactive_grasp to use the shadowhand_ros.py library instead of publishing directly the commands. This allows to use the ethercat hand without launching the separate compatibility node.

Description of the change

Created a new cpp library to allow to send targets to both CAN and ethercat hand, with any controllers running. sr_move_arm/hand_posture_execution is now using this library. Adapted reactive_grasp to use the shadowhand_ros.py library instead of publishing directly the commands. This allows to use the ethercat hand without launching the separate compatibility node.

https://app.asana.com/0/1470949453683/2390846818451

To post a comment you must log in.
Revision history for this message
markpitchless (markpitchless) wrote :
396. By markpitchless

Rename ShadowhandRos to HandCommander.

397. By markpitchless

Start a test. Fails at the moment.

398. By markpitchless

Fix the test, we need to be a node.

399. By markpitchless

Convert to a test that launches nodes.

400. By markpitchless

Use size_t

401. By markpitchless

Cleanup for better readability.

402. By markpitchless

Send updates after ethercat init.

403. By markpitchless

Update sr_arm_move to use renamed shadowrobot::HandCommander

404. By markpitchless

Fix and test hand posture action server.

* Fixed bug with joint names on pre and grasp requests.
* Added a basic rostest.

Revision history for this message
Ugo (ugocupcic) wrote :

Don't use #define (ever), use static const.

review: Needs Fixing
Revision history for this message
Ugo (ugocupcic) wrote :

Do you mind if we name the cpp header files *.hpp ?? This way I have a different mode in emacs for C headers (.h) and C++ headers (.hpp)...

Revision history for this message
Ugo (ugocupcic) wrote :

Excellent use of boost::ptr_map!

Revision history for this message
Ugo (ugocupcic) wrote :

Why is hand_posture_execution_test in sr_move_arm/bin/test and not in /test? It seems a bit confusing (I usually wipe bin)

Revision history for this message
Ugo (ugocupcic) wrote :

> Don't use #define (ever), use static const.

I fixed it.

Revision history for this message
Ugo (ugocupcic) wrote :

The test is failing here :S was it working for you??

review: Needs Fixing
Revision history for this message
markpitchless (markpitchless) wrote :

> Why is hand_posture_execution_test in sr_move_arm/bin/test and not in /test?
> It seems a bit confusing (I usually wipe bin)

That is where the ros wiki tutorials on rostest tell you to put them. The add exe commands in the cmake file for the test are still relative to bin/

Revision history for this message
markpitchless (markpitchless) wrote :

> The test is failing here :S was it working for you??

Damn. Yes, both the tests I added passed. Which test and what the error?

Revision history for this message
Ugo (ugocupcic) wrote :

OK thanks for this

On Wed, Nov 14, 2012 at 11:53 AM, markpitchless <email address hidden>wrote:

> > Why is hand_posture_execution_test in sr_move_arm/bin/test and not in
> /test?
> > It seems a bit confusing (I usually wipe bin)
>
> That is where the ros wiki tutorials on rostest tell you to put them. The
> add exe commands in the cmake file for the test are still relative to bin/
> --
>
> https://code.launchpad.net/~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte/+merge/133688
> You are reviewing the proposed merge of
> lp:~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte into
> lp:sr-ros-interface/fuerte.
>

--
Ugo Cupcic | Shadow Robot Company | <email address hidden>
Senior Software Engineer | 251 Liverpool Road |
need a Hand? | London N1 1LX | +44 20 7700 2487
http://www.shadowrobot.com/hand/ @shadowrobot

Revision history for this message
markpitchless (markpitchless) wrote :

> Do you mind if we name the cpp header files *.hpp ?? This way I have a
> different mode in emacs for C headers (.h) and C++ headers (.hpp)...

No worries from me.

Revision history for this message
Ugo (ugocupcic) wrote :

Here's the error message;
http://pastebin.com/gQZML6t3

On Wed, Nov 14, 2012 at 11:54 AM, markpitchless <email address hidden>wrote:

> > The test is failing here :S was it working for you??
>
> Damn. Yes, both the tests I added passed. Which test and what the error?
> --
>
> https://code.launchpad.net/~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte/+merge/133688
> You are reviewing the proposed merge of
> lp:~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte into
> lp:sr-ros-interface/fuerte.
>

--
Ugo Cupcic | Shadow Robot Company | <email address hidden>
Senior Software Engineer | 251 Liverpool Road |
need a Hand? | London N1 1LX | +44 20 7700 2487
http://www.shadowrobot.com/hand/ @shadowrobot

405. By Toni Oliver

Increased the time for the gazebo simulated hand to load from 2 s to 15 s which should be enough even for a slow computer.

Revision history for this message
Toni Oliver (toliver-shadow) wrote :

I solved the test failure and pushed, but it's the only thing I did, the rest of modifications (the #define, etc) are still pending.
I increased the time for the gazebo simulated hand to load from 2 s to 15 s which should be enough even for a much slower computer.
We have to admit it Ugo, Mark has a faster computer than me and you.

> Here's the error message;
> http://pastebin.com/gQZML6t3
>
>
> On Wed, Nov 14, 2012 at 11:54 AM, markpitchless
> <email address hidden>wrote:
>
> > > The test is failing here :S was it working for you??
> >
> > Damn. Yes, both the tests I added passed. Which test and what the error?
> > --
> >
> > https://code.launchpad.net/~shadowrobot/sr-ros-
> interface/Feature_ethercat_sr_move_arm_fuerte/+merge/133688
> > You are reviewing the proposed merge of
> > lp:~shadowrobot/sr-ros-interface/Feature_ethercat_sr_move_arm_fuerte into
> > lp:sr-ros-interface/fuerte.
> >
>
>
>
> --
> Ugo Cupcic | Shadow Robot Company | <email address hidden>
> Senior Software Engineer | 251 Liverpool Road |
> need a Hand? | London N1 1LX | +44 20 7700 2487
> http://www.shadowrobot.com/hand/ @shadowrobot

Revision history for this message
Ugo (ugocupcic) wrote :

> > Do you mind if we name the cpp header files *.hpp ?? This way I have a
> > different mode in emacs for C headers (.h) and C++ headers (.hpp)...
>
> No worries from me.
fixed

Revision history for this message
Ugo (ugocupcic) wrote :

OK everything is now fixed and tested. Good job!

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file '.bzrignore'
2--- .bzrignore 2012-10-22 08:48:10 +0000
3+++ .bzrignore 2012-11-14 19:52:22 +0000
4@@ -308,3 +308,5 @@
5 sr_utilities/.pydevproject
6 sr_utilities/cmake_install.cmake
7 sr_mechanism_controllers/_gtest_from_src
8+sr_hand/_gtest_from_src
9+sr_move_arm/bin/hand_posture_execution
10
11=== modified file 'sr_hand/CMakeLists.txt'
12--- sr_hand/CMakeLists.txt 2012-07-23 14:42:29 +0000
13+++ sr_hand/CMakeLists.txt 2012-11-14 19:52:22 +0000
14@@ -157,3 +157,15 @@
15 # EXAMPLES #
16 ###############
17 rosbuild_add_executable(examples/link_joints examples/link_joints.cpp)
18+
19+############################################################################
20+# Hand command library (gives compatibility with CAN and ethercat hand) #
21+############################################################################
22+rosbuild_add_library(HandCommander src/hand_commander.cpp)
23+rosbuild_link_boost(HandCommander thread)
24+SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -pthread")
25+#rosbuild_add_gtest(test/hand_commander_test test/hand_commander_test.cpp)
26+rosbuild_add_executable(test/hand_commander_test test/hand_commander_test.cpp)
27+rosbuild_add_gtest_build_flags(test/hand_commander_test)
28+target_link_libraries(test/hand_commander_test HandCommander)
29+rosbuild_add_rostest(test/hand_commander_test.launch)
30
31=== added directory 'sr_hand/bin/test'
32=== added file 'sr_hand/include/sr_hand/hand_commander.h'
33--- sr_hand/include/sr_hand/hand_commander.h 1970-01-01 00:00:00 +0000
34+++ sr_hand/include/sr_hand/hand_commander.h 2012-11-14 19:52:22 +0000
35@@ -0,0 +1,89 @@
36+/**
37+ * @file hand_commander.h
38+ * @author Toni Oliver <toni@shadowrobot.com>, Contact <contact@shadowrobot.com>
39+ * @date Thu Nov 08 15:34:37 2012
40+ *
41+*
42+* Copyright 2011 Shadow Robot Company Ltd.
43+*
44+* This program is free software: you can redistribute it and/or modify it
45+* under the terms of the GNU General Public License as published by the Free
46+* Software Foundation, either version 2 of the License, or (at your option)
47+* any later version.
48+*
49+* This program is distributed in the hope that it will be useful, but WITHOUT
50+* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
51+* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
52+* more details.
53+*
54+* You should have received a copy of the GNU General Public License along
55+* with this program. If not, see <http://www.gnu.org/licenses/>.
56+*
57+ * @brief This is a library that offers a simple interface to send commands to hand joints.
58+ * It is compatible with the Shadow Robot CAN hand and ethercat hand.
59+ * It allows the user not worry about the name of the currently running controllers.
60+ * Only position control is allowed (targets must represent angles).
61+ *
62+ *
63+ */
64+
65+#pragma once
66+
67+#include <ros/ros.h>
68+#include <vector>
69+#include <string>
70+#include <map>
71+
72+#include <boost/smart_ptr.hpp>
73+#include <boost/ptr_container/ptr_map.hpp>
74+#include <sr_robot_msgs/joint.h>
75+
76+using namespace ros;
77+
78+
79+namespace shadowhandRosLib
80+{
81+ enum HandType
82+ {
83+ UNKNOWN,
84+ CAN,
85+ ETHERCAT
86+ };
87+}
88+
89+namespace shadowrobot
90+{
91+
92+/**
93+ * This ROS subscriber is used to issue commands to the hand / arm, from sending a set of targets, to changing the
94+ * controller parameters.
95+ */
96+class HandCommander
97+{
98+public:
99+ HandCommander();
100+
101+ /// Destructor
102+ ~HandCommander();
103+
104+ void sendCommands(std::vector<sr_robot_msgs::joint> joint_vector);
105+
106+private:
107+ ///ros node handle
108+ NodeHandle node_;
109+ ///Publisher for the CAN hand targets
110+ Publisher sr_hand_target_pub;
111+ ///Publishers for the ethercat hand targets for every joint
112+ boost::ptr_map<std::string,Publisher> sr_hand_target_pub_map;
113+
114+ shadowhandRosLib::HandType hand_type;
115+ bool ethercat_controllers_found;
116+
117+ /**
118+ * init function for the ethercat hand
119+ * It can be called if we know that there's an ethercat hand (pr2_controller_manager running)
120+ */
121+ void initializeEthercatHand();
122+}; // end class ShadowhandSubscriber
123+
124+} // end namespace
125
126=== modified file 'sr_hand/manifest.xml'
127--- sr_hand/manifest.xml 2012-10-19 16:34:36 +0000
128+++ sr_hand/manifest.xml 2012-11-14 19:52:22 +0000
129@@ -19,6 +19,7 @@
130 <depend package="sensor_msgs"/>
131 <depend package="sr_robot_msgs"/>
132 <depend package="pr2_controllers_msgs"/>
133+ <depend package="pr2_mechanism_msgs"/>
134 <depend package="sr_utilities"/>
135 <depend package="diagnostic_msgs"/>
136 <depend package="dynamic_reconfigure"/>
137@@ -28,7 +29,7 @@
138 <depend package="gazebo_msgs"/>
139
140 <export>
141- <cpp cflags="-I${prefix}/include" lflags="-L${prefix}/lib -lSrVirtual"/>
142+ <cpp cflags="-I${prefix}/include" lflags="-L${prefix}/lib -lSrVirtual -lHandCommander"/>
143 <python path="${prefix}/python_lib"/>
144 <python path="${prefix}/python_lib/grasp"/>
145 </export>
146
147=== added file 'sr_hand/src/hand_commander.cpp'
148--- sr_hand/src/hand_commander.cpp 1970-01-01 00:00:00 +0000
149+++ sr_hand/src/hand_commander.cpp 2012-11-14 19:52:22 +0000
150@@ -0,0 +1,121 @@
151+/**
152+ * @file hand_commander.cpp
153+ * @author Toni Oliver <toni@shadowrobot.com>, Contact <contact@shadowrobot.com>
154+ * @date Thu Nov 08 15:34:37 2012
155+ *
156+*
157+* Copyright 2011 Shadow Robot Company Ltd.
158+*
159+* This program is free software: you can redistribute it and/or modify it
160+* under the terms of the GNU General Public License as published by the Free
161+* Software Foundation, either version 2 of the License, or (at your option)
162+* any later version.
163+*
164+* This program is distributed in the hope that it will be useful, but WITHOUT
165+* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
166+* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
167+* more details.
168+*
169+* You should have received a copy of the GNU General Public License along
170+* with this program. If not, see <http://www.gnu.org/licenses/>.
171+*
172+ * @brief This is a library that offers a simple interface to send commands to hand joints.
173+ * It is compatible with the Shadow Robot CAN hand and ethercat hand.
174+ * It allows the user not worry about the name of the currently running controllers.
175+ * Only position control is allowed (targets must represent angles).
176+ *
177+ *
178+ */
179+
180+#include <sr_hand/hand_commander.h>
181+#include <pr2_mechanism_msgs/ListControllers.h>
182+#include <sr_robot_msgs/sendupdate.h>
183+#include <std_msgs/Float64.h>
184+
185+
186+namespace shadowrobot
187+{
188+
189+#define TIMEOUT_TO_DETECT_CONTROLLER_MANAGER 3.0
190+
191+HandCommander::HandCommander():
192+ hand_type(shadowhandRosLib::UNKNOWN),
193+ ethercat_controllers_found(false)
194+{
195+ //We use the presence of the pr2_controller_manager/list_controllers service to detect that the hand is ethercat
196+ if(ros::service::waitForService("pr2_controller_manager/list_controllers", ros::Duration(TIMEOUT_TO_DETECT_CONTROLLER_MANAGER)))
197+ {
198+ hand_type = shadowhandRosLib::ETHERCAT;
199+ initializeEthercatHand();
200+ ROS_INFO("HandCommander library: ETHERCAT hand detected");
201+ }
202+ else
203+ {
204+ hand_type = shadowhandRosLib::CAN;
205+ sr_hand_target_pub = node_.advertise<sr_robot_msgs::sendupdate>("/srh/sendupdate", 2);
206+ ROS_INFO("HandCommander library: CAN hand detected");
207+ }
208+}
209+
210+HandCommander::~HandCommander()
211+{
212+}
213+
214+void HandCommander::initializeEthercatHand()
215+{
216+ sr_hand_target_pub_map.clear();
217+
218+ ros::ServiceClient controller_list_client = node_.serviceClient<pr2_mechanism_msgs::ListControllers>("pr2_controller_manager/list_controllers");
219+
220+ pr2_mechanism_msgs::ListControllers controller_list;
221+ std::string controlled_joint_name;
222+
223+ controller_list_client.call(controller_list);
224+
225+ for (size_t i=0;i<controller_list.response.controllers.size() ;i++ )
226+ {
227+ if(controller_list.response.state[i]=="running")
228+ {
229+ std::string controller = controller_list.response.controllers[i];
230+ if (node_.getParam("/"+controller+"/joint", controlled_joint_name))
231+ {
232+ ROS_DEBUG("controller %d:%s controls joint %s\n",
233+ (int)i,controller.c_str(),controlled_joint_name.c_str());
234+ sr_hand_target_pub_map[controlled_joint_name]
235+ = node_.advertise<std_msgs::Float64>(controller+"/command", 2);
236+ ethercat_controllers_found = true;
237+ }
238+ }
239+ }
240+
241+}
242+
243+void HandCommander::sendCommands(std::vector<sr_robot_msgs::joint> joint_vector)
244+{
245+ if(hand_type == shadowhandRosLib::ETHERCAT)
246+ {
247+ if(!ethercat_controllers_found)
248+ {
249+ initializeEthercatHand();
250+ // No controllers we found so bail out
251+ if (!ethercat_controllers_found)
252+ return;
253+ }
254+ for(size_t i = 0; i < joint_vector.size(); ++i)
255+ {
256+ std_msgs::Float64 target;
257+ target.data = joint_vector.at(i).joint_target * M_PI/180.0;
258+ sr_hand_target_pub_map[joint_vector.at(i).joint_name].publish(target);
259+ }
260+ }
261+ else
262+ {
263+ sr_robot_msgs::sendupdate sendupdate_msg;
264+ sendupdate_msg.sendupdate_length = joint_vector.size();
265+ sendupdate_msg.sendupdate_list = joint_vector;
266+
267+ sr_hand_target_pub.publish(sendupdate_msg);
268+ }
269+}
270+
271+}
272
273=== added directory 'sr_hand/test'
274=== added file 'sr_hand/test/hand_commander_test.cpp'
275--- sr_hand/test/hand_commander_test.cpp 1970-01-01 00:00:00 +0000
276+++ sr_hand/test/hand_commander_test.cpp 2012-11-14 19:52:22 +0000
277@@ -0,0 +1,25 @@
278+
279+// We are testing this
280+#include "sr_hand/hand_commander.h"
281+
282+// ROS
283+#include "ros/ros.h"
284+
285+// Gtest
286+#include <gtest/gtest.h>
287+
288+using namespace shadowrobot;
289+
290+TEST(HandCommander, constructor)
291+{
292+ HandCommander handcmd = HandCommander();
293+ EXPECT_TRUE(true);
294+}
295+
296+int main(int argc, char **argv)
297+{
298+ testing::InitGoogleTest(&argc, argv);
299+ ros::init(argc, argv, "hand_commander_test");
300+ ros::NodeHandle nh; // init the node
301+ return RUN_ALL_TESTS();
302+}
303
304=== added file 'sr_hand/test/hand_commander_test.launch'
305--- sr_hand/test/hand_commander_test.launch 1970-01-01 00:00:00 +0000
306+++ sr_hand/test/hand_commander_test.launch 2012-11-14 19:52:22 +0000
307@@ -0,0 +1,3 @@
308+<launch>
309+ <test test-name="hand_commander_test" pkg="sr_hand" type="hand_commander_test" />
310+</launch>
311
312=== modified file 'sr_move_arm/CMakeLists.txt'
313--- sr_move_arm/CMakeLists.txt 2011-03-04 18:29:05 +0000
314+++ sr_move_arm/CMakeLists.txt 2012-11-14 19:52:22 +0000
315@@ -23,3 +23,5 @@
316
317 rosbuild_add_executable(hand_posture_execution src/hand_posture_execution.cpp)
318 rosbuild_link_boost(hand_posture_execution thread)
319+
320+rosbuild_add_rostest(test/hand_posture_execution_test.launch)
321
322=== added directory 'sr_move_arm/bin'
323=== added directory 'sr_move_arm/bin/test'
324=== added file 'sr_move_arm/bin/test/hand_posture_execution_test'
325--- sr_move_arm/bin/test/hand_posture_execution_test 1970-01-01 00:00:00 +0000
326+++ sr_move_arm/bin/test/hand_posture_execution_test 2012-11-14 19:52:22 +0000
327@@ -0,0 +1,69 @@
328+#! /usr/bin/env python
329+PKG='sr_move_arm'
330+import roslib; roslib.load_manifest(PKG)
331+import rospy
332+import unittest
333+
334+import actionlib
335+from object_manipulation_msgs.msg import *
336+from sensor_msgs.msg import *
337+import math
338+
339+class HandPostureExecutionTest(unittest.TestCase):
340+
341+ def assertJointPos(self, joint_name, ok_pos):
342+ """Test a joints position. Pos is in degrees."""
343+ msg = rospy.wait_for_message('/gazebo/joint_states', JointState, timeout = 3.0)
344+ pos = round(math.degrees(msg.position[msg.name.index(joint_name)]), 0)
345+ self.assertEqual( pos, ok_pos,
346+ "Joint %s is not at position %i degrees, got %i"%(joint_name, ok_pos, pos) )
347+
348+ def test_basic(self):
349+ client = actionlib.SimpleActionClient(
350+ '/right_arm/hand_posture_execution',GraspHandPostureExecutionAction)
351+ client.wait_for_server()
352+
353+ jnames = ['FFJ4', 'FFJ3', 'FFJ0',
354+ 'MFJ4', 'MFJ3', 'MFJ0',
355+ 'RFJ4', 'RFJ3', 'RFJ0',
356+ 'LFJ5', 'LFJ4', 'LFJ3', 'LFJ0',
357+ 'THJ5', 'THJ4', 'THJ3', 'THJ2', 'THJ1']
358+
359+ # We send a pre grasp followed by a grasp to test the 2 flows through
360+ # the action server.
361+ # TODO: Add a release at the end
362+
363+ # Zero the hand
364+ goal = GraspHandPostureExecutionGoal()
365+ goal.goal = GraspHandPostureExecutionGoal.PRE_GRASP
366+ goal.grasp.pre_grasp_posture = JointState()
367+ goal.grasp.pre_grasp_posture.name = jnames
368+ goal.grasp.pre_grasp_posture.position = [0] * len(jnames)
369+ client.send_goal(goal)
370+ client.wait_for_result(rospy.Duration.from_sec(5.0))
371+ # Wait for the move. TODO: Check the action state instead of sleeping
372+ rospy.sleep(10.0)
373+ self.assertJointPos("THJ4", 0)
374+
375+ # Move the thumb in
376+ target_pos = 70 # deg
377+ goal = GraspHandPostureExecutionGoal()
378+ goal.goal = GraspHandPostureExecutionGoal.GRASP
379+ goal.grasp.grasp_posture = JointState()
380+ goal.grasp.grasp_posture.name = jnames
381+ goal.grasp.grasp_posture.position = [0] * len(jnames)
382+ goal.grasp.grasp_posture.position[jnames.index("THJ4")] = math.radians(target_pos)
383+ client.send_goal(goal)
384+ client.wait_for_result(rospy.Duration.from_sec(5.0))
385+ # Wait for the move. TODO: Check the action state instead of sleeping
386+ rospy.sleep(12.0)
387+ self.assertJointPos("THJ4", target_pos)
388+
389+
390+
391+if __name__ == '__main__':
392+ rospy.sleep(15.0) # Dirty little sleep to wait for things to settle
393+ import rostest
394+ rospy.init_node('hand_posture_execution_test')
395+ rostest.rosrun(PKG, 'hand_posture_execution_test', HandPostureExecutionTest)
396+
397
398=== modified file 'sr_move_arm/include/sr_move_arm/hand_posture_execution.hpp'
399--- sr_move_arm/include/sr_move_arm/hand_posture_execution.hpp 2011-11-11 16:04:37 +0000
400+++ sr_move_arm/include/sr_move_arm/hand_posture_execution.hpp 2012-11-14 19:52:22 +0000
401@@ -12,8 +12,8 @@
402
403 #include <ros/ros.h>
404 #include <boost/smart_ptr.hpp>
405-#include <sr_robot_msgs/sendupdate.h>
406 #include <sr_robot_msgs/is_hand_occupied.h>
407+#include <sr_hand/hand_commander.h>
408
409 #include <actionlib/server/simple_action_server.h>
410 #include <object_manipulation_msgs/GraspHandPostureExecutionAction.h>
411@@ -41,10 +41,9 @@
412
413 boost::shared_ptr<actionlib::SimpleActionServer<object_manipulation_msgs::GraspHandPostureExecutionAction> > action_server;
414
415- Publisher sr_hand_target_pub;
416+ boost::shared_ptr<shadowrobot::HandCommander> shadowhand_ros_lib;
417 ServiceServer get_status_server;
418 ServiceClient is_hand_occupied_client;
419- sr_robot_msgs::sendupdate sendupdate_msg;
420 std::vector<sr_robot_msgs::joint> joint_vector;
421
422 bool hand_occupied;
423@@ -57,4 +56,4 @@
424 End:
425 */
426
427-#endif SR_MOVE_ARM_SIMPLE_ACTION_H
428+#endif //SR_MOVE_ARM_SIMPLE_ACTION_H
429
430=== modified file 'sr_move_arm/manifest.xml'
431--- sr_move_arm/manifest.xml 2012-03-16 11:04:42 +0000
432+++ sr_move_arm/manifest.xml 2012-11-14 19:52:22 +0000
433@@ -14,6 +14,7 @@
434 <url>http://ros.org/wiki/sr_move_arm</url>
435 <depend package="roscpp"/>
436 <depend package="rospy"/>
437+ <depend package="rostest"/>
438 <depend package="std_msgs"/>
439 <depend package="std_srvs"/>
440 <depend package="arm_navigation_msgs"/>
441@@ -24,6 +25,7 @@
442 <depend package="actionlib_msgs"/>
443 <depend package="sr_robot_msgs"/>
444 <depend package="object_manipulator"/>
445+ <depend package="sr_hand"/>
446
447 </package>
448
449
450=== modified file 'sr_move_arm/src/hand_posture_execution.cpp'
451--- sr_move_arm/src/hand_posture_execution.cpp 2012-07-25 20:52:06 +0000
452+++ sr_move_arm/src/hand_posture_execution.cpp 2012-11-14 19:52:22 +0000
453@@ -21,7 +21,7 @@
454
455 get_status_server = nh.advertiseService("/right_arm/grasp_status", &SrHandPostureExecutionSimpleAction::getStatusCallback, this);
456
457- sr_hand_target_pub = nh.advertise<sr_robot_msgs::sendupdate>("/srh/sendupdate", 2);
458+ shadowhand_ros_lib = boost::shared_ptr<shadowrobot::HandCommander>( new shadowrobot::HandCommander() );
459
460 action_server->start();
461 }
462@@ -61,7 +61,18 @@
463 }
464
465
466- std::vector<std::string> joint_names = goal->grasp.pre_grasp_posture.name;
467+ std::vector<std::string> joint_names;
468+ if (goal->goal == object_manipulation_msgs::GraspHandPostureExecutionGoal::GRASP)
469+ joint_names = goal->grasp.grasp_posture.name;
470+ else
471+ joint_names = goal->grasp.pre_grasp_posture.name;
472+
473+ if (joint_names.empty())
474+ {
475+ ROS_ERROR("Shadow Robot grasp execution: names empty in requested grasp");
476+ action_server->setAborted();
477+ return;
478+ }
479
480 joint_vector.clear();
481 for(unsigned int i = 0; i < joint_names.size(); ++i)
482@@ -70,7 +81,6 @@
483 joint.joint_name = joint_names[i];
484 joint_vector.push_back(joint);
485 }
486- sendupdate_msg.sendupdate_length = joint_vector.size();
487
488 object_manipulation_msgs::GraspHandPostureExecutionResult result;
489
490@@ -81,18 +91,17 @@
491
492 if (goal->grasp.grasp_posture.position.empty())
493 {
494- ROS_ERROR("Shadow Robot grasp execution: position vector empty in requested grasp");
495- action_server->setAborted();
496- return;
497+ ROS_ERROR("Shadow Robot grasp execution: position vector empty in requested grasp");
498+ action_server->setAborted();
499+ return;
500 }
501 for(unsigned int i = 0; i < goal->grasp.grasp_posture.position.size(); ++i)
502 {
503 joint_vector[i].joint_target = goal->grasp.grasp_posture.position[i]*180.0/M_PI;
504 ROS_DEBUG("[%s]: %f", joint_names[i].c_str(), joint_vector[i].joint_target);
505 }
506- sendupdate_msg.sendupdate_list = joint_vector;
507
508- sr_hand_target_pub.publish(sendupdate_msg);
509+ shadowhand_ros_lib->sendCommands(joint_vector);
510 ROS_DEBUG("Hand in grasp position");
511
512 result.result.value = object_manipulation_msgs::ManipulationResult::SUCCESS;
513@@ -106,9 +115,9 @@
514
515 if (goal->grasp.pre_grasp_posture.position.empty())
516 {
517- ROS_ERROR("Shadow Robot grasp execution: position vector empty in requested pre_grasp");
518- action_server->setAborted();
519- return;
520+ ROS_ERROR("Shadow Robot grasp execution: position vector empty in requested pre_grasp");
521+ action_server->setAborted();
522+ return;
523 }
524 //move to pregrasp
525 for(unsigned int i = 0; i < goal->grasp.pre_grasp_posture.position.size(); ++i)
526@@ -116,9 +125,8 @@
527 joint_vector[i].joint_target = goal->grasp.pre_grasp_posture.position[i]*180.0/M_PI;
528 ROS_DEBUG("[%s]: %f", joint_names[i].c_str(), joint_vector[i].joint_target);
529 }
530- sendupdate_msg.sendupdate_list = joint_vector;
531
532- sr_hand_target_pub.publish(sendupdate_msg);
533+ shadowhand_ros_lib->sendCommands(joint_vector);
534 ROS_DEBUG("Hand in pregrasp position");
535
536 result.result.value = object_manipulation_msgs::ManipulationResult::SUCCESS;
537@@ -136,9 +144,8 @@
538 joint_vector[i].joint_target = 0.0;
539 ROS_DEBUG("[%s]: %f", joint_names[i].c_str(), joint_vector[i].joint_target);
540 }
541- sendupdate_msg.sendupdate_list = joint_vector;
542
543- sr_hand_target_pub.publish(sendupdate_msg);
544+ shadowhand_ros_lib->sendCommands(joint_vector);
545 ROS_DEBUG("Hand opened");
546
547 result.result.value = object_manipulation_msgs::ManipulationResult::SUCCESS;
548@@ -178,3 +185,4 @@
549 c-basic-offset: 2
550 End:
551 */
552+// vim: expandtab:ts=2:sw=2
553
554=== modified file 'sr_move_arm/src/reactive_actions/reactive_grasp.py'
555--- sr_move_arm/src/reactive_actions/reactive_grasp.py 2012-09-28 18:50:23 +0000
556+++ sr_move_arm/src/reactive_actions/reactive_grasp.py 2012-11-14 19:52:22 +0000
557@@ -8,7 +8,6 @@
558 import scipy, time
559 from object_manipulator.convert_functions import *
560 from object_manipulation_msgs.msg import GripperTranslation, ManipulationPhase
561-from sr_robot_msgs.msg import sendupdate, joint
562 from sr_robot_msgs.srv import which_fingers_are_touching
563 from trajectory_msgs.msg import JointTrajectory
564 from actionlib import SimpleActionClient
565@@ -17,6 +16,8 @@
566 #from geometric_shapes_msgs.msg import Shape
567 from actionlib_msgs.msg import GoalStatus
568
569+from shadowhand_ros import ShadowHand_ROS
570+
571 ##abort exception
572 class Aborted(Exception): pass
573
574@@ -54,8 +55,7 @@
575 self._phase_pub = rospy.Publisher('/reactive_manipulation_phase', ManipulationPhase)
576
577 #send targets to the arm / hand
578- self.sr_hand_target_pub = rospy.Publisher('/srh/sendupdate', sendupdate)
579- self.sr_arm_target_pub = rospy.Publisher('/sr_arm/sendupdate', sendupdate)
580+ self.sr_lib = ShadowHand_ROS()
581 self.move_arm_client = None
582
583 if which_arm == 'r':
584@@ -235,15 +235,15 @@
585 joint_names = joint_path.joint_names
586
587 for trajectory_step in joint_path.points:
588- sendupdate_msg = []
589+ sendupdate_dict = {}
590
591 for (joint_name, joint_target) in zip(joint_names, trajectory_step.positions):
592 # convert targets to degrees
593- sendupdate_msg.append(joint(joint_name = joint_name, joint_target = joint_target * 57.325))
594-
595- self.sr_arm_target_pub.publish(sendupdate(len(sendupdate_msg), sendupdate_msg) )
596- self.sr_hand_target_pub.publish(sendupdate(len(sendupdate_msg), sendupdate_msg) )
597-
598+ sendupdate_dict[joint_name] = joint_target * 57.325
599+
600+ self.sr_lib.sendupdate_arm_from_dict(sendupdate_dict)
601+ self.sr_lib.sendupdate_from_dict(sendupdate_dict)
602+
603 current_sleep_time = trajectory_step.time_from_start - last_time
604 rospy.sleep( current_sleep_time )
605 last_time = trajectory_step.time_from_start
606@@ -269,14 +269,14 @@
607 joint_names = joint_path.joint_names
608
609 for trajectory_step in joint_path.points:
610- sendupdate_msg = []
611+ sendupdate_dict = {}
612
613 for (joint_name, joint_target) in zip(joint_names, trajectory_step.positions):
614 # convert targets to degrees
615- sendupdate_msg.append(joint(joint_name = joint_name, joint_target = joint_target * 57.325))
616+ sendupdate_dict[joint_name] = joint_target * 57.325
617
618- self.sr_arm_target_pub.publish(sendupdate(len(sendupdate_msg), sendupdate_msg) )
619- self.sr_hand_target_pub.publish(sendupdate(len(sendupdate_msg), sendupdate_msg) )
620+ self.sr_lib.sendupdate_arm_from_dict(sendupdate_dict)
621+ self.sr_lib.sendupdate_from_dict(sendupdate_dict)
622
623 current_sleep_time = trajectory_step.time_from_start - last_time
624 rospy.sleep( current_sleep_time )
625@@ -352,7 +352,7 @@
626 fingers_touching = [0,0,0,0,0]
627
628 for i_step in range(0, nb_steps + 1):
629- sendupdate_msg = []
630+ sendupdate_dict = {}
631 fingers_touch_index = {"FF":0, "MF":1, "RF":2, "LF":3, "TH":4}
632 for (index, joint_name, grasp_target, pregrasp_target) in zip(range(0,len(joint_names)),joint_names, grasp, pregrasp):
633 # only update the finger that are not touching
634@@ -368,11 +368,11 @@
635 joint_target = pregrasp_target + float(grasp_target - pregrasp_target)*(float(i_step) / float(nb_steps) )
636 myjoint_target = joint_target * 180.0 / math.pi
637 current_targets[index] = joint_target
638- sendupdate_msg.append(joint(joint_name = joint_name, joint_target = myjoint_target))
639+ sendupdate_dict[joint_name] = myjoint_target
640 rospy.logdebug("["+joint_name+"]: (p/g/t) = "+str(pregrasp_target)+"/"+str(grasp_target)+"/"+str(myjoint_target) + " ("+
641 str(float(i_step) / float(nb_steps))+"%)")
642
643- self.sr_hand_target_pub.publish(sendupdate(len(sendupdate_msg), sendupdate_msg) )
644+ self.sr_lib.sendupdate_from_dict(sendupdate_dict)
645 rospy.sleep(iteration_time)
646 #check which fingers are touching
647 which_fingers_are_touching_response = []
648@@ -469,13 +469,13 @@
649 """
650 joint_names = pregrasp_posture.name
651 joint_targets = pregrasp_posture.position
652- sendupdate_msg = []
653+ sendupdate_dict = {}
654
655 for (joint_name, joint_target) in zip(joint_names, joint_targets):
656 myjoint_target=joint_target * 180 / math.pi
657- sendupdate_msg.append(joint(joint_name = joint_name, joint_target = myjoint_target))
658+ sendupdate_dict[joint_name] = myjoint_target
659
660- self.sr_hand_target_pub.publish(sendupdate(len(sendupdate_msg), sendupdate_msg) )
661+ self.sr_lib.sendupdate_from_dict(sendupdate_dict)
662
663 def command_cartesian(self, pose, frame_id='world'):
664 """
665
666=== added file 'sr_move_arm/test/hand_posture_execution_test.launch'
667--- sr_move_arm/test/hand_posture_execution_test.launch 1970-01-01 00:00:00 +0000
668+++ sr_move_arm/test/hand_posture_execution_test.launch 2012-11-14 19:52:22 +0000
669@@ -0,0 +1,7 @@
670+<launch>
671+ <!-- Start simulated hand for testing -->
672+ <include file="$(find sr_hand)/launch/gazebo/gazebo_hand.launch" />
673+
674+ <node name="hand_posture_execution" pkg="sr_move_arm" type="hand_posture_execution" />
675+ <test test-name="hand_posture_execution_test" pkg="sr_move_arm" type="hand_posture_execution_test" />
676+</launch>

Subscribers

People subscribed via source and target branches

to all changes: