18 from uuv_control_interfaces
import DPControllerBase
24 Model-free sliding mode controller based on the work published in [1] and 25 [2], or model-free high order sliding mode controller. 27 [1] Garcia-Valdovinos, Luis Govinda, et al. "Modelling, design and robust 28 control of a remotely operated underwater vehicle." International 29 Journal of Advanced Robotic Systems 11.1 (2014): 1. 30 [2] Salgado-Jimenez, Tomas, Luis G. Garcia-Valdovinos, and Guillermo 31 Delgado-Ramirez. "Control of ROVs using a Model-free 2nd-Order Sliding 32 Mode Approach." Sliding Mode Control (2011): 347-368. 35 _LABEL =
'Model-free Sliding Mode Controller' 38 DPControllerBase.__init__(self, is_model_based=
False)
39 self._logger.info(
'Initializing: ' + self.
_LABEL)
48 self.
_Kd = np.zeros(6)
50 self.
_Ki = np.zeros(6)
54 if rospy.has_param(
'~K'):
55 coefs = rospy.get_param(
'~K')
57 self.
_K = np.array(coefs)
59 raise rospy.ROSException(
'K coefficients: 6 coefficients ' 62 self._logger.info(
'K=' + str(self.
_K))
64 if rospy.has_param(
'~Kd'):
65 coefs = rospy.get_param(
'~Kd')
67 self.
_Kd = np.array(coefs)
69 raise rospy.ROSException(
'Kd coefficients: 6 coefficients ' 72 self._logger.info(
'Kd=' + str(self.
_Kd))
74 if rospy.has_param(
'~Ki'):
75 coefs = rospy.get_param(
'~Ki')
77 self.
_Ki = np.array(coefs)
79 raise rospy.ROSException(
'Ki coeffcients: 6 coefficients ' 81 self._logger.info(
'Ki=' + str(self.
_Ki))
83 if rospy.has_param(
'~slope'):
84 coefs = rospy.get_param(
'~slope')
86 self.
_slope = np.array(coefs)
88 raise rospy.ROSException(
'Slope coefficients: 6 coefficients ' 91 self._logger.info(
'slope=' + str(self.
_slope))
94 if rospy.has_param(
'~sat_epsilon'):
95 self.
_sat_epsilon = max(0.0, rospy.get_param(
'~sat_epsilon'))
97 self._logger.info(
'Saturation limits=' + str(self.
_sat_epsilon))
107 self._services[
'set_sm_controller_params'] = rospy.Service(
108 'set_sm_controller_params',
109 SetSMControllerParams,
111 self._services[
'get_sm_controller_params'] = rospy.Service(
112 'get_sm_controller_params',
113 GetSMControllerParams,
117 self._logger.info(self.
_LABEL +
' ready')
130 self.
_tau = np.zeros(6)
133 return SetSMControllerParamsResponse(
True)
136 return GetSMControllerParamsResponse(
140 self._slope.tolist())
145 t = rospy.Time.now().to_sec()
152 e_p_linear_b = self._errors[
'pos']
153 e_v_linear_b = self._errors[
'vel'][0:3]
155 e_p_angular_b = self.error_orientation_rpy
156 e_v_angular_b = self._errors[
'vel'][3:6]
159 s_linear_b = -e_v_linear_b - np.multiply(self.
_slope[0:3],
161 s_angular_b = -e_v_angular_b - np.multiply(self.
_slope[3:6],
170 np.exp(-self.
_K[0:3] * (t - self.
_t_init)))
172 np.exp(-self.
_K[3:6] * (t - self.
_t_init)))
175 sn_linear_b = s_linear_b - sd_linear_b
176 sn_angular_b = s_angular_b - sd_angular_b
179 if self.
_prev_t > 0.0
and dt > 0.0:
186 sr_linear_b = sn_linear_b + np.multiply(self.
_Ki[0:3],
188 sr_angular_b = sn_angular_b + np.multiply(self.
_Ki[3:6],
192 force_b = -np.multiply(self.
_Kd[0:3], sr_linear_b)
193 torque_b = -np.multiply(self.
_Kd[3:6], sr_angular_b)
195 self.
_tau = np.hstack((force_b, torque_b))
197 self.publish_control_wrench(self.
_tau)
204 def sat(value, epsilon=0.5):
205 assert epsilon >= 0,
'Saturation constant must be greate or equal to zero' 207 return np.sign(value)
209 vec = value / epsilon
210 output = np.zeros(vec.size)
211 for i
in range(output.size):
214 elif vec[i] < -epsilon:
220 if __name__ ==
'__main__':
221 print(
'Starting Non-model-based Sliding Mode Controller')
222 rospy.init_node(
'rov_nmb_sm_controller')
227 except rospy.ROSInterruptException:
228 print(
'caught exception')
def get_sm_controller_params_callback(self, request)
def set_sm_controller_params_callback(self, request)
def sat(value, epsilon=0.5)
def _reset_controller(self)
def update_controller(self)