Skip to content

Commit a271be5

Browse files
authored
Merge pull request #6 from arduino/api_update
Api update
2 parents 48e92ce + 6f49117 commit a271be5

9 files changed

+189
-52
lines changed

arduino_alvik.py

+89-18
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
import math
22

3+
import gc
4+
35
from uart import uart
46
import _thread
57
from time import sleep_ms
@@ -42,6 +44,15 @@ def __init__(self):
4244
self.roll = None
4345
self.pitch = None
4446
self.yaw = None
47+
self.x = None
48+
self.y = None
49+
self.theta = None
50+
self.ax = None
51+
self.ay = None
52+
self.az = None
53+
self.gx = None
54+
self.gy = None
55+
self.gz = None
4556
self.left_tof = None
4657
self.center_left_tof = None
4758
self.center_tof = None
@@ -65,7 +76,11 @@ def begin(self) -> int:
6576
self._begin_update_thread()
6677
sleep_ms(100)
6778
self._reset_hw()
79+
while uart.any():
80+
uart.read(1)
6881
sleep_ms(1000)
82+
while self.last_ack != 0x00:
83+
sleep_ms(20)
6984
self.set_illuminator(True)
7085
return 0
7186

@@ -87,23 +102,45 @@ def _stop_update_thread(cls):
87102
"""
88103
cls._update_thread_running = False
89104

90-
def rotate(self, angle: float):
105+
def _wait_for_target(self):
106+
while not self.is_target_reached():
107+
pass
108+
109+
def is_target_reached(self) -> bool:
110+
if self.last_ack != ord('M') and self.last_ack != ord('R'):
111+
sleep_ms(50)
112+
return False
113+
else:
114+
self.packeter.packetC1B(ord('X'), ord('K'))
115+
uart.write(self.packeter.msg[0:self.packeter.msg_size])
116+
sleep_ms(200)
117+
return True
118+
119+
def rotate(self, angle: float, blocking: bool = True):
91120
"""
92121
Rotates the robot by given angle
93122
:param angle:
123+
:param blocking:
94124
:return:
95125
"""
126+
sleep_ms(200)
96127
self.packeter.packetC1F(ord('R'), angle)
97128
uart.write(self.packeter.msg[0:self.packeter.msg_size])
129+
if blocking:
130+
self._wait_for_target()
98131

99-
def move(self, distance: float):
132+
def move(self, distance: float, blocking: bool = True):
100133
"""
101134
Moves the robot by given distance
102135
:param distance:
136+
:param blocking:
103137
:return:
104138
"""
139+
sleep_ms(200)
105140
self.packeter.packetC1F(ord('G'), distance)
106141
uart.write(self.packeter.msg[0:self.packeter.msg_size])
142+
if blocking:
143+
self._wait_for_target()
107144

108145
def stop(self):
109146
"""
@@ -119,6 +156,10 @@ def stop(self):
119156
# stop the update thrad
120157
self._stop_update_thread()
121158

159+
# delete instance
160+
del self.__class__.instance
161+
gc.collect()
162+
122163
@staticmethod
123164
def _reset_hw():
124165
"""
@@ -156,19 +197,6 @@ def set_wheels_speed(self, left_speed: float, right_speed: float, unit: str = 'r
156197
self.packeter.packetC2F(ord('J'), left_speed, right_speed)
157198
uart.write(self.packeter.msg[0:self.packeter.msg_size])
158199

159-
def set_pid(self, side: str, kp: float, ki: float, kd: float):
160-
"""
161-
Sets motor PID parameters. Side can be 'L' or 'R'
162-
:param side:
163-
:param kp:
164-
:param ki:
165-
:param kd:
166-
:return:
167-
"""
168-
169-
self.packeter.packetC1B3F(ord('P'), ord(side), kp, ki, kd)
170-
uart.write(self.packeter.msg[0:self.packeter.msg_size])
171-
172200
def get_orientation(self) -> (float, float, float):
173201
"""
174202
Returns the orientation of the IMU
@@ -177,6 +205,27 @@ def get_orientation(self) -> (float, float, float):
177205

178206
return self.roll, self.pitch, self.yaw
179207

208+
def get_accelerations(self) -> (float, float, float):
209+
"""
210+
Returns the 3-axial acceleration of the IMU
211+
:return: ax, ay, az
212+
"""
213+
return self.ax, self.ay, self.az
214+
215+
def get_gyros(self) -> (float, float, float):
216+
"""
217+
Returns the 3-axial angular acceleration of the IMU
218+
:return: gx, gy, gz
219+
"""
220+
return self.gx, self.gy, self.gz
221+
222+
def get_imu(self) -> (float, float, float, float, float, float):
223+
"""
224+
Returns all the IMUs readouts
225+
:return: ax, ay, az, gx, gy, gz
226+
"""
227+
return self.ax, self.ay, self.az, self.gx, self.gy, self.gz
228+
180229
def get_line_sensors(self) -> (int, int, int):
181230
"""
182231
Returns the line sensors readout
@@ -202,6 +251,25 @@ def get_drive_speed(self) -> (float, float):
202251
"""
203252
return self.linear_velocity, self.angular_velocity
204253

254+
def reset_pose(self, x: float, y: float, theta: float):
255+
"""
256+
Resets the robot pose
257+
:param x: x coordinate of the robot
258+
:param y: y coordinate of the robot
259+
:param theta: angle of the robot
260+
:return:
261+
"""
262+
self.packeter.packetC3F(ord('Z'), x, y, theta)
263+
uart.write(self.packeter.msg[0:self.packeter.msg_size])
264+
sleep_ms(1000)
265+
266+
def get_pose(self) -> (float, float, float):
267+
"""
268+
Returns the current pose of the robot
269+
:return: x, y, theta
270+
"""
271+
return self.x, self.y, self.theta
272+
205273
def set_servo_positions(self, a_position: int, b_position: int):
206274
"""
207275
Sets A/B servomotor angle
@@ -301,7 +369,7 @@ def _parse_message(self) -> int:
301369
_, self.red, self.green, self.blue = self.packeter.unpacketC3I()
302370
elif code == ord('i'):
303371
# imu
304-
_, ax, ay, az, gx, gy, gz = self.packeter.unpacketC6F()
372+
_, self.ax, self.ay, self.az, self.gx, self.gy, self.gz = self.packeter.unpacketC6F()
305373
elif code == ord('p'):
306374
# battery percentage
307375
_, self.battery_perc = self.packeter.unpacketC1F()
@@ -330,6 +398,9 @@ def _parse_message(self) -> int:
330398
elif code == ord('x'):
331399
# robot ack
332400
_, self.last_ack = self.packeter.unpacketC1B()
401+
elif code == ord('z'):
402+
# robot ack
403+
_, self.x, self.y, self.theta = self.packeter.unpacketC3F()
333404
elif code == 0x7E:
334405
# firmware version
335406
_, *self.version = self.packeter.unpacketC3B()
@@ -401,9 +472,9 @@ def get_touch_right(self) -> bool:
401472
"""
402473
return bool(self.touch_bits & 0b10000000)
403474

404-
def get_color(self) -> (int, int, int):
475+
def get_color_raw(self) -> (int, int, int):
405476
"""
406-
Returns the RGB color (raw) readout
477+
Returns the color sensor's raw readout
407478
:return: red, green, blue
408479
"""
409480

examples/leds_setting.py

-4
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,6 @@
77

88
while True:
99
try:
10-
alvik._set_leds(0xff)
11-
sleep_ms(1000)
12-
alvik._set_leds(0x00)
13-
sleep_ms(1000)
1410
alvik.set_builtin_led(1)
1511
sleep_ms(1000)
1612
alvik.set_illuminator(1)

examples/move_example.py

-25
This file was deleted.

examples/pose_example.py

