diff --git a/Makefile b/Makefile index 2846746..54594ce 100644 --- a/Makefile +++ b/Makefile @@ -8,7 +8,7 @@ COMFLAGS=-g -Os -pedantic -Wall CFLAGS=$(COMFLAGS) -std=c99 -D_POSIX_C_SOURCE=200809L CXXFLAGS=$(COMFLAGS) -std=c++17 -OBJS = usb.o adc.o ringbuffer.o uart.o buttons.o printf.o +OBJS = usb.o adc.o ringbuffer.o uart.o buttons.o printf.o encoder.o BINARY ?= main DEVICE=STM32F405RG diff --git a/encoder.c b/encoder.c new file mode 100644 index 0000000..f0e0f61 --- /dev/null +++ b/encoder.c @@ -0,0 +1,74 @@ +#include +#include +#include +#include +#include +#include +#include "encoder.h" + +static volatile int pos; + +static void check(void); + +#define PIN1 GPIO4 +#define PIN1_IRQ NVIC_EXTI4_IRQ +#define PIN2 GPIO5 +#define PIN2_IRQ NVIC_EXTI9_5_IRQ + +void encoder_setup(void) { + rcc_periph_clock_enable(RCC_GPIOA); + + gpio_mode_setup(GPIOA, GPIO_MODE_INPUT, GPIO_PUPD_NONE, PIN1 | PIN2); + + /* Set up exti on A0 & A1 */ + exti_select_source(PIN1 | PIN2, GPIOA); + exti_set_trigger(PIN1 | PIN2, EXTI_TRIGGER_BOTH); + exti_enable_request(PIN1 | PIN2); + + nvic_enable_irq(PIN1_IRQ); + nvic_enable_irq(PIN2_IRQ); +} + +int encoder_get() { + return pos; +} + +static int prev = 0; +void check(void) { + int pp = pos; + int now = GPIO_IDR(GPIOA); + now = (!!(now & PIN1))<<0 | (!!(now & PIN2)) << 1; + + switch (prev << 2 | now) { + case 0 * 4 + 2: + case 1 * 4 + 0: + case 2 * 4 + 3: + case 3 * 4 + 1: + pos++; + break; + case 0 * 4 + 1: + case 1 * 4 + 3: + case 2 * 4 + 0: + case 3 * 4 + 2: + pos--; + break; + default: + prev = now; + return; + } + + prev = now; + if (pos < MIN_POS) + pos = MIN_POS; + if (pos > MAX_POS) + pos = MAX_POS; +} + +void exti4_isr(void) { + exti_reset_request(EXTI4); + check(); +} +void exti9_5_isr(void) { + exti_reset_request(EXTI5); + check(); +} diff --git a/encoder.h b/encoder.h new file mode 100644 index 0000000..d5fd2c5 --- /dev/null +++ b/encoder.h @@ -0,0 +1,11 @@ +#ifndef ENCODER_H +#define ENCODER_H +#define CLOSED_POS 220 +#define OPENED_POS 0 + +#define MAX_POS ((CLOSED_POS > OPENED_POS) ? CLOSED_POS : OPENED_POS) +#define MIN_POS ((CLOSED_POS < OPENED_POS) ? CLOSED_POS : OPENED_POS) + +void encoder_setup(void); +int encoder_get(void); +#endif