4_Ust-vo_poluchenia_velichi.../Encoder.c

99 lines
3.5 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

// Включаем библиотеку для работы с портами ввода-вывода микроконтроллера AVR.
#include <avr/io.h>
// Определяем частоту процессора микроконтроллера в 1 МГц.
#define F_CPU 1000000UL
// Определяем бит в регистре PIND для сигнала с клока энкодера.
#define PIND_CLK 0b00010000
// Определяем бит в регистре PIND для сигнала с DT энкодера.
#define PIND_DT 0b01000000
volatile uint8_t encoder_state, prev_encoder_state, state = 1;
int sw34, pin_clk_2, pin_dt_2;
void read_encoder_state()
{
// Устанавливаем начальные значения переменных равное 0
pin_clk_2 = 0;
pin_dt_2 = 0;
// Устанавливаем значение PIN_CLK_2 в зависимости от установки бита PIND_CLK в PIND
pin_clk_2 = (PIND & PIND_CLK) ? 1 : 0;
// Устанавливаем значение PIN_DT_2 в зависимости от установки бита PIND_DT в PIND
pin_dt_2 = (PIND & PIND_DT) ? 1 : 0;
// Получаем состояние энкодера
// Определяем и сохраняем следующее состояние энкодера
encoder_state = (pin_clk_2 << 1) | pin_dt_2;
// Проверяем, изменилось ли состояние энкодера
if (encoder_state != prev_encoder_state)
{
switch (encoder_state)
{
case 0: // Поворот против часовой стрелки (CCW)
if (prev_encoder_state == 3)
state++;
else if (prev_encoder_state == 0)
state--;
break;
case 1: // Поворот по часовой стрелке (CW)
if (prev_encoder_state == 1)
state++;
else if (prev_encoder_state == 2)
state--;
break;
case 2: // Поворот против часовой стрелки (CCW)
if (prev_encoder_state == 1)
state++;
else if (prev_encoder_state == 3)
state--;
break;
case 3: // Поворот по часовой стрелке (CW)
if (prev_encoder_state == 2)
state++;
else if (prev_encoder_state == 0)
state--;
break;
}
// Устанавливаем значение prev_encoder_state равным текущему состоянию энкодера
prev_encoder_state = encoder_state;
}
}
void encoder_setup()
{
// Инициализация последовательного порта
Serial.begin(9600);
// Настройка портов ввода-вывода
DDRD = 0x00;
PORTD = (PIND_CLK + PIND_DT);
}
uint8_t encoder_value()
{
// Читаем состояние энкодера
read_encoder_state();
// Если состояние энкодера изменилось, выводим его в последовательный порт
if (state != sw34)
{
//Serial.println(state);
sw34 = state;
return state;
}
}
void setup()
{
encoder_setup();
}
void loop()
{
//encoder_value();
Serial.println(encoder_value());
}