材料:
- 树莓派pico开发板(焊好排针方便插线)
- jy61或jy61p或jy901
- 杜邦线4根,分别插rx、tx、vcc、gnd(具体见后文)
- 一根microusb数据线连接树莓派pico和电脑
因为我们使用串口通信获取这款陀螺仪的输出信息才能使用被模块处理后的角度值,所以选择用串口通信来获取陀螺仪的信息。
测试代码:
首先,创建一个空的.py文件,把以下代码复制粘贴进去,并命名TestIMU.py。
from machine import Timer, UART, Pin
class Imu:
def __init__(self, uart):
self.ACCData = [0.0] * 8
self.GYROData = [0.0] * 8
self.AngleData = [0.0] * 8
self.FrameState = 0
self.Bytenum = 0
self.CheckSum = 0
self.a = [0.0] * 3
self.w = [0.0] * 3
self.Angle = [0.0] * 3
self.uart = uart
def recieveData(self, imuTimer): # 被用于周期性获取陀螺仪信息。
print(self.Angle) # 打印上一次获取到的角度值
if self.uart.any():
self.DueData(self.uart.read(33))
def DueData(self, inputdata):
for data in inputdata:
if self.FrameState == 0:
if data == 0x55 and self.Bytenum == 0:
self.CheckSum = data
self.Bytenum = 1
continue
elif data == 0x51 and self.Bytenum == 1:
self.CheckSum += data
self.FrameState = 1
self.Bytenum = 2
elif data == 0x52 and self.Bytenum == 1:
self.CheckSum += data
self.FrameState = 2
self.Bytenum = 2
elif data == 0x53 and self.Bytenum == 1:
self.CheckSum += data
self.FrameState = 3
self.Bytenum = 2
elif self.FrameState == 1:
if self.Bytenum < 10:
self.ACCData[self.Bytenum - 2] = data
self.CheckSum += data
self.Bytenum += 1
else:
if data == (self.CheckSum & 0xff):
self.a = self.get_acc(self.ACCData)
self.CheckSum = 0
self.Bytenum = 0
self.FrameState = 0
elif self.FrameState == 2:
if self.Bytenum < 10:
self.GYROData[self.Bytenum - 2] = data
self.CheckSum += data
self.Bytenum += 1
else:
if data == (self.CheckSum & 0xff):
self.w = self.get_gyro(self.GYROData)
self.CheckSum = 0
self.Bytenum = 0
self.FrameState = 0
elif self.FrameState == 3: # angle
if self.Bytenum < 10:
self.AngleData[self.Bytenum - 2] = data
self.CheckSum += data
self.Bytenum += 1
else:
if data == (self.CheckSum & 0xff):
self.Angle = self.get_angle(self.AngleData)
#d = self.a + self.w + self.Angle
self.CheckSum = 0
self.Bytenum = 0
self.FrameState = 0
def get_acc(self, datahex):
axl = datahex[0]
axh = datahex[1]
ayl = datahex[2]
ayh = datahex[3]
azl = datahex[4]
azh = datahex[5]
k_acc = 16.0
acc_x = (axh << 8 | axl) / 32768.0 * k_acc
acc_y = (ayh << 8 | ayl) / 32768.0 * k_acc
acc_z = (azh << 8 | azl) / 32768.0 * k_acc
if acc_x >= k_acc:
acc_x -= 2 * k_acc
if acc_y >= k_acc:
acc_y -= 2 * k_acc
if acc_z >= k_acc:
acc_z -= 2 * k_acc
return acc_x, acc_y, acc_z
def get_gyro(self, datahex):
wxl = datahex[0]
wxh = datahex[1]
wyl = datahex[2]
wyh = datahex[3]
wzl = datahex[4]
wzh = datahex[5]
k_gyro = 2000.0
gyro_x = (wxh << 8 | wxl) / 32768.0 * k_gyro
gyro_y = (wyh << 8 | wyl) / 32768.0 * k_gyro
gyro_z = (wzh << 8 | wzl) / 32768.0 * k_gyro
if gyro_x >= k_gyro:
gyro_x -= 2 * k_gyro
if gyro_y >= k_gyro:
gyro_y -= 2 * k_gyro
if gyro_z >= k_gyro:
gyro_z -= 2 * k_gyro
return gyro_x, gyro_y, gyro_z
def get_angle(self, datahex):
rxl = datahex[0]
rxh = datahex[1]
ryl = datahex[2]
ryh = datahex[3]
rzl = datahex[4]
rzh = datahex[5]
k_angle = 180.0
angle_x = (rxh << 8 | rxl) / 32768.0 * k_angle
angle_y = (ryh << 8 | ryl) / 32768.0 * k_angle
angle_z = (rzh << 8 | rzl) / 32768.0 * k_angle
if angle_x >= k_angle:
angle_x -= 2 * k_angle
if angle_y >= k_angle:
angle_y -= 2 * k_angle
if angle_z >= k_angle:
angle_z -= 2 * k_angle
return angle_x, angle_y, angle_z
MyIMU = Imu(UART(1, 115200, tx=Pin(4), rx=Pin(5))) # 选4和5分别用于tx和rx,并选用115200波特率。
imuTimer = Timer()
imuTimer.init(period=20, mode=Timer.PERIODIC, callback=MyIMU.recieveData)
接线:
树莓派pico GP4 ---> 陀螺仪rx
树莓派pico GP5 ---> 陀螺仪tx
树莓派pico 3v3(OUT)或者5v电源 ---> 陀螺仪vcc
树莓派pico GND ---> 陀螺仪GND
补充说明:
选GP4和GP5分别用作UART1 TX和UART1 RX。
这段代码把陀螺仪写成了一个类,方便管理变量,也方便定义多个陀螺仪。
“MyIMU = Imu(UART(1, 115200, tx=Pin(4), rx=Pin(5)))”声明了一个名为MyIMU的对象。
用定时器20ms周期性执行“recieveData”函数获取串口信息。
运行TestIMU.py,即可看见一串角度值不断打印。
参考维特智能官方提供的python代码: