Skip to content

Commit eab4d46

Browse files
committed
Update move_to_pose
1 parent 6edd3df commit eab4d46

File tree

1 file changed

+34
-10
lines changed

1 file changed

+34
-10
lines changed

Control/move_to_pose/move_to_pose.py

Lines changed: 34 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,10 @@ def __init__(self, Kp_rho, Kp_alpha, Kp_beta):
4040
self.Kp_rho = Kp_rho
4141
self.Kp_alpha = Kp_alpha
4242
self.Kp_beta = Kp_beta
43+
self.direction = 0 # 0: not initialized, 1: forward, -1: backward
44+
45+
def reset_direction(self):
46+
self.direction = 0
4347

4448
def calc_control_command(self, x_diff, y_diff, theta, theta_goal):
4549
"""
@@ -76,26 +80,38 @@ def calc_control_command(self, x_diff, y_diff, theta, theta_goal):
7680
# [-pi, pi] to prevent unstable behavior e.g. difference going
7781
# from 0 rad to 2*pi rad with slight turn
7882

83+
# Ref: The velocity v always has a constant sign which depends on the initial value of α.
84+
if self.direction == 0:
85+
alpha = angle_mod(np.arctan2(y_diff, x_diff) - theta)
86+
if alpha > np.pi / 2 or alpha < -np.pi / 2:
87+
print(f"alpha: {alpha}, direction: -1")
88+
self.direction = -1
89+
else:
90+
print(f"alpha: {alpha}, direction: 1")
91+
self.direction = 1
92+
7993
rho = np.hypot(x_diff, y_diff)
8094
v = self.Kp_rho * rho
8195

82-
alpha = angle_mod(np.arctan2(y_diff, x_diff) - theta)
83-
beta = angle_mod(theta_goal - theta - alpha)
84-
if alpha > np.pi / 2 or alpha < -np.pi / 2:
85-
# recalculate alpha to make alpha in the range of [-pi/2, pi/2]
96+
if self.direction == 1:
97+
alpha = angle_mod(np.arctan2(y_diff, x_diff) - theta)
98+
alpha = np.clip(alpha, -np.pi / 2, np.pi / 2)
99+
else:
100+
# backward direction should calculate alpha from the opposite direction
86101
alpha = angle_mod(np.arctan2(-y_diff, -x_diff) - theta)
87-
beta = angle_mod(theta_goal - theta - alpha)
88-
w = self.Kp_alpha * alpha - self.Kp_beta * beta
102+
alpha = np.clip(alpha, -np.pi / 2, np.pi / 2)
89103
v = -v
90-
else:
91-
w = self.Kp_alpha * alpha - self.Kp_beta * beta
104+
105+
beta = angle_mod(theta_goal - theta - alpha)
106+
w = self.Kp_alpha * alpha - self.Kp_beta * beta
92107

93108
return rho, v, w
94109

95110

96111
# simulation parameters
97112
controller = PathFinderController(9, 15, 3)
98113
dt = 0.01
114+
MAX_SIM_TIME = 5 # seconds, robot will stop moving when time exceeds this value
99115

100116
# Robot specifications
101117
MAX_LINEAR_SPEED = 15
@@ -105,17 +121,20 @@ def calc_control_command(self, x_diff, y_diff, theta, theta_goal):
105121

106122

107123
def move_to_pose(x_start, y_start, theta_start, x_goal, y_goal, theta_goal):
124+
controller.reset_direction()
108125
x = x_start
109126
y = y_start
110127
theta = theta_start
111128

112129
x_diff = x_goal - x
113130
y_diff = y_goal - y
114131

115-
x_traj, y_traj = [], []
132+
x_traj, y_traj, v_traj, w_traj = [x], [y], [0], [0]
116133

117134
rho = np.hypot(x_diff, y_diff)
118-
while rho > 0.001:
135+
t = 0
136+
while rho > 0.001 and t < MAX_SIM_TIME:
137+
t += dt
119138
x_traj.append(x)
120139
y_traj.append(y)
121140

@@ -130,6 +149,9 @@ def move_to_pose(x_start, y_start, theta_start, x_goal, y_goal, theta_goal):
130149
if abs(w) > MAX_ANGULAR_SPEED:
131150
w = np.sign(w) * MAX_ANGULAR_SPEED
132151

152+
v_traj.append(v)
153+
w_traj.append(w)
154+
133155
theta = theta + w * dt
134156
x = x + v * np.cos(theta) * dt
135157
y = y + v * np.sin(theta) * dt
@@ -154,6 +176,8 @@ def move_to_pose(x_start, y_start, theta_start, x_goal, y_goal, theta_goal):
154176
)
155177
plot_vehicle(x, y, theta, x_traj, y_traj)
156178

179+
return x_traj, y_traj, v_traj, w_traj
180+
157181

158182
def plot_vehicle(x, y, theta, x_traj, y_traj): # pragma: no cover
159183
# Corners of triangular vehicle when pointing to the right (0 radians)

0 commit comments

Comments
 (0)