文章目录

旋转编码器介绍主程序逻辑直接检测用外部中断检测下降沿定时器直接解码旋转编码器STM32中文参考手册V10.pdf定时器的编码器模式TIM2定时器编码器程序TIM3定时器编码器程序TIM4定时器编码器程序

旋转编码器介绍

旋转编码器简单来说,就是会输出2个PWM,依据相位可以知道旋转方向,依据脉冲个数可以知道旋转的角度。一般旋转一圈有一个固定数值的脉冲个数。 旋转编码器广泛用于电机、或者角度传感器,STM32的定时器可以直接接入这两个波形获取到信息。

前两个引脚(接地和Vcc)用于为编码器供电,我这里采用3.3V的供电。除了以顺时针方向和逆时针方向旋转旋钮外,编码器还有一个开关(低电平有效),按下内部的旋钮可以按下该开关。来自此开关的信号通过引脚3(Switch)获得。最后它有两个输出引脚。

主程序逻辑直接检测

主程序中不要加延时,否则可能检测不到下降沿。

//旋转编码器 //CLK–PA0 //DT—PA1 //SW—PA2

3.3V供电。

#include "sys.h"

#include "usart.h"

//旋转编码器

//CLK--PA0

//DT---PA1

//SW---PA2

#define CLK_in PAin(0)

#define DT_in PAin(1)

#define SW_in PAin(2)

u32 encoder_cnt = 100000;//旋转脉冲计数

u8 direction = 0;//旋转方向 1正传

u8 dt_high_flag = 0;

void rotary_encoder_Init(void) {

GPIO_InitTypeDef GPIO_InitStructure;

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); /* 使能时钟 */

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2;

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; /* 设置成上拉输入 */

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //IO口速度为50MHz

GPIO_Init(GPIOA, &GPIO_InitStructure); //根据设定参数初始化PC13

}

int main(void) {

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); /* 设置NVIC中断分组2:2位抢占优先级,2位响应优先级 */

delay_init(); /* 延时函数初始化 */

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);

GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable, ENABLE); /* 关闭jtag,使能SWD,可以用SWD模式调试 */

delay_ms(500); /* 等待稳定 */

uart_init(115200);

rotary_encoder_Init();

while (1) {

if (SW_in == 0) {

delay_ms(10);

if (SW_in == 0) {

printf("SW_in=0\r\n");

while (SW_in == 0);

}

}

//DT_in是下降沿的时候,如果CLK_in是高电平,那么就是正转,如果CLK_in是低电平,那么就是反转

if (DT_in == 1 && dt_high_flag == 0) {

dt_high_flag = 1;

}

if (DT_in == 0 && dt_high_flag == 1) {

dt_high_flag = 0;

if (CLK_in == 1) {

direction = 0;

} else {

direction = 1;

}

if (direction == 1) {

encoder_cnt++;

} else {

encoder_cnt--;

}

printf("direction=%d\r\n", (int) direction);

printf("encoder_cnt=%d\r\n", encoder_cnt);

}

}

}

顺时针转一圈可以得到一些结果,这个旋钮有明显的触感。顺时针转一个刻度就加1,逆时针转一个刻度就减1。

direction=1

encoder_cnt=100001

direction=1

encoder_cnt=100002

direction=1

encoder_cnt=100003

direction=1

encoder_cnt=100004

direction=1

encoder_cnt=100005

direction=1

encoder_cnt=100006

direction=1

encoder_cnt=100007

direction=1

encoder_cnt=100008

direction=1

encoder_cnt=100009

direction=0

encoder_cnt=100008

direction=1

encoder_cnt=100009

direction=1

encoder_cnt=100010

direction=1

encoder_cnt=100011

direction=1

encoder_cnt=100012

direction=1

encoder_cnt=100013

direction=1

encoder_cnt=100014

direction=1

encoder_cnt=100015

direction=1

encoder_cnt=100016

direction=1

encoder_cnt=100017

direction=1

encoder_cnt=100018

direction=1

encoder_cnt=100019

direction=1

encoder_cnt=100020

用外部中断检测下降沿

将DT输入设置为外部中断 ,下降沿触发,明显好用多了。

#include "sys.h"

#include "usart.h"

//旋转编码器

//CLK--PA0

//DT---PA1

//SW---PA2

#define CLK_in PAin(0)

#define DT_in PAin(1)

#define SW_in PAin(2)

u32 encoder_cnt = 100000;//旋转脉冲计数

u8 direction = 0;//旋转方向 1正传

u8 dt_high_flag = 0;

