树莓派通过脉冲宽度调制可以控制电机的速度。实际上在精度要求不是非常高的情况下,普通引脚也可以通过软件模拟来控制电机,实现pwm一样的功能。pwm功能可以控制直流电机的速度,同时,也可以控制步进电机的步数。
一.准备
树莓派4b
电机驱动TB6600
42步进电机
电源盒(4节1.5v电池)
电源线若干
二.电路连接示意图
https://shumeipai.nxez.com/raspberry-pi-pins-version-40
TB6600
这个是TB6600的外观,已经外壳上标注了各个针脚的作用。我切块以后做了以下的处理
主要分为上面框出来的几个大的模块:
A.电源 B.电机连接线 C.树莓派连线 D.电机电流选择按钮 E.步进电机运转一圈含有的脉冲数
A.电源(9v-42v)
下面四节干电池可能不行,需要提供大电压电源。
B.电机图:
连接图和TB6600上的图进行连接。
C.树莓派4B
D.电机电流选择
电机工作电流为1.7A
TB6600电机电流选择的描述,当设置SW2为按下,SW1,SW3为原位为1.7A的选中。所以设置SW1,SW2,SW3如下
通过SW1,SW2,SW3选择电流为1.7A
E.步进电机运转一圈含有的脉冲数
理论装备:步进电机一圈是360度。我用的42步进电机,上面标的步角是1.8度。意味着 200步走完一圈。即200步/圈。
在一个脉冲驱动一步的情况下,就是一个脉冲驱动1.8度的情况下下, 200个脉冲可以驱动电机转动一圈。
这种情况下因为步角太大,会造成低频震动和精度不够。所以需要进行细分。虽然电机本身是200步一圈,但是我们可以同过细分,把一个步角用 【细分】 个 脉冲来驱动,而不是一个脉冲。这时候,例如:8细分=8个脉冲驱动一个步角1.8度。那么驱动一圈需要8*200=1600个脉冲。
这个对应关系在
转自:http://www.zgbjdj.com/news2.asp?id=6507(强烈强度 五星/五星)
关于步进电机细分的概念及意义
所谓步进细分,就是将步进电机的一个步进角分成几步来走。
比如,不细分的情况下,一个脉冲走一个物理步进角; 4细分后就是4个脉冲走一个物理步进角。 因此,n细分的情况下,就是n个脉冲走一个物理步进角,一个脉冲走1/n个步进角。
用两相混合式步进电机来举例,通常步进角是1.8°,不细分的话一个脉冲电机转1.8度,则200个脉冲电机转一圈; n细分的话就是一个脉冲电机转n/1.8°,即200/n个脉冲电机转一圈。
通常有三种方式表示细分数:
1.直接表示法,即直接标出细分数,如1,2,4等
2.角度表示法,即标出细分后每个脉冲电机的转动的角度,如1.8°,0.9°,0.45°等
3.脉冲数表示法,即标出多少个脉冲电机旋转一圈,如200,400,800等,这种方法在三相步进系统中应用最多。
https://www.diangon.com/wenku/sfbj/201603/00031230.html
接下来,查看树莓派的主频:
[root@k8s-master ~]# lscpu
Architecture: aarch64
Byte Order: Little Endian
CPU(s): 4
On-line CPU(s) list: 0-3
Thread(s) per core: 1
Core(s) per socket: 4
座: 1
型号: 3
CPU max MHz: 1500.0000
CPU min MHz: 600.0000
BogoMIPS: 108.00
Flags: fp asimd evtstrm crc32 cpuid
看到4b 8g型号的cpu是物理4核,主频为1500MHz=1.5Ghz.PWM默认主频有文章说是19.2Mhz,默认分频32,在600khz。其中之间的关系暂时还没搞懂,有懂 的小伙伴请留言讨论。
我们的PWM针脚,设置为1600个脉冲,占空比100的情况下。这样一秒钟可以驱动轮子转一圈。后面会比较方便计算速度。一秒钟转一圈,假定轮子的直径是10cm,周长为L=2PI r=pi*D.这样就是0.1*3.14=0.314 米/秒。如果想提高速度,可以提高频率。速度越高,精度越高,不会出现抖动现象。例如,将pwm频率提高到3200个脉冲一秒,则占空比100的情况下,一秒转两圈,速度也提高两倍 0.314*2=0.628 m/s 。但是如果我们想降低速度,比如降到0.068m/s。那么需要设置160hz。这个时候,一个脉冲会驱动一个多步进电机的步角(42步进电机的步角1.8度。360度/1.8度=200步。)这个时候因精度下降,会出现精度下降的情况。这里可以提高精度,然后降低占空比来处理。
为了方便,因为步进电机设置的是1600个脉冲/圈。所以pwm设置也为1600,占空比100.这个设置就是java程序设置pwm针脚的时候处理的。
树莓派和TB6600的针脚如下:
void setPwm(int value):Set the PWM value/rate to toggle the GPIO pin. If this is a hardware PWM pin, the value should be between a range of 0 to 1024. If this is a software emulated PWM pin, the value should be between a range of 0 to 100.
voidsetPwmRange(int range): This sets the range register in the PWM generator. The default is 1024 for hardware PWM. The default is 100 for software emulated PWM.
PWM针脚,setPwmRange硬pwm,setPwmRange默认值为1024,软针脚默认为100;
setPwm(int value) 硬pwm,setPwm从0-1024,软针脚默认为从0-100;
我们使用 软pwm,两个值都为100.
三.程序
package top.fairy.global.globalfairytoppi4j.utils;
import com.pi4j.io.gpio.*;
import com.pi4j.util.CommandArgumentParser;
/**
* 设置轮子的速度
*
*/
public class PwmUtil {
// public boolean setSpeed(Pin enableAWheel, int speed){
// boolean result = true;
// try{
// GpioController gpio = GpioUtil.getGpioController();
//
// GpioPinPwmOutput pwm = gpio.provisionSoftPwmOutputPin(enableAWheel);
// pwm.setPwmRange(100);//默认值
// pwm.setPwm(speed);
// }catch (Exception e){
// result = false;
// }
// return result;
// }
public static void main(String[] args){
try{
GpioController gpio = GpioFactory.getInstance();
//启动
GpioPinDigitalOutput wheelAOut1 = gpio.provisionDigitalOutputPin(
RaspiPin.GPIO_00, "wheelAOut1", PinState.HIGH);
GpioPinDigitalOutput wheelAOut2 = gpio.provisionDigitalOutputPin(
RaspiPin.GPIO_01, "wheelAOut2", PinState.LOW);
Pin enableAWheel = CommandArgumentParser.getPin(//A的使能控制
RaspiPin.class, // pin provider class to obtain pin instance from
RaspiPin.GPIO_29, // default pin if no pin argument found
args);
GpioPinPwmOutput pwm = gpio.provisionSoftPwmOutputPin(enableAWheel);
pwm.setPwmRange(3000);
pwm.setPwm(2000);
try {
Thread.sleep(50000);//睡眠2秒
} catch (InterruptedException e) {
e.printStackTrace();
}
pwm.setPwmRange(1000);
try {
Thread.sleep(5000);//睡眠2秒
} catch (InterruptedException e) {
e.printStackTrace();
}
pwm.setPwmRange(0);
try {
Thread.sleep(5000);//睡眠2秒
} catch (InterruptedException e) {
e.printStackTrace();
}
pwm.setPwmRange(3000);
try {
Thread.sleep(5000);//睡眠2秒
} catch (InterruptedException e) {
e.printStackTrace();
}
pwm.setPwmRange(3000);
try {
Thread.sleep(2000000);//持续时间久一点
} catch (InterruptedException e) {
e.printStackTrace();
}
}catch(Exception e){
e.printStackTrace();
}
}
}
注意事项:
TB6600供电电压在DC.9~42VDC。我直接使用4块干电池,电压不足9v,才5v,其他连线的电压都正确,这种情况下,需要更换个大电压的供电器才行。
另外:千万别把连接线的导线头露在外面,一不小心短接,树莓派就报废了。