stm32系列--PWM捕获功能

Capture_Init(59999,120-1); // 可捕获最小频率 72M/(120*60000)= 17*0.6=10Hz PA1 // TIM2_CH2 PA7 做为捕获通道 // 输入捕获能捕获到的最小的频率为 72M/{ (ARR+1)*(PSC+1) } void Capture_Init(u16 arr, u16 psc) { GPIO_InitTypeDef GPIO_InitStructure; TIM_TimeBaseInitTypeDef TIM_TimeBaseInitSturcture; TIM_ICInitTypeDef TIM_ICInitSturcture; NVIC_InitTypeDef NVIC_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPD;//GPIO_Mode_IN_FLOATING GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOA, &GPIO_InitStructure); TIM_TimeBaseInitSturcture.TIM_Period = arr; TIM_TimeBaseInitSturcture.TIM_Prescaler = psc; TIM_TimeBaseInitSturcture.TIM_ClockDivision = TIM_CKD_DIV1; TIM_TimeBaseInitSturcture.TIM_CounterMode = TIM_CounterMode_Up; TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitSturcture); TIM_ICInitSturcture.TIM_Channel = TIM_Channel_2; TIM_ICInitSturcture.TIM_ICFilter = 0x0f; //0x00 TIM_ICInitSturcture.TIM_ICPolarity = TIM_ICPolarity_Rising; TIM_ICInitSturcture.TIM_ICPrescaler = TIM_ICPSC_DIV1; TIM_ICInitSturcture.TIM_ICSelection = TIM_ICSelection_DirectTI; //TIM_ICInit(TIM2, &TIM_ICInitSturcture); TIM_PWMIConfig(TIM2, &TIM_ICInitSturcture); //初始化PWM输入模式 // 当工作做PWM输入模式时,只需要设置触发信号的那一路即可(用于测量周期) // 另外一路(用于测量占空比)会由硬件自带设置,不需要再配置 TIM_SelectInputTrigger(TIM2, TIM_TS_TI2FP2); //选择输入捕获触发信号 TIM_SelectSlaveMode(TIM2, TIM_SlaveMode_Reset); // PWM输入模式时,从模式必须工作在复位模式,当捕获开始时,计数器CNT会被复位 TIM_SelectMasterSlaveMode(TIM2, TIM_MasterSlaveMode_Enable); NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02; NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); TIM_ITConfig(TIM2, TIM_IT_CC2, ENABLE); // 使能捕获中断,这个中断针对的是主捕获通道(测量周期那个) TIM_Cmd(TIM2, ENABLE); } //float DutyCycle = 0; //float Frequency = 0; u32 DutyCycle = 0; u32 Frequency = 0; u32 IC1Value = 0; u32 IC2Value = 0; // // 如果是第一个上升沿中断,计数器会被复位,锁存到CCR1寄存器的值是0,CCR2寄存器的值也是0, // 无法计算频率和占空比。当第二次上升沿到来的时候,CCR1和CCR2捕获到的才是有效的值。其中 // CCR1对应的是周期,CCR2对应的是占空比。 // void TIM2_IRQHandler(void) { IC1Value = TIM_GetCapture1(TIM2); // 占空比 IC2Value = TIM_GetCapture2(TIM2); // 总长度 if( myusart.reflag==0) { if(IC1Value != 0 && (IC2Value>IC1Value)) { DutyCycle = ((IC1Value + 1) * 10000) / (IC2Value + 1); //5050 50.5% Frequency = 600000 / (IC2Value + 1); } else { DutyCycle = 0; Frequency = 0; } } TIM_ClearITPendingBit(TIM2, TIM_IT_CC2); }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 单元测试从入门到精通
· 上周热点回顾(3.3-3.9)
· winform 绘制太阳,地球,月球 运作规律