Raspberry Pi Build HATでペンギン型(?)ロボットを作ったので、その備忘録です。
作ったロボット↓
旋回後に直進や後進を指定してもなーんか真っ直ぐ進まないけど、ご愛敬。
原因は未調査。まっすぐ進むこともある。そんな問題を抱えつつ、オリジナルロボットラジコン完成 !
主な材料、環境
ハード: Raspberry Pi 3 model B、Raspberry Pi Build HAT、F710ワイヤレス ゲームパッド 、レゴ、 ラズパイを固定するメイカープレート(3Dプリンタ出力)、バッテリー、バッテリーとBuild HATをつなぐケーブル
OS: Raspberry Pi OS (32bit)
レゴ組み立て方メモ
まずはメイカープレートにラズパイを固定


次にメイカープレートの上に二種類の枠を配置。Build HATのジャックの高さが微妙なのでごまかしている



腕と車輪を作成。(二組つくる)

小物を作成



全部くっつけて、裏側を補強

完成




Build HATとモーターの接続
| ポート | 接続するモーター |
|---|---|
| A | 左腕用 Mアンギュラーモーター |
| B | 右腕用 Mアンギュラーモーター |
| C | 左車輪用 Lアンギュラーモーター |
| D | 右車輪用 Lアンギュラーモーター |
ゲームパッドでの動かし方
| ボタン | 内容 |
|---|---|
| 十字キー | 上で前進、下で後退、左で左旋回、右で右旋回 |
| X | 左腕を上まであげる |
| B | 右腕を上まであげる |
| LB | 左腕を途中まであげる |
| RB | 右腕を途中まであげる |
プログラム
robo.pyという名前でラズパイ上に保存して実行。
import os
import pygame
from buildhat import Motor, MotorPair, Hat
from pygame.locals import *
os.environ["SDL_VIDEODRIVER"] = "dummy"
pygame.init()
pygame.joystick.init()
joy = pygame.joystick.Joystick(0)
joy.init()
# 右側モーターを基準にするので、反対側モーターは回転方向を反転
rotation_correction_left = -1
rotation_correction_right = 1
hat = Hat()
print('Hat voltage = %f' % hat.get_vin())
arm_motor_left = Motor('A')
arm_motor_right = Motor('B')
wheel_motor = MotorPair('C', 'D')
arm_motor_left.run_to_position(120 * rotation_correction_left)
arm_motor_right.run_to_position(120 * rotation_correction_right)
while True:
pygame.time.wait(30)
for e in pygame.event.get():
if e.type == pygame.locals.JOYAXISMOTION or e.type == pygame.locals.JOYHATMOTION:
hat_x = joy.get_hat(0)[0]
hat_y = joy.get_hat(0)[1]
axes_data = {
"HAT_X": hat_x,
"HAT_Y": hat_y,
}
print(axes_data)
if hat_y == 1:
wheel_motor.start(100 * rotation_correction_left, 100 * rotation_correction_right)
elif hat_y == -1:
wheel_motor.start(-100 * rotation_correction_left, -100 * rotation_correction_right)
elif hat_x == -1:
wheel_motor.start(-100 * rotation_correction_left, 100 * rotation_correction_right)
elif hat_x == 1:
wheel_motor.start(100 * rotation_correction_left, -100 * rotation_correction_right)
else:
wheel_motor.stop()
if e.type == pygame.locals.JOYBUTTONDOWN:
print('BUTTON %d DOWN' % e.button)
if e.button == 2:
arm_motor_left.run_to_position(0 * rotation_correction_left)
if e.button == 1:
arm_motor_right.run_to_position(0 * rotation_correction_right)
if e.button == 4:
arm_motor_left.run_to_position(90 * rotation_correction_left)
if e.button == 5:
arm_motor_right.run_to_position(90 * rotation_correction_right)
elif e.type == pygame.locals.JOYBUTTONUP:
print('BUTTON %d UP ' % e.button)
if e.button == 2:
arm_motor_left.run_to_position(120 * rotation_correction_left)
if e.button == 1:
arm_motor_right.run_to_position(120 * rotation_correction_right)
if e.button == 4:
arm_motor_left.run_to_position(120 * rotation_correction_left)
if e.button == 5:
arm_motor_right.run_to_position(120 * rotation_correction_right)
今のBuildHatライブラリだと、モータに対して頻繁に非同期指定でrun_to_positionを呼ぶと例外が発生した。そのため、腕はデフォルトの同期指定で操作。
(GitHubのissueでも取り上げられているので、そのうち解消されるのを期待)
リンク
モータの遅延の問題
https://forums.raspberrypi.com/viewtopic.php?p=2012025
https://github.com/RaspberryPiFoundation/python-build-hat/issues/152