/** * TODO file description */ #include #include "main.h" #include "app_knob.h" #include "tim.h" #include "FreeRTOS.h" #include "queue.h" #include "timers.h" #include "cmsis_os2.h" #include "Gui/gui_event.h" extern osTimerId_t buttonPushTimerHandle; extern osTimerId_t buttonReleaseTimerHandle; static struct { uint16_t wheel; bool push; } s_knob = {}; void app_knob_init() { /* Enable the rotary encoder */ LL_TIM_CC_EnableChannel(TIM_KNOB, LL_TIM_CHANNEL_CH1 | LL_TIM_CHANNEL_CH2); LL_TIM_EnableCounter(TIM_KNOB); // for the change interrupt LL_TIM_EnableIT_CC1(TIM_KNOB); LL_TIM_EnableIT_CC2(TIM_KNOB); } uint16_t app_knob_get_raw() { return LL_TIM_GetCounter(TIM_KNOB); } static char buf[100]; void app_knob_turn_isr() { // TODO uint16_t old_wheel = s_knob.wheel; s_knob.wheel = LL_TIM_GetCounter(TIM_KNOB); int16_t wheel_change = (int16_t)(s_knob.wheel - old_wheel); BaseType_t yield = pdFALSE; while (wheel_change > 0) { wheel_change--; enum GuiEvent ev = GUI_EVENT_KNOB_PLUS; xQueueSendFromISR(guiEventQueHandle, &ev, &yield); } while (wheel_change < 0) { wheel_change++; enum GuiEvent ev = GUI_EVENT_KNOB_MINUS; xQueueSendFromISR(guiEventQueHandle, &ev, &yield); } portYIELD_FROM_ISR(yield); } // TODO use EXTI for push bool app_knob_pushed() { return 0 == LL_GPIO_IsInputPinSet(KNOB_PUSH_GPIO_Port, KNOB_PUSH_Pin); } void app_knob_push_isr(bool push) { PUTCHAR(push ? '#' : '.'); BaseType_t yield = pdFALSE; if (push) { xTimerStopFromISR(buttonReleaseTimerHandle, &yield); xTimerStopFromISR(buttonPushTimerHandle, &yield); xTimerChangePeriodFromISR(buttonPushTimerHandle, pdMS_TO_TICKS(10), &yield); } else { xTimerStopFromISR(buttonPushTimerHandle, &yield); xTimerStopFromISR(buttonReleaseTimerHandle, &yield); xTimerChangePeriodFromISR(buttonReleaseTimerHandle, pdMS_TO_TICKS(10), &yield); } portYIELD_FROM_ISR(yield); } void app_push_debounce(void *argument) { bool push = (bool) argument; enum GuiEvent ev = push ? GUI_EVENT_KNOB_PRESS : GUI_EVENT_KNOB_RELEASE; xQueueSend(guiEventQueHandle, &ev, pdMS_TO_TICKS(100)); }