cancel
Showing results for 
Search instead for 
Did you mean: 

STM32 HAL Nucleo F446RE Quadrature Encoder

Max Baeuml
Associate II
Posted on January 21, 2018 at 21:31

1

https://stackoverflow.com/questions/48361193/stm32-hal-nucleo-f446re-quadrature-encoder

i have a problem with the quadrature encoder mode on tim3.

1) tim3 counts on every rising edge on the first signal. the CNT register counts up and i read the value with 1hz and then i set the register to 0.

All looks good but...

When i look on the

oscilloscope

the frequency is half as big as the value from the

CNT register output (1hz).

if i devide the CNT value by two the result is correct.

0690X000006042VQAQ.jpg 0690X00000609N4QAI.png

Why?

2) tim3 counts on both edges on the first signal. the CNT register output (1hz) is completely wrong.

0690X00000609ReQAI.png

my config is:

GPIO_InitTypeDef sInitEncoderPin1;
sInitEncoderPin1.Pin = pin1Encoder.pin; // A GPIO_PIN_6 
sInitEncoderPin1.Mode = GPIO_MODE_AF_PP; 
sInitEncoderPin1.Pull = GPIO_PULLUP;
sInitEncoderPin1.Speed = GPIO_SPEED_HIGH; 
sInitEncoderPin1.Alternate = altFunctionEncoder; // GPIO_AF2_TIM3 
GPIO_InitTypeDef sInitEncoderPin2; 
sInitEncoderPin2.Pin = pin2Encoder.pin; // A GPIO_PIN_7 
sInitEncoderPin2.Mode = GPIO_MODE_AF_PP; 
sInitEncoderPin2.Pull = GPIO_PULLUP; 
sInitEncoderPin2.Speed = GPIO_SPEED_HIGH; 
sInitEncoderPin2.Alternate = altFunctionEncoder; // GPIO_AF2_TIM3 
HAL_GPIO_Init(GPIOA, &sInitEncoderPin1); 
HAL_GPIO_Init(GPIOA, &sInitEncoderPin2); 
encoderTimer.Init.Period = 0xffff; 
encoderTimer.Init.Prescaler = 0; 
encoderTimer.Init.CounterMode = TIM_COUNTERMODE_UP; 
encoderTimer.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1; 
encoderTimer.Init.RepetitionCounter = 0; 
HAL_NVIC_SetPriorityGrouping(NVIC_PRIORITYGROUP_4); 
HAL_NVIC_SetPriority(SysTick_IRQn, 0, 1); 
encoder.EncoderMode = TIM_ENCODERMODE_TI1; 
encoder.IC1Filter = 0x0f; 
encoder.IC1Polarity = TIM_INPUTCHANNELPOLARITY_RISING; // TIM_INPUTCHANNELPOLARITY_BOTHEDGE 
encoder.IC1Prescaler = TIM_ICPSC_DIV1; 
encoder.IC1Selection = TIM_ICSELECTION_DIRECTTI; 
encoder.IC2Filter = 0x0f; 
encoder.IC2Polarity = TIM_INPUTCHANNELPOLARITY_RISING; 
encoder.IC2Prescaler = TIM_ICPSC_DIV1; 
encoder.IC2Selection = TIM_ICSELECTION_DIRECTTI; 
HAL_TIM_Encoder_Init(&encoderTimer, &encoder); 
HAL_TIM_Encoder_Start_IT(&encoderTimer, TIM_CHANNEL_ALL);

#quadrature-encoder #tim-encoder ##stm32f4 #stm32-encoder #stm32cube-hal #f446re
3 REPLIES 3
Uwe Bonnes
Principal II
Posted on January 22, 2018 at 12:03

Look e.g. ath the timer cookbook AN4013, chapter 4.3.4 and learn about X4 and X2 encoder mode.

John Craven
Senior
Posted on January 22, 2018 at 16:05

0690X00000609RyQAI.png

using one input, your 1s sample should be 2

 x the

 scope freq

using two inputs, your 1s sample should be 4 x the scope freq

Posted on January 23, 2018 at 17:01

this was very helpful. i read the chapter 4.3.4 and i think that i have understand my problem.