void rotary_encoder_Init(void) {

EXTI_InitTypeDef EXTI_InitStructure;

NVIC_InitTypeDef NVIC_InitStructure;

GPIO_InitTypeDef GPIO_InitStructure;

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); /* 使能时钟 */

GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable, ENABLE); /* 关闭JTAG功能 */

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); /* 使能时钟 */

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2;

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; /* 设置成上拉输入 */

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //IO口速度为50MHz

GPIO_Init(GPIOA, &GPIO_InitStructure);

//将DT_in PAin(1)设置为外部中断,下降沿触发

GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource1);

EXTI_InitStructure.EXTI_Line = EXTI_Line1; /* 外部中断线1 */

EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; /* 设置为中断请求 */

EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling; /* 下降沿触发 */

EXTI_InitStructure.EXTI_LineCmd = ENABLE; /* 使能中断 */

EXTI_Init(&EXTI_InitStructure); /* 配置 */

NVIC_InitStructure.NVIC_IRQChannel = EXTI1_IRQn; /* 外部中断1 */

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02; /* 抢占优先级2 */

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02; /* 子优先级2 */

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; /* 使能中断 */

NVIC_Init(&NVIC_InitStructure); /* 配置 */

}

void EXTI1_IRQHandler(void) {

if (CLK_in == 1) {

direction = 0;

} else {

direction = 1;

}

if (direction == 1) {

encoder_cnt++;

} else {

encoder_cnt--;

}

printf("direction=%d\r\n", (int) direction);

printf("encoder_cnt=%d\r\n", encoder_cnt);

EXTI_ClearITPendingBit(EXTI_Line1); /* 清除LINE1上的中断标志位 */

}

int main(void) {

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); /* 设置NVIC中断分组2:2位抢占优先级,2位响应优先级 */

delay_init(); /* 延时函数初始化 */

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);

GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable, ENABLE); /* 关闭jtag,使能SWD,可以用SWD模式调试 */

delay_ms(500); /* 等待稳定 */

uart_init(115200);

rotary_encoder_Init();

while (1) {

if (SW_in == 0) {

delay_ms(10);

if (SW_in == 0) {

printf("SW_in=0\r\n");

while (SW_in == 0);

}

}

}

}

当然需要记得添加库文件:

定时器直接解码旋转编码器

下图是定时器相关引脚:

STM32中文参考手册V10.pdf

普通定时器TIM2~TIM5都有这样的功能:

定时器的编码器模式

这张图是很重要的,如果我们这样配置:

TIM_EncoderInterfaceConfig(TIM2, TIM_EncoderMode_TI1, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式1

TIM_EncoderMode_TI1就是编码模式,TIM_ICPolarity_Rising和TIM_ICPolarity_Rising就是信号捕获边沿选择。

这张图告诉我们,编码器接收到AB相位是要同步的时候才会计数,有毛刺编码器是不会计数的。

而且还告诉我们,编码器顺时针旋转,逆时针旋转,我们的计数器是会对应增加或者减小的。

TIM2定时器编码器程序

#include "sys.h"

#include "usart.h"

//旋转编码器

//CLK--PA0

//DT---PA1

#define CLK_in PAin(0)

#define DT_in PAin(1)

/**************************************************************************

函数功能:把TIM2初始化为编码器接口模式

**************************************************************************/

void Encoder_Init_TIM2(u16 arr, u16 psc) {

GPIO_InitTypeDef GPIO_InitStructure;

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;

TIM_ICInitTypeDef TIM_ICInitStructure;

NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);//使能TIM4时钟

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1; //选择你要设置的IO口

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //设置传输速率

GPIO_Init(GPIOA, &GPIO_InitStructure); /* 初始化GPIO */

TIM_TimeBaseStructure.TIM_Period = arr; //自动装载值

TIM_TimeBaseStructure.TIM_Prescaler = psc; //分频系数

TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;

TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //设置向上计数模式

TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);

TIM_ICInitStructure.TIM_Channel = TIM_Channel_1; //通道1

TIM_ICInitStructure.TIM_ICFilter = 0x03; //滤波

TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_BothEdge;

TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1; //分频系数

TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//PA0直接映射到TI1

TIM_ICInit(TIM2, &TIM_ICInitStructure);

TIM_ICInitStructure.TIM_Channel = TIM_Channel_2; //通道1

TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//PA1直接映射到TI2

TIM_ICInit(TIM2, &TIM_ICInitStructure);

NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn;//中断通道

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 3;//抢占优先级

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; //子优先级

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道使能

NVIC_Init(&NVIC_InitStructure);

