使用STM32的Timer编码器模式调试旋钮

最近任务中使用到了旋钮,前面文章做了一个I/O口,今天记录一下使用STM32 timer编码器模式的方法

  1. 旋钮的左右2脚接到带有timer的脚上,配置为编码器模式, 这里使用了PC0和PC1

     //PB6 ch1  A,PB7 ch2 
     RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1, ENABLE);//使能TIM1时钟	
     RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOC, ENABLE);
     
     GPIO_StructInit(&GPIO_InitStructure);//将GPIO_InitStruct中的参数按缺省值输入
     GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1;         
     GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;//PA6 PA7浮空输入	
     GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
     GPIO_Init(GPIOC, &GPIO_InitStructure);                   
     
     GPIO_PinAFConfig(GPIOC, GPIO_PinSource0, GPIO_AF_2);
     GPIO_PinAFConfig(GPIOC, GPIO_PinSource1, GPIO_AF_2);	
     
     TIM_DeInit(TIM1);
     TIM_TimeBaseStructInit(&TIM_TimeBaseStructure);
     TIM_TimeBaseStructure.TIM_Period = 359*4;  //设定计数器重装值   TIMx_ARR = 359*4
     TIM_TimeBaseStructure.TIM_Prescaler = 0; //TIM3时钟预分频值
     TIM_TimeBaseStructure.TIM_ClockDivision =TIM_CKD_DIV1 ;//设置时钟分割 T_dts = T_ck_int	
     TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上计数 
     TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure);              
     
     TIM_EncoderInterfaceConfig(TIM1, TIM_EncoderMode_TI1, TIM_ICPolarity_BothEdge ,TIM_ICPolarity_BothEdge);//使用编码器模式3,上升下降都计数
     TIM_ICStructInit(&TIM_ICInitStructure);//将结构体中的内容缺省输入
     TIM_ICInitStructure.TIM_ICFilter = 6;  //选择输入比较滤波器 
     TIM_ICInit(TIM1, &TIM_ICInitStructure);//将TIM_ICInitStructure中的指定参数初始化TIM3
     
     //Reset counter
     TIM1->CNT = 0;//
     TIM_Cmd(TIM1, ENABLE);   //启动TIM1定时器
    
  2. 编码器检测
    需要用一个定时器记录时间来判断旋转快慢,定义为1ms记录一次,tim3_cnt4 为计数值。

     #define CMP_VALUE    (500)
     #define FAST_RANK_2  (200)
     #define FAST_RANK_1  (30)
     uint8_t g_enc_fast_flag;
    
     uint16_t Encoder_Process(void)
     {
     	static uint8_t flag = false; 
     	uint16_t enc_value;
     
     	if(TIM1->CNT == CMP_VALUE)//未旋转
     	{
     		flag = false;//清标志
     		g_enc_fast_flag = 0;
     
     		return 0;
     	}
     
     	if(TIM1->CNT > CMP_VALUE)// 向右
     	{
     		enc_value = BIT2;// 自己定义一个标志是代表向右的方向
     		TIM1->CNT = CMP_VALUE;
     
     	}else if(TIM1->CNT < CMP_VALUE){// 向左
     
     		enc_value = BIT0;;// 自己定义一个标志是代表向左的方向
     		TIM1->CNT = CMP_VALUE;
     	}
     
     	if(!flag)// 表示这次检测到了向左或向右
     	{
     		flag = true;
     		tim3_cnt4 = 0; // timer清0开始计时
     
     		return enc_value;// 返回旋转值
     	}
     
     	if(tim3_cnt4 < FAST_RANK_2)// 如果在限定时间内,认为是快旋
     	{
     		g_enc_fast_flag = 2;// 快旋标志
     
     		if(tim3_cnt4 <= FAST_RANK_1) // 如果时间更短, 表示旋转极快
     		{
     			g_enc_fast_flag = 1;// 极快标志
     		}
     
     		tim3_cnt4 = 0;// timer清0再次开始计时
     
     	}else{
     	
     		g_enc_fast_flag = 0; // 正常旋转速度
     	}
     
     	return enc_value; // 返回旋转值
     }
    

最后就是处理旋钮值了

你可能感兴趣的:(单片机)