+69
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
from arduino_alvik import ArduinoAlvik
2+
from time import sleep_ms
3+
import sys
4+
5+
alvik = ArduinoAlvik()
6+
alvik.begin()
7+
8+
while True:
9+
try:
10+
11+
alvik.move(100.0)
12+
print("on target after move")
13+
14+
alvik.move(50.0)
15+
print("on target after move")
16+
17+
alvik.rotate(90.0)
18+
print("on target after rotation")
19+
20+
alvik.rotate(-45.00)
21+
print("on target after rotation")
22+
23+
x, y, theta = alvik.get_pose()
24+
print(f'Current pose is x={x}, y={y} ,theta={theta}')
25+
26+
alvik.reset_pose(0, 0, 0)
27+
28+
x, y, theta = alvik.get_pose()
29+
print(f'Updated pose is x={x}, y={y} ,theta={theta}')
30+
sleep_ms(500)
31+
32+
print("___________NON-BLOCKING__________________")
33+
34+
alvik.move(50.0, blocking=False)
35+
while not alvik.is_target_reached():
36+
print(f"Not yet on target received:{alvik.last_ack}")
37+
print("on target after move")
38+
39+
alvik.rotate(45.0, blocking=False)
40+
while not alvik.is_target_reached():
41+
print(f"Not yet on target received:{alvik.last_ack}")
42+
print("on target after rotation")
43+
44+
alvik.move(100.0, blocking=False)
45+
while not alvik.is_target_reached():
46+
print(f"Not yet on target received:{alvik.last_ack}")
47+
print("on target after move")
48+
49+
alvik.rotate(-90.00, blocking=False)
50+
while not alvik.is_target_reached():
51+
print(f"Not yet on target received:{alvik.last_ack}")
52+
print("on target after rotation")
53+
54+
x, y, theta = alvik.get_pose()
55+
print(f'Current pose is x={x}, y={y} ,theta={theta}')
56+
57+
alvik.reset_pose(0, 0, 0)
58+
59+
x, y, theta = alvik.get_pose()
60+
print(f'Updated pose is x={x}, y={y} ,theta={theta}')
61+
sleep_ms(500)
62+
63+
alvik.stop()
64+
sys.exit()
65+
66+
except KeyboardInterrupt as e:
67+
print('over')
68+
alvik.stop()
69+
sys.exit()

examples/read_color_sensor.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
while True:
1010
try:
11-
r, g, b = alvik.get_color()
11+
r, g, b = alvik.get_color_raw()
1212
print(f'RED: {r}, Green: {g}, Blue: {b}')
1313
sleep_ms(100)
1414
except KeyboardInterrupt as e:

examples/read_imu.py

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
from arduino_alvik import ArduinoAlvik
2+
from time import sleep_ms
3+
import sys
4+
5+
alvik = ArduinoAlvik()
6+
alvik.begin()
7+
speed = 0
8+
9+
while True:
10+
try:
11+
ax, ay, az = alvik.get_accelerations()
12+
gx, gy, gz = alvik.get_gyros()
13+
print(f'ax: {ax}, ay: {ay}, az: {az}, gx: {gx}, gy: {gy}, gz: {gz}')
14+
sleep_ms(100)
15+
except KeyboardInterrupt as e:
16+
print('over')
17+
alvik.stop()
18+
sys.exit()

examples/set_pid.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,9 @@
88

99
while True:
1010
try:
11-
alvik.set_pid('L', 10.0, 1.3, 4.2)
11+
alvik.left_wheel.set_pid_gains(10.0, 1.3, 4.2)
1212
sleep_ms(100)
13-
alvik.set_pid('R', 4.0, 13, 1.9)
13+
alvik.right_wheel.set_pid_gains(4.0, 13, 1.9)
1414
sleep_ms(100)
1515
except KeyboardInterrupt as e:
1616
print('over')

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,5 @@
33
],
44
"deps": [
55
],
6-
"version": "0.0.7"
6+
"version": "0.1.0"
77
}

pinout_definitions.py

+9-1
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,15 @@
33
# NANO to STM32 PINS
44
D2 = 5 # ESP32 pin5 -> nano D2
55
D3 = 6 # ESP32 pin6 -> nano D3
6+
D4 = 7 # ESP32 pin7 -> nano D4
7+
8+
A4 = 11 # ESP32 pin11 SDA -> nano A4
9+
A5 = 12 # ESP32 pin12 SCL -> nano A5
610
A6 = 13 # ESP32 pin13 -> nano A6/D23
11+
712
BOOT0_STM32 = Pin(D2, Pin.OUT) # nano D2 -> STM32 Boot0
8-
RESET_STM32 = Pin(D3, Pin.OUT) # nano D2 -> STM32 NRST
13+
RESET_STM32 = Pin(D3, Pin.OUT) # nano D3 -> STM32 NRST
14+
NANO_CHK = Pin(D4, Pin.OUT) # nano D3 -> STM32 NRST
915
CHECK_STM32 = Pin(A6, Pin.IN, Pin.PULL_UP) # nano A6/D23 -> STM32 ROBOT_CHK
16+
ESP32_SDA = Pin(A4, Pin.OUT)
17+
ESP32_SCL = Pin(A5, Pin.OUT)

0 commit comments

Comments
 (0)