[STM32] TIM编码器接口

编码器接口简介:

• Encoder Interface 编码器接口
• 编码器接口可接收增量(正交)编码器的信号,根据编码器旋转产生的正交信号 脉冲,自动控制CNT自增或自减,从而指示编码器的位置、旋转方向和旋转速度
• 每个高级定时器和通用定时器都拥有1个编码器接口
• 两个输入引脚借用了输入捕获的通道1和通道2

正交编码器:

• 正交编码器一般可以测量位置,或者带有方向的速度值
在这里插入图片描述

正交编码器的旋转方向和旋转速度:

• 正交编码器的旋转速度:任意一相的信号的频率的倒数就是速度
• 正交编码器的旋转方向: 在正转时,A相提前B相90度,反转时,A相滞后B相90度。正转时,是A相提前还是A相滞后,并不是绝对的,这是一个极性问题。总之就是朝一个方向转是A相提前,另一个方向转是A相滞后。

正交信号:

在这里插入图片描述

• 使用正交信号的优势: 首先就是正交信号的精度更高,因为A,B相都可以计次,相当于计次频率提高了一倍。其次正交信号抗噪声,因为正交信号,两个信号必须是交替跳变的,所以可以设置一个抗噪声电路,如果一个信号不变,另一个信号连续跳变,也就是产生了噪声,那这时计次值是不会变化的。

读取编码器:

当出现某个边沿,判断另一相的电平,如果对应另一相的状态出现在正转的表里,那就是正转,计数值自增。如果对应另一相的状态出现在反转的表里,那就是反转,计数值自减。

编码器接口:

• 编码器引脚详见这里

编码器接口通路:

在这里插入图片描述

编码器接口基本结构:

在这里插入图片描述
• 输入部分:输入捕获前两个通道,通过GPIO口接入编码器的A,B相,产生TI1FP1和TI2FP2通过编码器接口。
• 编码器接口:编码器接口通过预分频器控制CNT计数器的时钟,同时编码器接口还根据编码器的旋转方向,控制CNT的计数方向。编码器正转时,CNT自增,编码器反转时,CNT自减。
• ARR: 一般设为65535,最大量程,利用补码特性,很容易得到负数。

工作模式:

在这里插入图片描述

实例:

实例(均不反相):

在这里插入图片描述

实例(TI1反相)

在这里插入图片描述
• 将反相的信号取反,再查表

代码实现:

基本步骤:

第一步:RCC开启时钟,开启GPIO和定时器的时钟。
第二步:配置GPIO。(这里配置PA6和PA7)。
第三步:配置时基单元,这里预分频器一般选择不分频,ARR配置为最大65535。
第四步: 配置输入捕获单元。(只有滤波器和极性有用)。
第五步:配置编码器模式。
第六步:调用TIM_cmd,启动定时器。

编码器接口配置函数:

/**
  * @brief  配置TIMx编码器接口。
  * @param  TIMx: 选择TIMx,其中x可以是1、2、3、4、5或8来。
  * @param  TIM_EncoderMode: 指定TIMx的编码器接口模式。
  *   这个参数可以是下列值之一:
  *     @arg TIM_EncoderMode_TI1: 仅在TI1计数
  *     @arg TIM_EncoderMode_TI2: 仅在TI2计数
  *     @arg TIM_EncoderMode_TI12: 在TI1和TI2计数
  * @param  TIM_IC1Polarity: 指定IC1极性
  *   这个参数可以是下列值之一:
  *     @arg TIM_ICPolarity_Falling: 反向。
  *     @arg TIM_ICPolarity_Rising: 不反向。
  * @param  TIM_IC2Polarity: 指定IC2极性
  *   This parameter can be one of the following values:
  *     @arg TIM_ICPolarity_Falling: 反向。
  *     @arg TIM_ICPolarity_Rising: 不反向。
  * @retval None
  */
void TIM_EncoderInterfaceConfig(TIM_TypeDef* TIMx, uint16_t TIM_EncoderMode,uint16_t TIM_IC1Polarity, uint16_t TIM_IC2Polarity)

编码器接口计数:

Encoder.c:

void Encoder_Init()
{
///开启GPIO和定时器的时钟
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3,ENABLE);
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
配置GPIO/
	GPIO_InitTypeDef GPIO_InitStruct;
	GPIO_InitStruct.GPIO_Mode=GPIO_Mode_IPU;
	GPIO_InitStruct.GPIO_Pin=GPIO_Pin_6|GPIO_Pin_7;//	这里配置PA6和PA7
	GPIO_InitStruct.GPIO_Speed=GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStruct);
//配置时基单元///	
	TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
	TIM_TimeBaseInitStructure.TIM_ClockDivision=TIM_CKD_DIV1;
	TIM_TimeBaseInitStructure.TIM_CounterMode=TIM_CounterMode_Up;
	TIM_TimeBaseInitStructure.TIM_Period=65536 - 1;//ARR配置为最大65535。
	TIM_TimeBaseInitStructure.TIM_Prescaler=1 - 1;//这里预分频器一般选择不分频。
	TIM_TimeBaseInitStructure.TIM_RepetitionCounter=0;
	
	TIM_TimeBaseInit(TIM3,&TIM_TimeBaseInitStructure);
/配置输入捕获单元/
	//极性在配置编码器模式时配置
	TIM_ICInitTypeDef TIM_ICInitstructure;
	TIM_ICStructInit(&TIM_ICInitstructure);
	TIM_ICInitstructure.TIM_Channel=TIM_Channel_1;
	TIM_ICInitstructure.TIM_ICFilter=0xF;//只有滤波器有用
	TIM_ICInit(TIM3,&TIM_ICInitstructure);
	TIM_ICInitstructure.TIM_Channel=TIM_Channel_2;
	TIM_ICInitstructure.TIM_ICFilter=0xF;//只有滤波器有用
	TIM_ICInit(TIM3,&TIM_ICInitstructure);
配置编码器模式。//
	TIM_EncoderInterfaceConfig(TIM3,TIM_EncoderMode_TI12,TIM_ICPolarity_Rising,TIM_ICPolarity_Rising);//将TIM3的编码器接口的工作模式配置为在TI1和TI2计数,将IC1配置为不反向,将IC2配置为不反向。
启动定时器///	
	TIM_Cmd(TIM3,ENABLE);
}

uint16_t Encoder_Get(void)
{
	int16_t Temp;
	Temp= TIM_GetCounter(TIM3);//读取TIM3的CNT
	TIM_SetCounter(TIM3,0);	//清零TIM3的CNT
	return Temp;
}

main.c

#include "stm32f10x.h"                  // Device header
#include "Delay.h"
#include "LED.h"
#include "Key.h"
#include "OLED.h"
#include "Timer.h"
#include "Encoder.h"
int16_t Num=0;
 int main(void)
 {
		OLED_Init();//OLED初始化
		Encoder_Init();//TIM3编码器接口初始化
		OLED_ShowString(1,1,"Speed:");
		Timer_Init();//TIM2初始化
		while(1)
		{
			OLED_ShowSignedNum(1,70,Num,5);//显示编码器的速度
		}
 }
void TIM2_IRQHandler(void)//TIM2的中断,一秒一次
{
	if(TIM_GetITStatus(TIM2,TIM_IT_Update)==SET)
	{
		Num=Encoder_Get();//获取编码器的速度
		TIM_ClearITPendingBit(TIM2,TIM_IT_Update);
	}
}
  • 30
    点赞
  • 47
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值