本帖最后由 慕容雪花 于 2024-2-5 11:05 编辑
这次来制作一个呼吸灯,一是来熟悉一下CubeIDE自带的代码生成功能,二来可以了解使用TIM3模块生成自定义周期和占空比的PWM信号等基础功能。
首先来参考开发板硬件电路图,小灯LD1连接到芯片的PC7引脚。
其次,查询U5芯片的数据手册,看到PC7引脚有个复用功能,定时器3的2通道即TIM3_CH2。制作呼吸灯的任务就是看看怎么让这个TIM3在通道2上输出PWM即可。
定时器TIM3属于U5XX芯片的内部外设,从架构框图上看到该外设挂载到APB1总线上。
接下来在CubeIDE的图形化配置工具中,配置APB1的时钟频率为48MHz。
其次在PinOut引脚功能分配图界面,选择PC7引脚功能为TIM3_CH2
接下来配置TIM3_CH2:
TIM3的输入时钟信号为48MHz,上图配置的预分频系数为47,所以得到的计数器频率为48MHz/(1+47) = 1MHz。自动加载寄存器设定为999,即1000个时钟后刚好占用1ms的时间。
点击保存后,自动生成代码还是非常方便。
static void MX_TIM3_Init(void)
{
/* USER CODE BEGIN TIM3_Init 0 */
/* USER CODE END TIM3_Init 0 */
TIM_ClockConfigTypeDef sClockSourceConfig = {0};
TIM_MasterConfigTypeDef sMasterConfig = {0};
TIM_OC_InitTypeDef sConfigOC = {0};
/* USER CODE BEGIN TIM3_Init 1 */
/* USER CODE END TIM3_Init 1 */
htim3.Instance = TIM3;
htim3.Init.Prescaler = 47;
htim3.Init.CounterMode = TIM_COUNTERMODE_UP;
htim3.Init.Period = 999;
htim3.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;
htim3.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_ENABLE;
if (HAL_TIM_Base_Init(&htim3) != HAL_OK)
{
Error_Handler();
}
sClockSourceConfig.ClockSource = TIM_CLOCKSOURCE_INTERNAL;
if (HAL_TIM_ConfigClockSource(&htim3, &sClockSourceConfig) != HAL_OK)
{
Error_Handler();
}
if (HAL_TIM_PWM_Init(&htim3) != HAL_OK)
{
Error_Handler();
}
sMasterConfig.MasterOutputTrigger = TIM_TRGO_RESET;
sMasterConfig.MasterSlaveMode = TIM_MASTERSLAVEMODE_DISABLE;
if (HAL_TIMEx_MasterConfigSynchronization(&htim3, &sMasterConfig) != HAL_OK)
{
Error_Handler();
}
sConfigOC.OCMode = TIM_OCMODE_PWM1;
sConfigOC.Pulse = 0;
sConfigOC.OCPolarity = TIM_OCPOLARITY_HIGH;
sConfigOC.OCFastMode = TIM_OCFAST_DISABLE;
if (HAL_TIM_PWM_ConfigChannel(&htim3, &sConfigOC, TIM_CHANNEL_2) != HAL_OK)
{
Error_Handler();
}
/* USER CODE BEGIN TIM3_Init 2 */
/* USER CODE END TIM3_Init 2 */
HAL_TIM_MspPostInit(&htim3);
}
在主函数里面启动TIM3,然后在循环体中改变:
/**
* [url=home.php?mod=space&uid=159083]@brief[/url] The application entry point.
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
/* 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();
/* Configure the System Power */
SystemPower_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_ADC1_Init();
MX_ICACHE_Init();
MX_UCPD1_Init();
MX_USART1_UART_Init();
MX_USB_OTG_HS_HCD_Init();
MX_MEMORYMAP_Init();
MX_TIM3_Init();
/* USER CODE BEGIN 2 */
HAL_TIM_PWM_Start(&htim3, TIM_CHANNEL_2);
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
static uint16_t dcycle_pulse = 0;
//htim3.Init.Period = 999
while(dcycle_pulse <htim3.Init.Period){
__HAL_TIM_SET_COMPARE(&htim3, TIM_CHANNEL_2, dcycle_pulse);
dcycle_pulse += 50;
HAL_Delay(100);
}
while(dcycle_pulse > 0){
__HAL_TIM_SET_COMPARE(&htim3, TIM_CHANNEL_2, dcycle_pulse);
dcycle_pulse -= 50;
HAL_Delay(100);
}
}
/* USER CODE END 3 */
}
实物效果:
呼吸灯