Charles Young's development fork. Going forward I only want to push mature code to main repository.
Fork of GEO_COUNTER_L432KC by
RotarySwitch.cpp
- Committer:
- charlesdavidyoung
- Date:
- 2018-09-05
- Revision:
- 26:166dbe6022e8
- Parent:
- 24:db7494389c03
- Child:
- 34:10550b327e3d
File content as of revision 26:166dbe6022e8:
/** * @author Charles Young * */ #include "RotarySwitch.hpp" // QEI class supports the mode wheel. In its most basic function it will tell // us which direction the wheel is moving (right or left) so that we can // use it to select the current mode. QEI Wheel(D12, D11, NC, 16); // Quadrature encoder #define CPM 0x01 #define CPS 0x02 #define PLS 0x04 #define VOLTS 0x08 #define CNT1 0x10 #define CNT2 0x20 #define HV 0x40 #define MENU 0x80 uint8_t LED_statuses[] = {CPM, CPS, PLS, VOLTS, CNT1, CNT2, HV, MENU}; RotarySwitch::RotarySwitch() { LED_status = CPM; LED_status_index = 0; WheelCurrent = 0; WheelPrevious = 0; QEPBpressed = false; WheelStateTimer = 0; LEDs_write(0x00); // initialize LEDs (CPM and CNT1 on) Wheel.reset(); } int RotarySwitch::GetPosition(void) { return LED_status_index; } //--------------------------------------------------------------------------- //Write to 74HC595 (LEDs) - Take care to avoid conflict with MAX7219 void RotarySwitch::LEDs_write(unsigned short data_val) { #define DT 1 // delay time in us for SPI emulation // Update 74HC595 shift registers unsigned short mask; SCK = 0; wait_us(DT); CS2 = 0; for(mask = 0x80; mask!= 0; mask>>= 1) { wait_us(DT); SCK = 0; if(mask & data_val) MOSI = 0; else MOSI = 1; wait_us(DT); SCK = 1; } SCK = 0; wait_us(DT); CS2 = 1; return; } void RotarySwitch::UpdateOutput() { // Blink mode LED if (WHEEL_SUBMODE_SELECT == currentWheelState) LEDs_write(0); if (WheelStateTimer) { WheelStateTimer++; if (++WheelStateTimer > WheelStateTimeout) { WheelStateMachine(WHEEL_Timeout); WheelStateTimer = 0; } } } float RotarySwitch::UpdateInput() { float direction = 0; // used to return direction of rotation if (WHEEL_INACTIVE == currentWheelState) LEDs_write(0); else LEDs_write(LED_statuses[LED_status_index]); // react to wheel if in proper state WheelCurrent = int(Wheel.getPulses()); if ( (WHEEL_MODE_SELECT == currentWheelState) || (WHEEL_SUBMODE_SELECT == currentWheelState)) { if (WheelCurrent > WheelPrevious) { if (WHEEL_MODE_SELECT == currentWheelState) LED_status_index = ++LED_status_index % sizeof(LED_statuses); direction = 1; } else if (WheelCurrent < WheelPrevious) { if (WHEEL_MODE_SELECT == currentWheelState) LED_status_index = --LED_status_index % sizeof(LED_statuses); direction = -1; } // Keep resetting WheelStateTimer as long as wheel is moving if (WheelPrevious != WheelCurrent) WheelStateTimer = 1; } WheelPrevious = WheelCurrent; // detect when wheel button is pressed but wait until it is released // before doing anything bool QEPBbutton = QEPB.read(); if ( (QEPBbutton) && (!QEPBpressed)) { QEPBpressed = true; } else if ( (!QEPBbutton) && (QEPBpressed)) { QEPBpressed = false; WheelStateMachine(WHEEL_Pressed); } return direction; } void RotarySwitch::WheelStateMachine(WheelStateEvent event) { switch (currentWheelState) { case WHEEL_INACTIVE: if (WHEEL_Pressed == event) { currentWheelState = WHEEL_MODE_SELECT; WheelStateTimer = 1; } break; case WHEEL_MODE_SELECT: if (WHEEL_Pressed == event) { currentWheelState = WHEEL_SUBMODE_SELECT; WheelStateTimer = 1; } else if (WHEEL_Timeout == event) currentWheelState = WHEEL_INACTIVE; break; case WHEEL_SUBMODE_SELECT: if (WHEEL_Pressed == event) { currentWheelState = WHEEL_MODE_SELECT; WheelStateTimer = 1; } else if (WHEEL_Timeout == event) currentWheelState = WHEEL_INACTIVE; break; default: break; } }