STM32标准库教程:PWM电机控制(开环控制)
目录
1.原理简介
1.1PWM控制原理
1.1.1 电机
1.1.2 电机驱动
2.硬件设计
2.1 PWM电机控制电路接线图
2.2 PWM电机控制电路原理图
3.软件设计
3.1 PWM.c
3.2 PWM.h
3.3 direction.c
3.4 direction.h
3.5 mian.c
1.原理简介
1.1PWM控制原理
使用STM32F103ZET6单片机输出2路PWM波(方波),通过L298N驱动芯片放大后输入GM37直流减速电机中,实现对电机的PWM调速、正反转。
1.1.1 电机
(1)选型:直流减速电机——GM37直流减速电机
(2)接线:
红色、黑色线:PWM输入
绿色、蓝色线:编码器电源
黄色、白色线:编码器输出
1.1.2 电机驱动
(1)选型:L298N
(2)接线:
2.硬件设计
2.1 PWM电机控制电路接线图
2.2 PWM电机控制电路原理图
3.软件设计
3.1 PWM.c
1.#include "PWM.h"
2.// ----------------------------1.初始化PWM--------------------------------------
3./* ---------------------------------函数声明-------------------------------------
4.*函数名称:TIM3_CH2_PWM_Iint(u16 per, u16 psc)
5.*输入参数:u16 per:自动重装载值;u16 psc:预分频系数
6.*返回参数:无
7.*功 能:初始化PWM,使用TIM3的通道2输出PWM
8.*作 者:lph
9.*日 期:2024/03/27
10.------------------------------------------------------------------------------ */
11.void TIM2_CH3_PWM_Iint(u16 per, u16 psc)
12.{
13. //1.1使能定时器及端口时钟
14. RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
15. RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
16. RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);
17.
18. //1.2初始化GPIO
19. GPIO_InitTypeDef GPIO_InitStruct;
20.
21. GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;
22. GPIO_InitStruct.GPIO_Pin = GPIO_Pin_2;
23. GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
24. GPIO_Init(GPIOA, &GPIO_InitStruct);
25.
26. //1.3设置引脚复用器映射
27. GPIO_PinRemapConfig(GPIO_PartialRemap1_TIM2, ENABLE);
28.
29. //2.初始化定时器参数,包含自动重装值,分频系数,计数方式等
30. TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
31.
32. TIM_TimeBaseInitStructure.TIM_Period=per;
33. TIM_TimeBaseInitStructure.TIM_Prescaler=psc;
34. TIM_TimeBaseInitStructure.TIM_CounterMode=TIM_CounterMode_Up;
35. TIM_TimeBaseInitStructure.TIM_ClockDivision=TIM_CKD_DIV1;
36. TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStructure);
37.
38. //3.初始化PWM输出参数,包含PWM模式、输出极性,使能等
39. TIM_OCInitTypeDef TIM_OCInitStructure;
40.
41. TIM_OCInitStructure.TIM_OCMode=TIM_OCMode_PWM1;
42. TIM_OCInitStructure.TIM_OutputState=TIM_OutputState_Enable;
43. TIM_OCInitStructure.TIM_OCPolarity=TIM_OCPolarity_High; //TIM_OCPolarity_Low,TIM_OCPolarity_High
44. TIM_OC3Init(TIM2, &TIM_OCInitStructure);
45.
46. //5.使能TIMx在CCRx上的预装载寄存器
47. TIM_OC3PreloadConfig(TIM2, TIM_OCPreload_Enable);
48.
49. //6.使能 TIMx 在 ARR 上的预装载寄存器允许位
50. TIM_ARRPreloadConfig(TIM2, ENABLE);
51.
52. //4.开启定时器
53. TIM_Cmd(TIM2, ENABLE);
54.}
55.void TIM2_CH4_PWM_Iint(u16 per, u16 psc)
56.{
57. //1.1使能定时器及端口时钟
58. RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
59. RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
60. RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);
61.
62. //1.2初始化GPIO
63. GPIO_InitTypeDef GPIO_InitStruct;
64.
65. GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;
66. GPIO_InitStruct.GPIO_Pin = GPIO_Pin_3;
67. GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
68. GPIO_Init(GPIOA, &GPIO_InitStruct);
69.
70. //1.3设置引脚复用器映射
71. GPIO_PinRemapConfig(GPIO_PartialRemap2_TIM2, ENABLE);
72.
73. //2.初始化定时器参数,包含自动重装值,分频系数,计数方式等
74. TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
75.
76. TIM_TimeBaseInitStructure.TIM_Period=per;
77. TIM_TimeBaseInitStructure.TIM_Prescaler=psc;
78. TIM_TimeBaseInitStructure.TIM_CounterMode=TIM_CounterMode_Up;
79. TIM_TimeBaseInitStructure.TIM_ClockDivision=TIM_CKD_DIV1;
80. TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStructure);
81.
82. //3.初始化PWM输出参数,包含PWM模式、输出极性,使能等
83. TIM_OCInitTypeDef TIM_OCInitStructure;
84.
85. TIM_OCInitStructure.TIM_OCMode=TIM_OCMode_PWM1;
86. TIM_OCInitStructure.TIM_OutputState=TIM_OutputState_Enable;
87. TIM_OCInitStructure.TIM_OCPolarity=TIM_OCPolarity_High; //TIM_OCPolarity_Low, TIM_OCPolarity_High
88. TIM_OC4Init(TIM2, &TIM_OCInitStructure);
89.
90. //5.使能TIMx在CCRx上的预装载寄存器
91. TIM_OC4PreloadConfig(TIM2, TIM_OCPreload_Enable);
92.
93. //6.使能 TIMx 在 ARR 上的预装载寄存器允许位
94. TIM_ARRPreloadConfig(TIM2, ENABLE);
95.
96. //4.开启定时器
97. TIM_Cmd(TIM2, ENABLE);
98.}
99.void TIM3_CH3_PWM_Iint(u16 per, u16 psc)
100.{
101. //1.1使能定时器及端口时钟
102. RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
103. RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);
104. RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);
105.
106. //1.2初始化GPIO
107. GPIO_InitTypeDef GPIO_InitStruct;
108.
109. GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;
110. GPIO_InitStruct.GPIO_Pin = GPIO_Pin_0;
111. GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
112. GPIO_Init(GPIOB, &GPIO_InitStruct);
113.
114. //1.3设置引脚复用器映射
115. GPIO_PinRemapConfig(GPIO_PartialRemap_TIM3, ENABLE);
116.
117. //2.初始化定时器参数,包含自动重装值,分频系数,计数方式等
118. TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
119.
120. TIM_TimeBaseInitStructure.TIM_Period=per;
121. TIM_TimeBaseInitStructure.TIM_Prescaler=psc;
122. TIM_TimeBaseInitStructure.TIM_CounterMode=TIM_CounterMode_Up;
123. TIM_TimeBaseInitStructure.TIM_ClockDivision=TIM_CKD_DIV1;
124. TIM_TimeBaseInit(TIM3, &TIM_TimeBaseInitStructure);
125.
126. //3.初始化PWM输出参数,包含PWM模式、输出极性,使能等
127. TIM_OCInitTypeDef TIM_OCInitStructure;
128.
129. TIM_OCInitStructure.TIM_OCMode=TIM_OCMode_PWM1;
130. TIM_OCInitStructure.TIM_OutputState=TIM_OutputState_Enable;
131. TIM_OCInitStructure.TIM_OCPolarity=TIM_OCPolarity_High; //TIM_OCPolarity_Low, TIM_OCPolarity_High
132. TIM_OC3Init(TIM3, &TIM_OCInitStructure);
133.
134. //5.使能TIMx在CCRx上的预装载寄存器
135. TIM_OC3PreloadConfig(TIM3, TIM_OCPreload_Enable);
136.
137. //6.使能 TIMx 在 ARR 上的预装载寄存器允许位
138. TIM_ARRPreloadConfig(TIM3, ENABLE);
139.
140. //4.开启定时器
141. TIM_Cmd(TIM3, ENABLE);
142.}
3.2 PWM.h
1.#ifndef __PWM_H
2.#define __PWM_H
3.#include "system.h"
4.void TIM2_CH3_PWM_Iint(u16 per, u16 psc);
5.void TIM2_CH4_PWM_Iint(u16 per, u16 psc);
6.void TIM3_CH3_PWM_Iint(u16 per, u16 psc);
7.#endif
3.3 direction.c
1.#include "direction.h"
2.
3./* ---------------------------------函数声明-------------------------------------
4.*函数名称:void Direction_Control(void)
5.*输入参数:无
6.*返回参数:无
7.*功 能:电机转动方向控制
8.*作 者:lph
9.*日 期:2024/03/27
10.------------------------------------------------------------------------------ */
11.void Direction_Iint(void)
12.{
13. RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
14.
15. GPIO_InitTypeDef GPIO_InitStructure;
16.
17. GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4;
18. GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
19. GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
20. GPIO_Init(GPIOA, &GPIO_InitStructure);
21. GPIO_ResetBits(GPIOA, GPIO_Pin_4);
22.
23. GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;
24. GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
25. GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
26. GPIO_Init(GPIOA, &GPIO_InitStructure);
27. GPIO_ResetBits(GPIOA,GPIO_Pin_5);
28.}
29.
30.void Direction_Control(u8 mode, u16 compare)
31.{
32. //L298N输入使能
33. INB_1 = 1;
34. INB_2 = 1;
35. if(mode == 1) //左转
36. {
37. TIM_SetCompare3(TIM2, compare);
38.// TIM_SetCompare4(TIM2, 0);
39. TIM_SetCompare3(TIM3, 0);
40. }
41. else if(mode == 2) //右转
42. {
43. TIM_SetCompare3(TIM2, 0);
44.// TIM_SetCompare4(TIM2, compare);
45. TIM_SetCompare3(TIM3, compare);
46. }
47.}
3.4 direction.h
1.#ifndef __direction_H
2.#define __direction_H
3.#include "system.h"
4.#include "PWM.h"
5.// GPIO位带操作
6.#define INB_1 PAout(4)
7.#define INB_2 PAout(5)
8.void Direction_Iint(void);
9.void Direction_Control(u8 mode, u16 compare);
10.#endif
3.5 mian.c
1./* Includes ------------------------------------------------------------------*/
2.#include "stm32f10x.h"
3.#include "system.h"
4.#include "SysTick.h"
5.#include "PWM.h"
6.#include "direction.h"
7.
8./* 主函数main() --------------------------------------------------------------*/
9.int main()
10.{
11. // 一.自定义变量
12.
13. // 二.初始化-------------------
14. SysTick_Iint(72);
15. NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); // 中断分组
16. Direction_Iint();
17. TIM2_CH3_PWM_Iint(65536 - 1, 36 - 1);
18. TIM3_CH3_PWM_Iint(65536 - 1, 36 - 1);
19. while(1)
20. {
21. //电机正反转控制
22. Direction_Control(2, 65536 - 1);
23. }
24.}
作者:微风の清风