一、工程配置
使用定時器5作為輸入捕獲定時器,將通道1(PA0)設置為輸入捕獲,設置預分頻器和計數(shù)值,這里設置為1us計數(shù)一次,最大可以捕獲周期為0xFFFFFFFFus的PWM,所以一般不需要考慮溢出的問題,使能自動重裝載。
使能定時器中斷,選擇合適的優(yōu)先級,?
?將引腳設置下拉,保證沒有信號輸入時保持電壓的穩(wěn)定,最大輸出速度選擇高。
?在這里在這里可以選擇任意定時器輸出PWM,便于檢驗輸入捕獲的準確性,將TIM14通道1設置為PWM輸出,頻率為100Hz,其他默認即可。
二、代碼初始化和捕獲實現(xiàn)
在主函數(shù)中開啟定時器捕獲和更新中斷,更新中斷本例未使用到,根據(jù)需求開啟。開啟TIM14通道1,用于輸出PWM,這里設置占空比為32.7%。
初始化代碼中,首先設置 為上升沿捕獲,進入InputCap.flag==0,記錄定時器計數(shù)值,并設置為下降沿捕獲,隨后等待PWM波形下降沿到來,再次記錄定時器計數(shù)值,兩次計數(shù)值的差值就為PWM正脈寬的時長。再將觸發(fā)方式設置為上升沿觸發(fā),同樣記錄計數(shù)值,得到負脈寬的時長,就完成一次捕獲。需要注意的是代碼中的溢出,若第一次記錄的計數(shù)值為4294967200,如果脈寬時長為100us,那么第二次的計數(shù)值就會溢出,變成5,因為計數(shù)值最大為4294967295,超過該值將重新從0開始計數(shù),這時候計算出來的脈寬就會為負值。我們只需要判斷兩次計數(shù)值的大小,做簡單的處理即可(InputCap.tim_n_l=InputCap.tim_n1+0xffffffff-InputCap.tim_n2;)。
//在tim.h文件中加入
//定義一個結(jié)構(gòu)體
typedef struct
{
uint32_t tim_n_h;
uint32_t tim_n_l;
uint32_t tim_n1;
uint32_t tim_n2;
uint32_t tim_n3;
uint32_t T;//周期
//uint16_t overflow;//溢出計數(shù)
uint8_t flag;//捕獲完成標志
}InputCapture;
extern InputCapture InputCap;
//在tim.c文件中實現(xiàn)捕獲功能/
//重定義結(jié)構(gòu)體
InputCapture InputCap;
//捕獲中斷(當發(fā)生上升/下降沿時進入該函數(shù))
void HAL_TIM_IC_CaptureCallback(TIM_HandleTypeDef *htim)
{
if(htim==&htim5)
{
if(InputCap.flag==0)//上升沿
{
InputCap.flag=1;//記錄索引
InputCap.tim_n1=TIM5->CCR1;//獲取計數(shù)值
//切換為下降沿捕獲
__HAL_TIM_SET_CAPTUREPOLARITY(&htim5,TIM_CHANNEL_1,TIM_INPUTCHANNELPOLARITY_FALLING);
}
else if(InputCap.flag==1)
{
InputCap.flag=2;//記錄索引
InputCap.tim_n2=TIM5->CCR1;//獲取計數(shù)值
//溢出
if(InputCap.tim_n2<InputCap.tim_n1)
{
InputCap.tim_n_h=InputCap.tim_n2+0xffffffff-InputCap.tim_n1;
}
else
{
InputCap.tim_n_h=InputCap.tim_n2-InputCap.tim_n1;
}
//切換為上升沿捕獲
__HAL_TIM_SET_CAPTUREPOLARITY(&htim5,TIM_CHANNEL_1,TIM_INPUTCHANNELPOLARITY_RISING);
}
else if(InputCap.flag==2)
{
InputCap.flag=0;//記錄索引
InputCap.tim_n1=TIM5->CCR1;
//溢出
if(InputCap.tim_n2>InputCap.tim_n1)
{
InputCap.tim_n_l=InputCap.tim_n1+0xffffffff-InputCap.tim_n2;
}
else
{
InputCap.tim_n_l=InputCap.tim_n1-InputCap.tim_n2;
}
InputCap.T=InputCap.tim_n_l+InputCap.tim_n_h;
//切換為上升沿捕獲
__HAL_TIM_SET_CAPTUREPOLARITY(&htim5,TIM_CHANNEL_1,TIM_INPUTCHANNELPOLARITY_RISING);
}
}
}
?之后,只要不關(guān)閉輸入捕獲功能,就可以持續(xù)捕獲,可以在main函數(shù)中100ms輸出一次捕獲結(jié)果
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
printf("%dus %dus %0.3f%% %fHz\r\n",
InputCap.tim_n_h,//高電平時長
InputCap.tim_n_l,//低電平時長
100.0*InputCap.tim_n_h/(InputCap.tim_n_h+InputCap.tim_n_l),//占空比
1.0/((InputCap.tim_n_h+InputCap.tim_n_l)*0.000001)//頻率
);
HAL_Delay(100);
}
三、效果驗證
把單片機的PA0(捕獲)和PF9(PWM,也可以使用外部的波形發(fā)生器),連接起來,打開串口調(diào)試助手即可看到PWM相關(guān)信息,如正負脈寬,頻率,占空比等。文章來源:http://www.zghlxwxcb.cn/news/detail-839880.html
文章來源地址http://www.zghlxwxcb.cn/news/detail-839880.html
下期一起學習使用定時器讀取正交編碼器的值,控制PWM的占空比?
到了這里,關(guān)于STM32 CubeMX學習實驗13:定時器輸入捕獲獲取PWM頻率的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!