1.1旋转编码器
旋转编码器概述:
1.光栅编码器
光栅编码器是一种利用光栅的光学特性来精确测量位移的装置。它由主光栅和指示光栅组成,物体移动使透过光栅的光发生变化,经光电探测器转换为电信号,通过计数脉冲确定位移量。具有高精度、高可靠性和快速响应等特点,广泛应用于工业和仪器仪表领域。然而,光栅编码器存在一些不足。它只能计算位置和速度,不能判断方向。在某些应用中,这可能会限制其使用。为了弥补这一缺陷,可以结合其他能够判断方向的旋转编码器,以提高测量的准确性和全面性。
2.旋转编码器
旋转编码器是一种用于测量旋转角度或位置的传感器。它通常由一个旋转轴和一个固定的外壳组成,内部包含了光学或磁性的编码元件。
旋转编码器可以产生正交波形,也称为 A 相和 B 相波形。这两个波形具有以下特点:
一、波形特征
-
相位差:
-
A 相和 B 相波形之间存在 90 度的相位差。这意味着当旋转编码器的轴旋转时,A 相和 B 相波形的上升沿和下降沿会交替出现,且相位相差四分之一周期。(见图2)
-
例如,当 A 相波形处于高电平时,B 相波形可能处于上升沿、下降沿或低电平状态,具体取决于旋转方向和编码器的分辨率。
-
-
脉冲数:
-
旋转编码器每旋转一圈,会产生一定数量的脉冲。这个脉冲数通常与编码器的分辨率有关。例如,一个分辨率为 1024 线的编码器,每旋转一圈会产生 1024 个脉冲。
-
A 相和 B 相波形的脉冲数是相同的,它们可以用来确定旋转的角度或位置。通过计数 A 相或 B 相波形的脉冲数,并结合相位差信息,可以确定旋转的方向。
-
3.霍尔传感器编码器
一、工作原理霍尔传感器编码器通常由一个磁体和多个霍尔元件组成。当磁体与霍尔元件之间发生相对运动时,霍尔元件会检测到磁场的变化,并产生相应的电信号。这些电信号可以被处理和解读,以确定旋转角度、线性位移或速度等参数。二、特点
-
非接触式测量:霍尔传感器编码器采用非接触式测量方式,不会对被测物体产生磨损,具有较高的可靠性和寿命。
-
高精度:能够提供高精度的测量结果,适用于对测量精度要求较高的场合。
-
快速响应:对运动的响应速度快,能够实时监测被测物体的运动状态。
4.独立编码器元件
独立编码器元件是一种可以独立工作的用于测量角度、位置、速度等物理量的电子元件。
一、结构组成
通常包括码盘(可以是光学码盘、磁性码盘等)、检测元件(如光电二极管、霍尔元件等)以及信号处理电路等部分。
输入轴转动,输出轴就会有波形。
旋转编码器硬件电路
编码器控制数值 代码实现
硬件电路接线
初始化代码
#include "stm32f10x.h" // Device header
int16_t Encoder_Count;
void Encoder_Init(void ){
//因为这里会产生90°的相位差,所以在A相低电平,B相下降沿的时候为正转
//在A相下降沿,B相低电平的时候才判断为反转
//第一步配置GPIO 跟 APIO 这里参考手册或是函数说明选择APBX
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode =GPIO_Mode_IPU;
GPIO_InitStructure.GPIO_Pin =GPIO_Pin_0 | GPIO_Pin_1;
GPIO_InitStructure.GPIO_Speed =GPIO_Speed_50MHz;
GPIO_Init(GPIOB,&GPIO_InitStructure);
//指定外部中断线,以及端口,想要哪个端口触发中断,根据信号线初始化端口选择GPIO_PinSourcex的参数
GPIO_EXTILineConfig(GPIO_PortSourceGPIOB,GPIO_PinSource0);
GPIO_EXTILineConfig(GPIO_PortSourceGPIOB,GPIO_PinSource1);
EXTI_InitTypeDef EXTI_InitStructure;
EXTI_InitStructure.EXTI_Line=EXTI_Line0 | EXTI_Line1;
EXTI_InitStructure.EXTI_LineCmd=ENABLE;
EXTI_InitStructure.EXTI_Mode=EXTI_Mode_Interrupt;
EXTI_InitStructure.EXTI_Trigger=EXTI_Trigger_Falling;
EXTI_Init(&EXTI_InitStructure);
//这里是两个端口,所以要分别进行优先级的设置
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
NVIC_InitTypeDef NVIC_InitStructure;
NVIC_InitStructure.NVIC_IRQChannel=EXTI0_IRQn;
NVIC_InitStructure.NVIC_IRQChannelCmd=ENABLE;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority=1;
NVIC_Init(&NVIC_InitStructure);
NVIC_InitStructure.NVIC_IRQChannel=EXTI1_IRQn;
NVIC_InitStructure.NVIC_IRQChannelCmd=ENABLE;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority=2;
NVIC_Init(&NVIC_InitStructure);
}
uint16_t Encoder_Get(void)
{
int16_t Key;
Key=Encoder_Count;
Encoder_Count = 0;
return Key;
}
//中断函数编写
void EXTI0_IRQHandler(void )
{
if(EXTI_GetITStatus(EXTI_Line0) == SET)
{
if(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_1) ==0)
{
Encoder_Count--;
}
EXTI_ClearITPendingBit(EXTI_Line0);//清除中断标志位
}
}
void EXTI1_IRQHandler(void )
{
if(EXTI_GetITStatus(EXTI_Line1) == SET)
{
if(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_0) ==0)
{
Encoder_Count++;
}
EXTI_ClearITPendingBit(EXTI_Line1);//清除中断标志位
}
}
主程序
#include "stm32f10x.h" // Device header
#include "OLED.h"
#include "Encoder.h"
int16_t Num;
int main(void)
{
OLED_Init();
OLED_ShowString(1,1,"Num:");
Encoder_Init();
while(1)
{
Num += Encoder_Get();
OLED_ShowSignedNum(1,5,Num,5);
}
}
实现效果
旋转编码器正转的时候数值增大,反之减小,另外这款编码器的sw 口(switch)还可以在按下的时候作为按键使用,有兴趣可以自行研究