Python Raspberry Pi Pico プログラム 回路 電子工作 高専3年生

【Raspberry Pi Pico】ロボット制御入門②~ライブラリの作成~【Python】

前回モーター制御を行いましたが, このままでは毎回モーター制御のためのプログラムを書く必要があります。

しかし今後すべてのプログラムでモーター制御を使うため, 毎回コードを書いていては非常に面倒です。

そこでモーター制御のプログラムをライブラリ化していつでもインポートして参照できるようにしましょう。

ライブラリの仕組みは複雑ですので, ここでは簡単にこういうものがあってこうすれば使えると言うことだけ覚えていただければ大丈夫です。

ライブラリの自作

Pythonでの「ライブラリ」とは、必要な機能や処理をまとめて使えるようにしたものです。

例えば、今まで使ってきたmachinetimeは、importというコマンドで使えるようにしてきましたが、自分で作成することもできます。

ライブラリを使えば、複雑な機能を簡単に呼び出すことができます。

ここでは、自分で簡単なライブラリを作成してみましょう。

まずはmotor.pyというファイルを作成し、以下のコードを貼り付けてください。

これは、前回作成したモーター制御のコードを少しアレンジしたものです。

from machine import Pin
import utime

class Robot:
    # 初期化(最初に設定する部分)
    def __init__(self):
        self.MotorL_plus = Pin(0, Pin.OUT)
        self.MotorL_minus = Pin(1, Pin.OUT)
        self.MotorR_plus = Pin(2, Pin.OUT)
        self.MotorR_minus = Pin(3, Pin.OUT) 
    
    # 前進
    def forward(self):
        self.MotorL_plus.value(1)
        self.MotorL_minus.value(0)
        self.MotorR_plus.value(1)
        self.MotorR_minus.value(0)
    # 右折
    def right(self):
        self.MotorL_plus.value(0)
        self.MotorL_minus.value(1)
        self.MotorR_plus.value(1)
        self.MotorR_minus.value(0)
    # 左折
    def left(self):
        self.MotorL_plus.value(1)
        self.MotorL_minus.value(0)
        self.MotorR_plus.value(0)
        self.MotorR_minus.value(1)
    # 後退
    def back(self):
        self.MotorL_plus.value(0)
        self.MotorL_minus.value(1)
        self.MotorR_plus.value(0)
        self.MotorR_minus.value(1)
    # ブレーキ
    def brake(self):
        self.MotorL_plus.value(1)
        self.MotorL_minus.value(1)
        self.MotorR_plus.value(1)
        self.MotorR_minus.value(1) 
    # 停止
    def stop(self):
        self.MotorL_plus.value(0)
        self.MotorL_minus.value(0)
        self.MotorR_plus.value(0)
        self.MotorR_minus.value(0)

のプログラムで注目すべきポイントは、class__init__selfの3つです。

  • classは、関連する関数をまとめて使いやすくするための仕組みです。今回はモーターの動きをまとめています。
  • __init__は、クラスの初期設定を行う特別な関数です。プログラムが実行されると自動的に最初に呼ばれます。ここではピンの設定をまとめています。
  • selfは、クラスの中で使う変数や関数を指定するための決まりの文になっています。

ではこちらのプログラムをmotor.pyで本体に保存した後、以下のプログラムをmain.pyとして保存して呼び出してみます。

# 作成したライブラリからRobotクラスをインポート
from motor import Robot
import time

# Robotクラスを使う準備
robot = Robot()

while True:
    try:
        # robot.forward()で前進を実行
        robot.forward()
        time.sleep(3)
        robot.brake()
        time.sleep(3)
    finally:
        # 動作を停止
        robot.stop()

課題3

前回作成した、PWM制御も実装したライブラリを作成してください。

3秒50%で前進し、3秒30%で後退して、3秒停止するプログラムを作成してください。

解答例はこちら

ライブラリ

from machine import Pin, PWM

class Robot:
    # 初期化
    def __init__(self):
        # PWMを使ったモーター制御用ピンの設定
        self.MotorL_plus = PWM(Pin(0))
        self.MotorL_minus = PWM(Pin(1))
        self.MotorR_plus = PWM(Pin(2))
        self.MotorR_minus = PWM(Pin(3))
        
        # PWMの周波数を設定
        self.MotorL_plus.freq(1000)
        self.MotorL_minus.freq(1000)
        self.MotorR_plus.freq(1000)
        self.MotorR_minus.freq(1000)
        
        # 16ビットの最大値
        self.MAX_DUTY = 65535

    # 前進
    def forward(self, duty_ratio=1.0):
        duty = int(self.MAX_DUTY * duty_ratio)
        self.MotorL_plus.duty_u16(duty)
        self.MotorL_minus.duty_u16(0)
        self.MotorR_plus.duty_u16(duty)
        self.MotorR_minus.duty_u16(0)

    # 右折
    def right(self, duty_ratio=1.0):
        duty = int(self.MAX_DUTY * duty_ratio)
        self.MotorL_plus.duty_u16(duty)
        self.MotorL_minus.duty_u16(0)
        self.MotorR_plus.duty_u16(0)
        self.MotorR_minus.duty_u16(duty)

    # 左折
    def left(self, duty_ratio=1.0):
        duty = int(self.MAX_DUTY * duty_ratio)
        self.MotorL_plus.duty_u16(0)
        self.MotorL_minus.duty_u16(duty)
        self.MotorR_plus.duty_u16(duty)
        self.MotorR_minus.duty_u16(0)

    # 後退
    def back(self, duty_ratio=1.0):
        duty = int(self.MAX_DUTY * duty_ratio)
        self.MotorL_plus.duty_u16(0)
        self.MotorL_minus.duty_u16(duty)
        self.MotorR_plus.duty_u16(0)
        self.MotorR_minus.duty_u16(duty)

    # ブレーキ
    def brake(self):
        self.MotorL_plus.duty_u16(self.MAX_DUTY)
        self.MotorL_minus.duty_u16(self.MAX_DUTY)
        self.MotorR_plus.duty_u16(self.MAX_DUTY)
        self.MotorR_minus.duty_u16(self.MAX_DUTY)

    # 停止
    def stop(self):
        self.MotorL_plus.duty_u16(0)
        self.MotorL_minus.duty_u16(0)
        self.MotorR_plus.duty_u16(0)
        self.MotorR_minus.duty_u16(0)

main.py

from motor import Robot  # 作成したライブラリをインポート
import time

# Robotクラスのインスタンスを作成
robot = Robot()

try:
    while True:
        # 50%の速度で3秒間前進
        robot.forward(duty_ratio=0.5)
        time.sleep(3)

        # 30%の速度で3秒間後退
        robot.back(duty_ratio=0.3)
        time.sleep(3)

        # 3秒間停止
        robot.stop()
        time.sleep(3)

finally:
    # 終了時にモーターを停止
    robot.stop()

次回はこちら

Follow me!

-Python, Raspberry Pi Pico, プログラム, 回路, 電子工作, 高専3年生
-, , , , ,

PAGE TOP