dock_server.py
Go to the documentation of this file.
1 #!/usr/bin/env python
2 
3 import math
4 import rospy
5 import tf
6 
7 from actionlib import SimpleActionClient
8 from actionlib.action_server import ActionServer
9 
10 from geometry_msgs.msg import Pose, Twist, PoseStamped
11 from move_base_msgs.msg import MoveBaseGoal, MoveBaseFeedback, MoveBaseAction
12 
13 from caster_base.srv import SetDigitalOutput
14 from caster_app.msg import DockAction, DockFeedback, DockResult
15 
17  def __init__(self, name):
18  ActionServer.__init__(self, name, DockAction, self.__goal_callback, self.__cancel_callback, False)
19 
20  self.__docked = False
21 
22  self.__dock_speed = rospy.get_param("~dock/dock_speed", 0.05)
23  self.__dock_distance = rospy.get_param("~dock/dock_distance", 1.0)
24  self.__map_frame = rospy.get_param("~map_frame", "map")
25  self.__odom_frame = rospy.get_param("~odom_frame", "odom")
26  self.__base_frame = rospy.get_param("~base_frame", "base_footprint")
27 
28  self.__dock_ready_pose = Pose()
29  self.__dock_ready_pose.position.x = rospy.get_param("~dock/pose_x")
30  self.__dock_ready_pose.position.y = rospy.get_param("~dock/pose_y")
31  self.__dock_ready_pose.position.z = rospy.get_param("~dock/pose_z")
32  self.__dock_ready_pose.orientation.x = rospy.get_param("~dock/orientation_x")
33  self.__dock_ready_pose.orientation.y = rospy.get_param("~dock/orientation_y")
34  self.__dock_ready_pose.orientation.z = rospy.get_param("~dock/orientation_z")
35  self.__dock_ready_pose.orientation.w = rospy.get_param("~dock/orientation_w")
36 
37  self.__dock_ready_pose_2 = PoseStamped()
38 
39  rospy.loginfo("param: dock_spped, %s, dock_distance %s" % (self.__dock_speed, self.__dock_distance))
40  rospy.loginfo("param: map_frame %s, odom_frame %s, base_frame %s" % (self.__map_frame, self.__odom_frame, self.__base_frame))
41  rospy.loginfo("dock_pose:")
42  rospy.loginfo(self.__dock_ready_pose)
43 
44  self.__movebase_client = SimpleActionClient('move_base', MoveBaseAction)
45  rospy.loginfo("wait for movebase server...")
46  self.__movebase_client.wait_for_server()
47  rospy.loginfo("movebase server connected")
48 
49  self.__cmd_pub = rospy.Publisher('cmd_vel', Twist, queue_size=10)
50 
51  rospy.Subscriber("dock_pose", PoseStamped, self.__dock_pose_callback)
52 
54 
55  self.__docked = False
56  self.__saved_goal = MoveBaseGoal()
57 
58  rospy.loginfo("Creating ActionServer [%s]\n", name)
59 
60  def __dock_pose_callback(self, data):
61  ps = PoseStamped()
62  # ps.header.stamp = rospy.Time.now()
63  ps.header.frame_id = "dock"
64  ps.pose.position.x = -self.__dock_distance
65 
66  try:
67  self.__dock_ready_pose_2 = self.__tf_listener.transformPose("map", ps)
69  self.__dock_ready_pose_2.pose.position.z = -1.0
70  rospy.logwarn("tf 1error, %s" % e)
71 
72  self.__dock_ready_pose_2.pose.position.z = 0.0
73 
74  # rospy.loginfo("get dock pose")
75 
76  def __goal_callback(self, gh):
77  self.__saved_gh = gh
78  self.__saved_goal = gh.get_goal()
79 
80  if self.__saved_goal.dock == True:
81  if self.__docked == True:
82  rospy.logwarn("rejected, robot has already docked")
83  gh.set_rejected(None, "already docked")
84  else:
85  rospy.loginfo("Docking")
86  gh.set_accepted("Docking")
88  elif self.__saved_goal.dock == False:
89  if self.__docked == False:
90  rospy.logwarn("cancel_all_goals")
91  self.__movebase_client.cancel_all_goals()
92  cmd = Twist()
93  cmd.linear.x = self.__dock_speed
94  cmd.linear.x = 0
95  self.__cmd_pub.publish(cmd)
96  rospy.Rate(1).sleep()
97  rospy.logwarn("rejected, robot is not on charging")
98  gh.set_rejected(None, "robot is not on charging")
99  else:
100  rospy.loginfo("Start undock")
101  gh.set_accepted("Start undock")
102  self.__undock()
103  else:
104  rospy.logwarn("unknown dock data type, should be true or false")
105 
106  def __set_charge_relay(self, state):
107  rospy.loginfo("set relay %d" % state)
108  rospy.loginfo("check caster base service...")
109  rospy.wait_for_service('caster_base_node/set_digital_output')
110  rospy.loginfo("service exist")
111 
112  try:
113  set_digital_output = rospy.ServiceProxy('caster_base_node/set_digital_output', SetDigitalOutput)
114  resp = set_digital_output(4, state)
115  except rospy.ServiceException, e:
116  print "Service call failed: %s" % e
117 
118  def __cancel_callback(self, gh):
119  self.__movebase_client.cancel_goal()
120  rospy.logwarn("cancel callback")
121 
122  def __moveto_dock(self):
123  cmd = Twist()
124  cmd.linear.x = self.__dock_speed
125 
126  ca_feedback = DockFeedback()
127 
128  try :
129  last_pose, last_quaternion = self.__tf_listener.lookupTransform(self.__odom_frame, self.__base_frame, rospy.Time(0))
131  rospy.logwarn(e)
132  rospy.logwarn("tf error")
133 
134  delta_distance = 0
135  while delta_distance < self.__dock_distance-0.30 and not rospy.is_shutdown():
136  self.__cmd_pub.publish(cmd)
137 
138  try :
139  current_pose, current_quaternion = self.__tf_listener.lookupTransform(self.__odom_frame, self.__base_frame, rospy.Time(0))
140  delta_distance = math.sqrt(math.pow(current_pose[0]-last_pose[0],2)+math.pow(current_pose[1]-last_pose[1],2)+math.pow(current_pose[2]-last_pose[2],2))
141 
142  ca_feedback.dock_feedback = "Moving to Dock, %fm left" % (self.__dock_distance-delta_distance)
143  self.__saved_gh.publish_feedback(ca_feedback)
144 
145  rospy.loginfo("Moving to Dock, %fm left" % (self.__dock_distance-delta_distance))
147  rospy.logwarn(e)
148  rospy.logwarn("tf error aa")
149 
150  rospy.Rate(20).sleep()
151 
152  ca_feedback.dock_feedback = "Stop on Dock"
153  self.__saved_gh.publish_feedback(ca_feedback)
154  rospy.loginfo("stop robot")
155 
156  # stop robot
157  cmd.linear.x = 0
158  self.__cmd_pub.publish(cmd)
159 
160  # set charge relay on
161  self.__set_charge_relay(True)
162 
163  self.__docked = True
164  self.__saved_gh.set_succeeded(None, "Docked")
165  rospy.loginfo("Docked")
166 
168  # step 1
169  mb_goal = MoveBaseGoal()
170  mb_goal.target_pose.header.stamp = rospy.Time.now()
171  mb_goal.target_pose.header.frame_id = self.__map_frame
172  mb_goal.target_pose.pose = self.__dock_ready_pose
173 
174  self.__movebase_client.send_goal(mb_goal)
175 
176  self.__movebase_client.wait_for_result()
177  rospy.loginfo("arrived __dock_ready_pose")
178 
179  rospy.Rate(1).sleep()
180 
181  mb_goal.target_pose.header.stamp = rospy.Time.now()
182  mb_goal.target_pose.header.frame_id = self.__map_frame
183 
184  if self.__dock_ready_pose_2.pose.position.z == -0.3:
185  rospy.logwarn("dock_ready_pose_2 failed")
186  return
187  else:
188  t = self.__dock_ready_pose_2.pose
189 
190  t.position.z == 0.0
191  mb_goal.target_pose.pose = t
192 
193  rospy.logwarn("move to dock_ready_pose_2")
194  self.__movebase_client.send_goal(mb_goal)
195 
196  self.__movebase_client.wait_for_result()
197  rospy.loginfo("arrived dock_ready_pose_2")
198 
199  self.__moveto_dock()
200 
201  def __undock(self):
202  cmd = Twist()
203  cmd.linear.x = -self.__dock_speed
204 
205  ca_feedback = DockFeedback()
206 
207  try :
208  last_pose, last_quaternion = self.__tf_listener.lookupTransform(self.__odom_frame, self.__base_frame, rospy.Time(0))
210  rospy.logwarn(e)
211  rospy.logwarn("tf error")
212 
213  delta_distance = 0
214  while delta_distance < self.__dock_distance and not rospy.is_shutdown():
215  self.__cmd_pub.publish(cmd)
216 
217  try :
218  current_pose, current_quaternion = self.__tf_listener.lookupTransform(self.__odom_frame, self.__base_frame, rospy.Time(0))
219  delta_distance = math.sqrt(math.pow(current_pose[0]-last_pose[0],2)+math.pow(current_pose[1]-last_pose[1],2)+math.pow(current_pose[2]-last_pose[2],2))
220 
221  ca_feedback.dock_feedback = "Undock, %fm left" % (self.__dock_distance-delta_distance)
222  self.__saved_gh.publish_feedback(ca_feedback)
223 
224  rospy.loginfo("Undock, %fm left" % (self.__dock_distance-delta_distance))
226  rospy.logwarn(e)
227  rospy.logwarn("tf error aa")
228 
229  rospy.Rate(20).sleep()
230 
231  ca_feedback.dock_feedback = "Stop on DockReady"
232  self.__saved_gh.publish_feedback(ca_feedback)
233  rospy.loginfo("stop robot")
234 
235  # stop robot
236  cmd.linear.x = 0.0
237  self.__cmd_pub.publish(cmd)
238 
239  # set charge relay off
240  self.__set_charge_relay(False)
241 
242  self.__docked = False
243  self.__saved_gh.set_succeeded(None, "Undocked")
244  rospy.loginfo("UnDocked")
245 
246 def main():
247  rospy.init_node("dock_server")
248  ref_server = DockActionServer("dock_action")
249  ref_server.start()
250 
251  rospy.spin()
252 
253 if __name__ == '__main__':
254  main()
def __goal_callback(self, gh)
Definition: dock_server.py:76
def __init__(self, name)
Definition: dock_server.py:17
def __set_charge_relay(self, state)
Definition: dock_server.py:106
def __dock_pose_callback(self, data)
Definition: dock_server.py:60
def __cancel_callback(self, gh)
Definition: dock_server.py:118


caster_app
Author(s): Ye Tian
autogenerated on Wed Dec 18 2019 03:34:44