microbit电机驱动扩展板-步进电机驱动(PCA9685驱动)

micro:bit编程、教学、展示
STEM
回复
头像
shaoziyang
帖子: 742
注册时间: 2019年 10月 21日 13:48

microbit电机驱动扩展板-步进电机驱动(PCA9685驱动)

#1

帖子 shaoziyang » 2019年 11月 25日 12:07

原帖作者:chpczx 发表于 2019-7-13 

PCA9685采用数字方式驱动步进电机,不是采用PWM方式驱动。(采用此扩展板驱动,将增加16个模拟/数字输出引脚)。程序用mu调试通过

Code: Select all

from microbit import *
import math


class PCA9685:
    def __init__(self, freq, init):
        self.I2C = i2c
        self.I2C.init(freq=100000, sda=pin20, scl=pin19)
        if not init:
            self.i2cW(0x00, 0x00)
            self.freq(freq)

    def i2cW(self, reg, value):
        buf = bytearray(2)
        buf[0] = reg
        buf[1] = value
        self.I2C.write(0x40, buf)

    def i2cR(self, reg):
        buf = bytearray(1)
        buf[0] = reg
        self.I2C.write(0x40, buf)
        return self.I2C.read(0x40, 1)

    def freq(self, freq):
        pre = math.floor(((25000000/4096/(freq))-1) + 0.5)
        oldmode = self.i2cR(0x00)
        self.i2cW(0x00, (oldmode[0] & 0x7F) | 0x10)
        self.i2cW(0xFE, pre)
        self.i2cW(0x00, oldmode[0])
        sleep(5)
        self.i2cW(0x00, oldmode[0] | 0xa1)

    # 16个输出脚作模拟使用(channel 0-15)
    def pwm(self, channel, on, off):
        if ((channel < 0) or (channel > 15)):
            return
        buf = bytearray(5)
        buf[0] = 0x06 + 4 * channel
        buf[1] = on & 0xff
        buf[2] = (on >> 8) & 0xff
        buf[3] = off & 0xff
        buf[4] = (off >> 8) & 0xff
        self.I2C.write(0x40,buf)

    # 16个输出脚作数字使用(channel 0-15)
    def write_digital(self, channel, value):
        if value == 1:  # OFF优先
            self.i2cW((0x06 + channel * 4 + 3), 0x00)
            self.i2cW((0x06 + channel * 4 + 1), 0xFF)
        else:
            self.i2cW((0x06 + channel * 4 + 3), 0xFF)

# 转一圈需要509步多一点
FULL_ROTATION = 509

# 半步励磁
HALF_STEP = [
    [0, 0, 0, 1],
    [0, 0, 1, 1],
    [0, 0, 1, 0],
    [0, 1, 1, 0],
    [0, 1, 0, 0],
    [1, 1, 0, 0],
    [1, 0, 0, 0],
    [1, 0, 0, 1],
]

# 全步励磁
FULL_STEP = [
    [0, 0, 0, 1],
    [0, 0, 1, 0],
    [0, 1, 0, 0],
    [1, 0, 0, 0]
]

class MultiStepper():
    def __init__(self):
        self.pca = PCA9685(1500, 0)
        self.servoList = [[7, 6, 5, 4],[3, 2, 1, 0]]

    # servoIndexList--电机索引列表,第一个添加的电机索引为0
    # directionList --电机转动方向列表 1表示逆时候,-1表示顺时针
    def doAction(self, servoIndexList, directionList, stepCount, mode=FULL_STEP, delay=3):
        for x in range(stepCount):
            for y in range(len(mode)):
                for z in range(len(servoIndexList)):
                    pinList = self.servoList[servoIndexList[z]]
                    bit = mode[::directionList[z]][y]
                    self.pca.write_digital(pinList[0], bit[0])
                    self.pca.write_digital(pinList[1], bit[1])
                    self.pca.write_digital(pinList[2], bit[2])
                    self.pca.write_digital(pinList[3], bit[3])
                sleep(delay)

        for i in range(len(servoIndexList)):
            pinList = self.servoList[servoIndexList[i]]
            self.pca.write_digital(pinList[0], 0)
            self.pca.write_digital(pinList[1], 0)
            self.pca.write_digital(pinList[2], 0)
            self.pca.write_digital(pinList[3], 0)


if __name__ == '__main__':
    s = MultiStepper()
    # 第一个电机顺时针走255步,全步励磁
    s.doAction([0],[-1],255, FULL_STEP,3)
    # 第一个电机逆时针和第二个电机顺时针各转一圈,全步励磁
    s.doAction([0, 1], [1, -1], FULL_ROTATION, FULL_STEP, 0)
    # 第二个电机逆时针走255步,全步励磁
    s.doAction([1],[1],255, FULL_STEP,3)[/i]

回复

  • 随机主题
    回复总数
    阅读次数
    最新文章