TIM_EncoderInterfaceConfig(TIM2, TIM_EncoderMode_TI1, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式1

//TIM_EncoderInterfaceConfig(TIM2, TIM_EncoderMode_TI12, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式3

TIM_ICStructInit(&TIM_ICInitStructure); //将结构体中的内容缺省输入

TIM_ICInitStructure.TIM_ICFilter = 10;

TIM_ICInit(TIM2, &TIM_ICInitStructure);

TIM_ClearFlag(TIM2, TIM_FLAG_Update);//清除TIM的更新标志位

TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE);//运行更新中断

TIM_SetCounter(TIM2, 10000);//初始化计数器初值

TIM_Cmd(TIM2, ENABLE); //使能定时器

}

// 计数超过arr就会产生溢出中断

// 也可以把NVIC_Init(&NVIC_InitStructure);注释掉就不要开启中断

void TIM2_IRQHandler(void) {

if (TIM2->SR & 0X0001)//溢出中断

{

printf("interrupt\r\n");

}

TIM2->SR &= ~(1 << 0);//清除中断标志位

}

short Read_Encoder(u8 TIMX) {

unsigned Encoder_TIM;

switch (TIMX) {

case 2:

Encoder_TIM = (short) TIM2->CNT;

TIM2->CNT = 0;

break;

case 3:

Encoder_TIM = (short) TIM3->CNT;

TIM3->CNT = 0;

break;

case 4:

Encoder_TIM = (short) TIM4->CNT;

break;

default:

Encoder_TIM = 0;

}

return Encoder_TIM;

}

int main(void) {

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); /* 设置NVIC中断分组2:2位抢占优先级,2位响应优先级 */

delay_init(); /* 延时函数初始化 */

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);

GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable, ENABLE); /* 关闭jtag,使能SWD,可以用SWD模式调试 */

delay_ms(500); /* 等待稳定 */

uart_init(115200);

Encoder_Init_TIM2(0xffff, 0); //初始化TIM2为编码器接口模式

while (1) {

printf("%d \r\n", (int) TIM_GetCounter(TIM2));

}

}

旋转编码器就可以看到计数器的变化了:

TIM3定时器编码器程序

类似地写程序即可。

#include "sys.h"

#include "usart.h"

//旋转编码器

//CLK--PA6

//DT---PA7

#define CLK_in PAin(6)

#define DT_in PAin(7)

/**************************************************************************

函数功能:把TIM3初始化为编码器接口模式

**************************************************************************/

void Encoder_Init_TIM3(u16 arr, u16 psc) {

GPIO_InitTypeDef GPIO_InitStructure;

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;

TIM_ICInitTypeDef TIM_ICInitStructure;

NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);//使能TIM4时钟

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7; //选择你要设置的IO口

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //设置传输速率

GPIO_Init(GPIOA, &GPIO_InitStructure); /* 初始化GPIO */

TIM_TimeBaseStructure.TIM_Period = arr; //自动装载值

TIM_TimeBaseStructure.TIM_Prescaler = psc; //分频系数

TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;

TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //设置向上计数模式

TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);

TIM_ICInitStructure.TIM_Channel = TIM_Channel_1; //通道1

TIM_ICInitStructure.TIM_ICFilter = 0x03; //滤波

TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_BothEdge;

TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1; //分频系数

TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//PA6直接映射到TI1

TIM_ICInit(TIM3, &TIM_ICInitStructure);

TIM_ICInitStructure.TIM_Channel = TIM_Channel_2; //通道1

TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//PA7直接映射到TI2

TIM_ICInit(TIM3, &TIM_ICInitStructure);

NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;//中断通道

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 3;//抢占优先级

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; //子优先级

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道使能

NVIC_Init(&NVIC_InitStructure);

TIM_EncoderInterfaceConfig(TIM3, TIM_EncoderMode_TI1, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式1

//TIM_EncoderInterfaceConfig(TIM3, TIM_EncoderMode_TI12, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式3

TIM_ICStructInit(&TIM_ICInitStructure); //将结构体中的内容缺省输入

TIM_ICInitStructure.TIM_ICFilter = 10;

TIM_ICInit(TIM3, &TIM_ICInitStructure);

TIM_ClearFlag(TIM3, TIM_FLAG_Update);//清除TIM的更新标志位

TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);//运行更新中断

TIM_SetCounter(TIM3, 10000);//初始化计数器初值

TIM_Cmd(TIM3, ENABLE); //使能定时器

}

// 计数超过arr就会产生溢出中断

// 也可以把NVIC_Init(&NVIC_InitStructure);注释掉就不要开启中断

void TIM3_IRQHandler(void) {

if (TIM3->SR & 0X0001)//溢出中断

{

printf("interrupt\r\n");

}

TIM3->SR &= ~(1 << 0);//清除中断标志位

}

