VelocityControl.py
Go to the documentation of this file.
1 #!/usr/bin/env python
2 # Copyright (c) 2016 The UUV Simulator Authors.
3 # All rights reserved.
4 #
5 # Licensed under the Apache License, Version 2.0 (the "License");
6 # you may not use this file except in compliance with the License.
7 # You may obtain a copy of the License at
8 #
9 # http://www.apache.org/licenses/LICENSE-2.0
10 #
11 # Unless required by applicable law or agreed to in writing, software
12 # distributed under the License is distributed on an "AS IS" BASIS,
13 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 # See the License for the specific language governing permissions and
15 # limitations under the License.
16 
17 import numpy
18 import rospy
19 from dynamic_reconfigure.server import Server
20 import geometry_msgs.msg as geometry_msgs
21 from nav_msgs.msg import Odometry
22 import tf.transformations as trans
23 from rospy.numpy_msg import numpy_msg
24 
25 # Modules included in this package
26 from PID import PIDRegulator
27 from uuv_control_cascaded_pid.cfg import VelocityControlConfig
28 
29 
31  def __init__(self):
32  print('VelocityControllerNode: initializing node')
33 
34  self.config = {}
35 
36  self.v_linear_des = numpy.zeros(3)
37  self.v_angular_des = numpy.zeros(3)
38 
39  # Initialize pids with default parameters
40  self.pid_angular = PIDRegulator(1, 0, 0, 1)
41  self.pid_linear = PIDRegulator(1, 0, 0, 1)
42 
43  # ROS infrastructure
44  self.sub_cmd_vel = rospy.Subscriber('cmd_vel', numpy_msg(geometry_msgs.Twist), self.cmd_vel_callback)
45  self.sub_odometry = rospy.Subscriber('odom', numpy_msg(Odometry), self.odometry_callback)
46  self.pub_cmd_accel = rospy.Publisher('cmd_accel', geometry_msgs.Accel, queue_size=10)
47  self.srv_reconfigure = Server(VelocityControlConfig, self.config_callback)
48 
49  def cmd_vel_callback(self, msg):
50  """Handle updated set velocity callback."""
51  # Just store the desired velocity. The actual control runs on odometry callbacks
52  v_l = msg.linear
53  v_a = msg.angular
54  self.v_linear_des = numpy.array([v_l.x, v_l.y, v_l.z])
55  self.v_angular_des = numpy.array([v_a.x, v_a.y, v_a.z])
56 
57  def odometry_callback(self, msg):
58  """Handle updated measured velocity callback."""
59  if not bool(self.config):
60  return
61 
62  linear = msg.twist.twist.linear
63  angular = msg.twist.twist.angular
64  v_linear = numpy.array([linear.x, linear.y, linear.z])
65  v_angular = numpy.array([angular.x, angular.y, angular.z])
66 
67  if self.config['odom_vel_in_world']:
68  # This is a temp. workaround for gazebo's pos3d plugin not behaving properly:
69  # Twist should be provided wrt child_frame, gazebo provides it wrt world frame
70  # see http://docs.ros.org/api/nav_msgs/html/msg/Odometry.html
71  xyzw_array = lambda o: numpy.array([o.x, o.y, o.z, o.w])
72  q_wb = xyzw_array(msg.pose.pose.orientation)
73  R_bw = trans.quaternion_matrix(q_wb)[0:3, 0:3].transpose()
74 
75  v_linear = R_bw.dot(v_linear)
76  v_angular = R_bw.dot(v_angular)
77 
78  # Compute compute control output:
79  t = msg.header.stamp.to_sec()
80  e_v_linear = (self.v_linear_des - v_linear)
81  e_v_angular = (self.v_angular_des - v_angular)
82 
83  a_linear = self.pid_linear.regulate(e_v_linear, t)
84  a_angular = self.pid_angular.regulate(e_v_angular, t)
85 
86  # Convert and publish accel. command:
87  cmd_accel = geometry_msgs.Accel()
88  cmd_accel.linear = geometry_msgs.Vector3(*a_linear)
89  cmd_accel.angular = geometry_msgs.Vector3(*a_angular)
90  self.pub_cmd_accel.publish(cmd_accel)
91 
92  def config_callback(self, config, level):
93  """Handle updated configuration values."""
94  # config has changed, reset PID controllers
95  self.pid_linear = PIDRegulator(config['linear_p'], config['linear_i'], config['linear_d'], config['linear_sat'])
96  self.pid_angular = PIDRegulator(config['angular_p'], config['angular_i'], config['angular_d'], config['angular_sat'])
97 
98  self.config = config
99 
100  return config
101 
102 
103 if __name__ == '__main__':
104  print('starting VelocityControl.py')
105  rospy.init_node('velocity_control')
106 
107  try:
109  rospy.spin()
110  except rospy.ROSInterruptException:
111  print('caught exception')
112  print('exiting')
def config_callback(self, config, level)


uuv_control_cascaded_pids
Author(s): Musa Morena Marcusso Manhaes , Sebastian Scherer , Luiz Ricardo Douat
autogenerated on Mon Jul 1 2019 19:39:10