文章目录
前言
主控板STM32F302R8+驱动板X-NUCLEO-IHM07M1+直流无刷电机WR36BL61,实现电机的开环调速。
关于X-NUCLEO-IHM07M1驱动板的介绍,请阅读:
直流有刷电机驱动基于STM32F302R8+X-NUCLEO-IHM07M1(一)
直流无刷电机的驱动原理,请阅读:
直流无刷电机及Matlab/Simulink驱动仿真
直流无刷电机的六步换相驱动实现,请阅读:
直流无刷电机驱动基于STM32F302R8+X-NUCLEO-IHM07M1(一)
一、直流无刷电机开环调速原理
直流无刷电机驱动基于STM32F302R8+X-NUCLEO-IHM07M1(一)章节,当需要MOS管导通时,直接将电源加载到线圈上,电机很快飙升到最大速度,并以最大速度运行。实际应用中我们以PWM代替高低电平,把连续的开通转变为开/关交替的PWM形式,来实现调速控制。通常使用PWM控制直流无刷电机常见方法有五种:
本次实验采用第四种PWM控制方式:H_PWM-L_ON,即三相桥臂上管子导通时给PWM信号,下管子导通时给高电平信号,通过控制PWM的占空比即可控制加载到线圈的电压,实现电机的调速。
二、STM32F302R8+X-NUCLEO-IHM07M1直流无刷电机的开环调速
2.1.功能需求
通过按键控制直流无刷电机的转速,由于STM32F302R8控制器只有一个按键,因此只能单方向控制电机的加速或者减速,本次实验为加速实验,每按一次按键,电机的转速将增加。
2.2.硬件设计
控制板:STM32F302R8
驱动板:X-NUCLEO-IHM07M1
直流无刷电机:WR36BL61,额定功率10W,额定电压24V,额定电流0.5A,转速2000RMP,极对数2。
2.3.软件设计
2.3.1.STM32CubeMX底层配置
1、RCC设置外接HSE(Crystal/Ceramic Resonator),时钟设置为72MHz
2、PC10、PC11、PC12设置为推挽输出、无上下拉电阻、高速,初始化状态设为0;PB13设置为推挽输出,下拉电阻、高速,初始化状态为0;PC13设置为输入,无上下拉电阻。
3、PA8设置为TIM1_CH1,PA9设置为TIM1_CH2,PA10设置为TIM1_CH3;TIM1设置为内部时钟,TIM1_CH1、TIM1_CH2、TIM1_CH3设置为PWM模式,PSC设置为36-1,向上计数,ARR设置为100-1,频率为:72000000/36/100=20KHz,其余保持默认。
4、PA15设置为TIM2_CH1,PB3设置为TIM2_CH2,PB10设置为TIM2_CH3;TIM2设置为内部时钟,TIM2设置为XOR ON/Hall Sensor Mode模式,PSC设置为72-1,向上计数,ARR值设置为1000-1频率为1KHz,Hall Sensor时钟不分频,双边沿触发(注CubeMX只能选择上升沿或者下降沿触发,生成代码后手动修改为双边沿触发),输入滤波值设置为10,不开启软件延时;开启TIM2全局中断,中断优先级设置为1,0
5、使能USART2,异步模式,波特率115200,8位数据位,1位停止位,无奇偶校验位
6、IDE设置为MDK-RAM,在Keil环境中编写应用层程序
**
**
**
**
**
**
**
**
**
**
2.3.2.应用层开发
在Keil环境中编写应用层程序,实现功能需求。
主函数:
int main(void)
{
/* USER CODE BEGIN 1 */
uint8_t count=0;
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_TIM1_Init();
MX_TIM2_Init();
MX_USART2_UART_Init();
/* USER CODE BEGIN 2 */
HAL_TIM_PWM_Start(&htim1,TIM_CHANNEL_1); //开启TIM1 PWM输出
HAL_TIM_PWM_Start(&htim1,TIM_CHANNEL_2);
HAL_TIM_PWM_Start(&htim1,TIM_CHANNEL_3);
__HAL_TIM_ENABLE_IT(&htim2,TIM_IT_TRIGGER); //开启TIM2触发中断
__HAL_TIM_CLEAR_IT(&htim2,TIM_IT_TRIGGER); //清除触发中断标志位
HAL_TIMEx_HallSensor_Start(&htim2); //开启霍尔传感器功能
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
if(Key_Scany(KEY_GPIO_Port,KEY_Pin)==1) //调节占空比
{
Duty+=10;
if(Duty>100)
Duty=100;
}
if(Hall_InterruptFlag==0) //开启电机时未进入触发中断,此时直接驱动电机
{
BLDC_Driver(1);
}
HAL_Delay(10);
count++;
if(count%50==0)
{
count=0;
HAL_GPIO_TogglePin(LED_GPIO_Port, LED_Pin); //程序运行指示灯
}
}
/* USER CODE END 3 */
}
中断函数,每次霍尔状态发生变化进行电机换相驱动:
/* USER CODE BEGIN 1 */
void HAL_TIM_TriggerCallback(TIM_HandleTypeDef *htim)
{
Hall_InterruptFlag=1;
BLDC_Driver(1);
}
/* USER CODE END 1 */
按键扫描函数Key_Scany():
/* USER CODE BEGIN 2 */
uint8_t Key_Scany(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)
{
if(HAL_GPIO_ReadPin(GPIOx, GPIO_Pin)==0)
{
while(HAL_GPIO_ReadPin(GPIOx, GPIO_Pin)==0);
return 1;
}
else
return 0;
}
/* USER CODE END 2 */
无刷电机驱动函数BLDC_Driver()
/**************************************************/
/**WR36BL61的换相表,不同于正常直流无刷电机两两导通的
换相表,为尽大可能的利用资源,WR36BL61的换相表为每时刻
三个桥臂均有一个管子开启,厂家提供的换相表如下*******/
/*电机正转换相表**T为1代表桥臂上开下闭,T为0表示桥臂上闭下开*/
/*
H1 H2 H3 T1 T2 T3
0 0 1 1 0 1
1 0 1 1 0 0
1 0 0 1 1 0
1 1 0 0 1 0
0 1 0 0 1 1
0 1 1 0 0 1
*************************************************/
/*电机反转换相表******
0 0 1 0 1 0
1 0 1 0 1 1
1 0 0 0 0 1
1 1 0 1 0 1
0 1 0 1 0 0
0 1 1 1 1 0
**************************************************/
void BLDC_Driver(uint8_t Dirction) //根据获取的霍尔状态值进行采用六步换相法实现电机驱动
{
uint8_t Hall_State=0;
Hall_State=Get_HallState();
HAL_GPIO_WritePin(GPIOC, EN1_Pin, GPIO_PIN_SET); //使能三个桥臂
HAL_GPIO_WritePin(GPIOC, EN2_Pin, GPIO_PIN_SET);
HAL_GPIO_WritePin(GPIOC, EN3_Pin, GPIO_PIN_SET);
TIM1->CCR1=0; //三路PWM的占空比设置为0,即三路桥臂均上闭下开
TIM1->CCR2=0;
TIM1->CCR3=0;
if(Dirction==1) //Direction为1 电机正转 否则 电机反转
{
switch(Hall_State)
{
case 1:
TIM1->CCR1=Duty;
TIM1->CCR2=0;
TIM1->CCR3=Duty;
break;
case 5:
TIM1->CCR1=Duty;
TIM1->CCR2=0;
TIM1->CCR3=0;
break;
case 4:
TIM1->CCR1=Duty;
TIM1->CCR2=Duty;
TIM1->CCR3=0;
break;
case 6:
TIM1->CCR1=0;
TIM1->CCR2=Duty;
TIM1->CCR3=0;
break;
case 2:
TIM1->CCR1=0;
TIM1->CCR2=Duty;
TIM1->CCR3=Duty;
break;
case 3:
TIM1->CCR1=0;
TIM1->CCR2=0;
TIM1->CCR3=Duty;
break;
default:
break;
}
}
else
{
switch(Hall_State)
{
case 1:
TIM1->CCR1=0;
TIM1->CCR2=Duty;
TIM1->CCR3=0;
break;
case 5:
TIM1->CCR1=0;
TIM1->CCR2=Duty;
TIM1->CCR3=Duty;
break;
case 4:
TIM1->CCR1=0;
TIM1->CCR2=0;
TIM1->CCR3=Duty;
break;
case 6:
TIM1->CCR1=Duty;
TIM1->CCR2=0;
TIM1->CCR3=Duty;
break;
case 2:
TIM1->CCR1=Duty;
TIM1->CCR2=0;
TIM1->CCR3=0;
break;
case 3:
TIM1->CCR1=Duty;
TIM1->CCR2=Duty;
TIM1->CCR3=0;
break;
default:
break;
}
}
}
霍尔状态函数Get_HallState():
uint8_t Get_HallState(void) //获取霍尔状态值
{
uint8_t HallState=0;
HallState=HAL_GPIO_ReadPin(H1_GPIO_Port, H1_Pin);
HallState<<=1;
HallState|=HAL_GPIO_ReadPin(GPIOB, H2_Pin);
HallState<<=1;
HallState|=HAL_GPIO_ReadPin(GPIOB, H3_Pin);
return HallState;
}
2.4.编译下载观察试验现象
PWM占空比设置为10时A相的电压:
PWM占空比设置为20时的A相电压:
PWM占空比设置为50时的A相电压:
总结
主控板STM32F302R8+驱动板X-NUCLEO-IHM07M1+直流无刷电机WR36BL61,实现了直流无刷电机的开环调速,为后续章节的分析奠定基础。