short Read_Encoder(u8 TIMX) {

unsigned Encoder_TIM;

switch (TIMX) {

case 2:

Encoder_TIM = (short) TIM2->CNT;

TIM2->CNT = 0;

break;

case 3:

Encoder_TIM = (short) TIM3->CNT;

TIM3->CNT = 0;

break;

case 4:

Encoder_TIM = (short) TIM4->CNT;

break;

default:

Encoder_TIM = 0;

}

return Encoder_TIM;

}

int main(void) {

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); /* 设置NVIC中断分组2:2位抢占优先级,2位响应优先级 */

delay_init(); /* 延时函数初始化 */

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);

GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable, ENABLE); /* 关闭jtag,使能SWD,可以用SWD模式调试 */

delay_ms(500); /* 等待稳定 */

uart_init(115200);

Encoder_Init_TIM3(0xffff, 0); //初始化TIM2为编码器接口模式

while (1) {

printf("%d \r\n", (int) TIM_GetCounter(TIM3));

}

}

TIM4定时器编码器程序

类似地写程序即可。

#include "sys.h"

#include "usart.h"

//旋转编码器

//CLK--PB6

//DT---PB7

#define CLK_in PBin(6)

#define DT_in PBin(7)

/**************************************************************************

函数功能:把TIM4初始化为编码器接口模式

**************************************************************************/

void Encoder_Init_TIM4(u16 arr, u16 psc) {

GPIO_InitTypeDef GPIO_InitStructure;

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;

TIM_ICInitTypeDef TIM_ICInitStructure;

NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);//使能TIM4时钟

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7; //选择你要设置的IO口

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //设置传输速率

GPIO_Init(GPIOB, &GPIO_InitStructure); /* 初始化GPIO */

TIM_TimeBaseStructure.TIM_Period = arr; //自动装载值

TIM_TimeBaseStructure.TIM_Prescaler = psc; //分频系数

TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;

TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //设置向上计数模式

TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure);

TIM_ICInitStructure.TIM_Channel = TIM_Channel_1; //通道1

TIM_ICInitStructure.TIM_ICFilter = 0x03; //滤波

TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_BothEdge;

TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1; //分频系数

TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//PA6直接映射到TI1

TIM_ICInit(TIM4, &TIM_ICInitStructure);

TIM_ICInitStructure.TIM_Channel = TIM_Channel_2; //通道1

TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//PA7直接映射到TI2

TIM_ICInit(TIM4, &TIM_ICInitStructure);

NVIC_InitStructure.NVIC_IRQChannel = TIM4_IRQn;//中断通道

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 3;//抢占优先级

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; //子优先级

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道使能

NVIC_Init(&NVIC_InitStructure);

TIM_EncoderInterfaceConfig(TIM4, TIM_EncoderMode_TI1, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式1

//TIM_EncoderInterfaceConfig(TIM4, TIM_EncoderMode_TI12, TIM_ICPolarity_Rising, TIM_ICPolarity_Rising);//使用编码器模式3

TIM_ICStructInit(&TIM_ICInitStructure); //将结构体中的内容缺省输入

TIM_ICInitStructure.TIM_ICFilter = 10;

TIM_ICInit(TIM4, &TIM_ICInitStructure);

TIM_ClearFlag(TIM4, TIM_FLAG_Update);//清除TIM的更新标志位

TIM_ITConfig(TIM4, TIM_IT_Update, ENABLE);//运行更新中断

TIM_SetCounter(TIM4, 10000);//初始化计数器初值

TIM_Cmd(TIM4, ENABLE); //使能定时器

}

// 计数超过arr就会产生溢出中断

// 也可以把NVIC_Init(&NVIC_InitStructure);注释掉就不要开启中断

void TIM4_IRQHandler(void) {

if (TIM4->SR & 0X0001)//溢出中断

{

printf("interrupt\r\n");

}

TIM4->SR &= ~(1 << 0);//清除中断标志位

}

int main(void) {

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); /* 设置NVIC中断分组2:2位抢占优先级,2位响应优先级 */

delay_init(); /* 延时函数初始化 */

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);

GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable, ENABLE); /* 关闭jtag,使能SWD,可以用SWD模式调试 */

delay_ms(500); /* 等待稳定 */

uart_init(115200);

Encoder_Init_TIM4(0xffff, 0); //初始化TIM2为编码器接口模式

while (1) {

printf("%d \r\n", (int) TIM_GetCounter(TIM4));

}

}

参考阅读

评论可见,请评论后查看内容,谢谢!!!
 您阅读本篇文章共花了: