# (志航) [STM32]定時器
## 定時器輸入捕獲 PWM占空比
### 定時器TIM
:::success

:::
***
#### 硬體設置





___
#### 主要程式碼
``` c=
#include "main.h"
#include "stdio.h"
void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_TIM3_Init(void);
static void MX_USART1_UART_Init(void);
char txBuffer[100];
uint8_t rising_flag = 0;
uint8_t falling_flag = 0;
uint8_t overflow_v = 0;
uint16_t cnt_v = 0;
uint32_t V = 0;
void HAL_TIM_IC_CaptureCallback(TIM_HandleTypeDef *htim)//輸入捕獲
{
if(htim -> Instance == TIM3 && htim->Channel == HAL_TIM_ACTIVE_CHANNEL_4)
{
if(falling_flag == 0){
if(rising_flag == 1){
falling_flag = 1;
cnt_v = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_4);
__HAL_TIM_SET_CAPTUREPOLARITY(htim, TIM_CHANNEL_4, TIM_INPUTCHANNELPOLARITY_RISING);
}else{
overflow_v = 0;
cnt_v = 0;
V = 0;
rising_flag = 1;
__HAL_TIM_DISABLE(htim);
__HAL_TIM_SET_COUNTER(htim, 0);
__HAL_TIM_SET_CAPTUREPOLARITY(htim, TIM_CHANNEL_4, TIM_INPUTCHANNELPOLARITY_FALLING);
__HAL_TIM_ENABLE(htim);
}
}
}
}
int main(void)
{
HAL_Init();
SystemClock_Config();
MX_GPIO_Init();
MX_TIM3_Init();
MX_USART1_UART_Init();
HAL_TIM_Base_Start_IT(&htim3);
HAL_TIM_IC_Start_IT(&htim3, TIM_CHANNEL_4);
while (1)
{
if(falling_flag == 1){
V = overflow_v * 65536; // 按鈕按下秒數=溢出次數*(ARR+1) + CNT
V += cnt_v;
sprintf(txBuffer, "PB1_Trigger_time: %ld ms\n", V/1000);
HAL_UART_Transmit(&huart1, (uint8_t *)txBuffer, strlen(txBuffer), 1000);
falling_flag = 0;
rising_flag = 0;
}
}
}
```

CCR:比較值或捕獲值,用於輸入捕獲。
ARR:自動重載寄存器,控制計數器的最大值。
``` c=
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)//記數週期結束觸發
{
if(htim -> Instance == TIM3 )
{
if(rising_flag == 1){
if((overflow_v & 0xff) == 0xff){
falling_flag = 1;
__HAL_TIM_SET_CAPTUREPOLARITY(htim, TIM_CHANNEL_4, TIM_INPUTCHANNELPOLARITY_RISING);
}else{
overflow_v ++;
}
}
}
}
```


``` c=
MX_TIM2_Init();
HAL_TIM_PWM_Start(&htim2, TIM_CHANNEL_1);
uint8_t PB_ON (GPIO_TypeDef *GPIOx, uint16_t GPIO_Pin){
uint8_t PB = 0;
if (HAL_GPIO_ReadPin(GPIOx, GPIO_Pin))
{
HAL_Delay(50);
PB = 1;
}
while(HAL_GPIO_ReadPin(GPIOx, GPIO_Pin))
{
}
HAL_Delay(50);
return PB;
}
void LED_BRI (void){
if(PB_ON(GPIOD, PB2_Pin)){
i += 30;
if (i > 100) {
i = 0;
}
__HAL_TIM_SET_COMPARE(&htim2, TIM_CHANNEL_1, i);
}
}
```
#### 成果
{%youtube I9U-Xy01ewM%}
{%youtube I9QaW7QKIJQ%}
___
## **實驗進度**
- [x] 6-跑馬燈實驗
- [x] 7-蜂鳴器實驗
- [x] 8-按鈕輸入實驗
- [x] 9-序列埠通訊實驗
- [x] 10-外部中斷實驗
- [x] 12-窗口門狗(WWDG)實驗
- [x] 13-定時器中斷實驗
- [x] 14-PWN輸出實驗
- [ ] 16-電容觸摸按鍵實驗
- [ ] 18-TFTLCD顯示實驗
- [ ] 19-USMART調試組件實驗
- [ ] 20-RTC即時時鐘實驗
- [ ] 23-ADC實驗
- [ ] 29-IIC實驗
- [ ] 30-SPI實驗
- [ ] 36-DHT11數位溫濕度感測器實驗