搭建开发环境
本小项目开发环境根据官方windows+eclipse教程进行搭建。详情参考【Ai-WB2入门篇】搭建windows+eclipse环境。
产生PWM波
首先要了解Ai-WB2的pwm特性,这里参考的是Ai-WB2的pwm入门篇教程。
打开eclipse,进入官方例程application/peripherals/demo_pwm/demo_pwm/main.c
将pwm入门篇教程中的pwm使用实例代码覆盖在main.c中,编译代码,连接好Ai-WB2-12F模块后用官方的烧录工具将代码烧录入其中。
烧录方式如下:

选择好相应参数以及文件进行烧录。
烧录好后reset,便会看到位于端口IO3的蓝色RGB小灯闪烁。
驱动电机
之后进行电机驱动。这里用到了TB6612电机驱动模块,3个按钮模块(用于开关和调速)和一个130直流电机。


TB6612电机驱动模块如图所示。它最多可以独立双向控制两个直流电机。AIN1/AIN2、BIN1/BIN2、PWMA/PWMB为控制信号输入端;AO1/AO2、BO1/BO2为2路电机控制输出端;STBY为正常工作/待机状态控制引脚;VM为电机驱动电压输入端;VCC为电机逻辑电平输入端。
接线方法如下:
VM接5V
PWMA接IO12(Ai-WB2-12F模块输出PWM引脚)
STBY接3.3V
AIN1、AIN2分别接3.3V、GND(电机正转)或者GND、3.3V(电机反转)
GND接GND(驱动模块与Ai-WB2-12F模块共地)
130直流电机的正负极分别接驱动模块的AO1、AO2
3个按钮模块分别接Ai-WB2-12F模块的IO11、IO4、IO5
这里Ai-WB2-12F模块的3.3V供电接口可能不太够,我使用的面包板将3.3V和GND的接口扩展出来了。
接下来进行代码编写。
由于要涉及到按钮的检测,要先包括GPIO的头文件
#include <bl_gpio.h>
修改按钮的名字(按钮0用于开关、按钮1用于加速、按钮2用于减速)
#define GPIO_BUTTON0_PIN 11
#define GPIO_BUTTON1_PIN 4
#define GPIO_BUTTON2_PIN 5
先初始化要用到的全局参数
uint8_t flagOC=0;
uint8_t flagP=0;
uint8_t flagD=0;
int32_t currentduty=15;
int32_t currentfreq=10000;
修改初始化pwm参数(主要是端口和引脚)
void demo_hosal_pwm_init(void)
{
/* pwm 端口及引脚设置 注意:端口与引脚有对应关系,对于 bl602,映射为端口=引脚%5 */
pwm.port = 2;
/* pwm config */
pwm.config.pin = 12;
pwm.config.duty_cycle = 5000; //占空比范围为:0~10000相当于0~100%
pwm.config.freq = 500; //频率范围为 0~40MHZ
/* 初始化PWM */
hosal_pwm_init(&pwm);
}
添加按键初始化(IO3的蓝色小灯还在亮?调试很久没看出哪里有问题直接手动关掉了)
void demo_button_init(void)
{
/*初始化按键*/
bl_gpio_enable_output(3, 0, 0);
bl_gpio_output_set(3,0);
bl_gpio_enable_input(GPIO_BUTTON0_PIN, 0, 0);
bl_gpio_enable_input(GPIO_BUTTON1_PIN, 0, 0);
bl_gpio_enable_input(GPIO_BUTTON2_PIN, 0, 0);
}
扩展pwm参数修改函数(可以更改pwm的占空比和频率)
void demo_hosal_pwm_change_param(uint32_t duty,uint32_t cfreq)
{
/*周期(period)单位为微秒(us),频率(cfreq)单位为赫兹(Hz)*/
/*占空比(duty)范围为:0~1000*/
/* 更改PWM配置 */
hosal_pwm_config_t para;
para.duty_cycle = (duty * 100);
para.freq = cfreq;
// 更新PWM配置
hosal_pwm_para_chg(&pwm, para);
}
按钮检测函数(使用了复杂的判断...)
void button_detect(void)
{
if(bl_gpio_input_get_value(GPIO_BUTTON0_PIN)==1)
{
vTaskDelay(pdMS_TO_TICKS(50));
while(bl_gpio_input_get_value(GPIO_BUTTON0_PIN)==1);
vTaskDelay(pdMS_TO_TICKS(50));
if(flagOC==0)
{
flagOC=1;
hosal_pwm_start(&pwm);
printf("pwm task working\r\n");
printf("Current freq:%d",currentfreq);
}
else if(flagOC==1)
{
flagOC=0;
hosal_pwm_stop(&pwm);
printf("pwm task end\r\n");
}
}
if(bl_gpio_input_get_value(GPIO_BUTTON1_PIN)==1)
{
vTaskDelay(pdMS_TO_TICKS(50));
while(bl_gpio_input_get_value(GPIO_BUTTON1_PIN)==1);
vTaskDelay(pdMS_TO_TICKS(50));
flagP=flagP+1;
}
if(bl_gpio_input_get_value(GPIO_BUTTON2_PIN)==1)
{
vTaskDelay(pdMS_TO_TICKS(50));
while(bl_gpio_input_get_value(GPIO_BUTTON2_PIN)==1);
vTaskDelay(pdMS_TO_TICKS(50));
flagD=flagD+1;
}
}
最后是任务执行函数
void pwm_task(void* params) {
printf("pwm task start...\r\n");
demo_hosal_pwm_init();
demo_button_init();
while(1)
{
button_detect();
if(flagOC==1)
{
button_detect();
if(flagP!=0)
{
currentduty=currentduty+5;
demo_hosal_pwm_change_param(currentduty,currentfreq);
printf("Current freq:%d",currentfreq);
flagP=0;
}
if(flagD!=0)
{
currentduty=currentduty-5;
demo_hosal_pwm_change_param(currentduty,currentfreq);
printf("Current freq:%d",currentfreq);
flagD=0;
}
if(currentduty<0||currentduty>35)
{
currentduty=15;
demo_hosal_pwm_change_param(currentduty,currentfreq);
printf("Current freq:%d",currentfreq);
}
}
}
vTaskDelete(NULL);
}
void main(void) {
printf("pwm demo inited\r\n");
xTaskCreate(pwm_task, "pwm_task", 1024, NULL, 15, NULL);
}
这个小项目通过按钮实现了电机的开关和调速(调整pwm的占空比),在电机上装上一个小扇叶,便成为一个小风扇了(设置了7档)。(第一次写帖子有点生疏
,项目感觉还有很大的优化空间)
下面是实物演示视频。(忽略环境声
)