#include "Encoder.h" void DS_EncoderInitTim(DS_Encoder *Encoder, TIM_HandleTypeDef *hTim) { Encoder->hTim = hTim; Encoder->State = 0; HAL_TIM_Base_Start(hTim); } void DS_EncoderInit(DS_Encoder *Encoder, GPIO_TypeDef *PortEncSignal1, uint16_t PinEncSignal1, GPIO_TypeDef *PortEncSignal2, uint16_t PinEncSignal2) { Encoder->hTim = 0; Encoder->Direction = 0; Encoder->State = 0; Encoder->PrevTick = HAL_GetTick(); Encoder->PinEncSignal1 = PinEncSignal1; Encoder->PinEncSignal2 = PinEncSignal2; Encoder->PortEncSignal1 = PortEncSignal1; Encoder->PortEncSignal2 = PortEncSignal2; Encoder->ValueSignal1 = 0; Encoder->ValueSignal2 = 0; } void DS_EncoderUpdate(DS_Encoder *Encoder) { uint32_t CurrentTick = HAL_GetTick(); if ((CurrentTick - Encoder->PrevTick) < 1) return; Encoder->PrevTick = CurrentTick; //Обновление состояние первой сигнальной линии GPIO_PinState Pin1State = HAL_GPIO_ReadPin(Encoder->PortEncSignal1, Encoder->PinEncSignal1); if (Pin1State == GPIO_PIN_SET) { Encoder->ValueSignal1 = 1; } else { Encoder->ValueSignal1 = 0; } //Обновление состояние второй сигнальной линии GPIO_PinState Pin2State = HAL_GPIO_ReadPin(Encoder->PortEncSignal2, Encoder->PinEncSignal2); if (Pin2State == GPIO_PIN_SET) { Encoder->ValueSignal2 = 1; } else { Encoder->ValueSignal2 = 0; } //Рассчитываем в какую сторону повернули энкодер // Если на первой линии высокий уровень, а на второй линии - низкий, то вращаем в одну сторону if(Encoder->ValueSignal1 == 1 && Encoder->ValueSignal2 == 0) { Encoder->Direction = 1; } // Если на первой линии низкий уровень, а на второй линии - высокий, то вращаем в другую сторону if(Encoder->ValueSignal1 == 0 && Encoder->ValueSignal2 == 1) { Encoder->Direction = -1; } // как определились с направлением - ждём когда оба сигнала поднимутся в высокий уровень, фиксируем шаг, и сбрасываем флаг направления. if(Encoder->Direction != 0 && Encoder->ValueSignal1 == 1 && Encoder->ValueSignal2 == 1) { Encoder->State = Encoder->State + Encoder->Direction; Encoder->Direction = 0; } } int8_t DS_EncoderGetState(DS_Encoder *Encoder) { if (Encoder->hTim != 0) { int8_t CurrentCounter = Encoder->hTim->Instance->CNT / 4; int8_t ValueToReturn = CurrentCounter - Encoder->State; Encoder->State = CurrentCounter; return ValueToReturn; } else { int8_t ValueToReturn = Encoder->State; Encoder->State = 0; return ValueToReturn; } }