From 58c6c18733fb36a23e906e99df7f9a5956bb4a24 Mon Sep 17 00:00:00 2001 From: Lars-Dominik Braun Date: Tue, 8 Jul 2014 15:15:31 +0200 Subject: Coarse/fine selection modes --- ui.c | 157 +++++++++++++++++++++++++++++++++++++------------------------------ 1 file changed, 88 insertions(+), 69 deletions(-) (limited to 'ui.c') diff --git a/ui.c b/ui.c index 57c75c5..0bfe7ba 100644 --- a/ui.c +++ b/ui.c @@ -14,13 +14,6 @@ #include "pwm.h" #define sign(x) ((x < 0) ? -1 : 1) -/* 10 seconds */ -#define SELECT_M1_INC 10 -/* 1 minute steps for mode 2 */ -#define SELECT_M2_INC 60 -/* start of mode 2, seconds */ -#define SELECT_M2_START (5*60) -#define SELECT_MAX (60*60) /* stop alarm after #seconds */ #define ALARM_TIME 30 @@ -30,7 +23,8 @@ typedef enum { /* deep sleep */ UIMODE_SLEEP, /* select time */ - UIMODE_SELECT, + UIMODE_SELECT_COARSE, + UIMODE_SELECT_FINE, /* idle, showing time */ UIMODE_IDLE, /* count time */ @@ -41,7 +35,10 @@ typedef enum { static uimode mode = UIMODE_INIT; /* timer seconds */ -static int16_t seconds = 0; +static int16_t coarseSeconds = 0, fineSeconds = 0; +static uint8_t step = 0, substep = 0; +static uint16_t secPerSubstep = 0; +static uint16_t substepsec = 0; static horizon h = HORIZON_NONE; static bool horizonChanged = false; @@ -71,48 +68,53 @@ static uint8_t horizonLed (uint8_t i) { } } -/* - * We use the following LED coding (top to bottom): - * 1-5 minutes: (off) (5m ) (4m ) (3m ) (2m ) (1m ) - * 5-60 minutes: (on ) (50m) (40m) (30m) (20m) (10m) - */ -static void updateLeds () { - if (seconds <= SELECT_M2_START) { - const uint8_t minutes = seconds / 60; - for (uint8_t i = 0; i < minutes; i++) { - pwmSetBlink (horizonLed (i), PWM_BLINK_ON); - } - /* 10 second steps */ - pwmSetBlink (horizonLed (minutes), (seconds - minutes*60)/10); - for (uint8_t i = minutes+1; i < PWM_LED_COUNT; i++) { - pwmSetBlink (horizonLed (i), PWM_BLINK_OFF); - } +static int16_t limits (const int16_t in, const int16_t min, const int16_t max) { + if (in < min) { + return min; + } else if (in > max) { + return max; } else { - const uint8_t tenminutes = seconds/60/10; + return in; + } +} + +/* Timer value selection + */ +static void doSelectCoarse () { + if (accelGetShakeCount () >= 2) { + /* stop selection */ + accelResetShakeCount (); + mode = UIMODE_SELECT_FINE; + printf ("selectcoarse->selectfine(%i)\n", coarseSeconds); + return; + } + + /* use zticks as seconds */ + const int16_t zticks = gyroGetZTicks (); + if (abs (zticks) > 0) { + gyroResetZTicks (); + coarseSeconds = limits(coarseSeconds + zticks*60*5, 0, 60*60); + printf ("c:%it:%i\n", coarseSeconds, zticks); + + const uint8_t tenminutes = coarseSeconds/60/10; for (uint8_t i = 0; i < tenminutes; i++) { pwmSetBlink (horizonLed (i), PWM_BLINK_ON); } - /* 2 minute steps */ - pwmSetBlink (horizonLed (tenminutes), - (seconds - tenminutes*10*60)/60/2); - for (uint8_t i = tenminutes+1; i < PWM_LED_COUNT-1; i++) { + for (uint8_t i = tenminutes; i < PWM_LED_COUNT; i++) { pwmSetBlink (horizonLed (i), PWM_BLINK_OFF); } - pwmSetBlink (horizonLed (PWM_LED_COUNT-1), PWM_BLINK_ON); } } -/* Timer value selection - */ -static void doSelect () { +static void doSelectFine () { if (accelGetShakeCount () >= 2) { /* stop selection */ accelResetShakeCount (); + step = 6; + substep = 3; + secPerSubstep = (coarseSeconds + fineSeconds)/(6*3); mode = UIMODE_IDLE; - printf ("select->idle(%i)\n", seconds); - speakerStart (); - _delay_ms (50); - speakerStop (); + printf ("selectfine->idle(%u,%u)\n", coarseSeconds + fineSeconds, secPerSubstep); return; } @@ -120,33 +122,28 @@ static void doSelect () { const int16_t zticks = gyroGetZTicks (); if (abs (zticks) > 0) { gyroResetZTicks (); - if (seconds > SELECT_M2_START) { - const int16_t newseconds = seconds + sign (zticks) * SELECT_M2_INC; - /* when decrementing one minute steps might be too much */ - if (newseconds < SELECT_M2_START) { - seconds = SELECT_M2_START; - } else { - seconds = newseconds; - } - } else { - /* 10 second steps */ - seconds += sign (zticks) * SELECT_M1_INC; + fineSeconds = limits(fineSeconds + zticks*30, -5*60, 5*60); + printf ("f:%it:%i\n", fineSeconds, zticks); + + const uint8_t minutes = abs (fineSeconds)/60; + for (uint8_t i = 0; i < minutes; i++) { + pwmSetBlink (horizonLed (i), PWM_BLINK_ON); } - if (seconds < 0) { - seconds = 0; - } else if (seconds > SELECT_MAX) { - seconds = SELECT_MAX; + for (uint8_t i = minutes; i < PWM_LED_COUNT-1; i++) { + pwmSetBlink (horizonLed (i), PWM_BLINK_OFF); + } + if (fineSeconds < 0) { + pwmSetBlink (horizonLed (PWM_LED_COUNT-1), PWM_BLINK_ON); + } else { + pwmSetBlink (horizonLed (PWM_LED_COUNT-1), PWM_BLINK_OFF); } - printf ("%i\n", seconds); } - - updateLeds (); } /* Idle function, waits for timer start or select commands */ static void doIdle () { - if (horizonChanged && seconds > 0) { + if (horizonChanged) { /* start timer */ mode = UIMODE_RUN; timerStart (); @@ -157,7 +154,7 @@ static void doIdle () { } else if (accelGetShakeCount () >= 2) { /* set timer */ accelResetShakeCount (); - mode = UIMODE_SELECT; + mode = UIMODE_SELECT_COARSE; printf ("idle->select\n"); speakerStart (); _delay_ms (50); @@ -170,17 +167,33 @@ static void doIdle () { */ static void doRun () { if (timerHit ()) { - --seconds; - printf ("run: %i\n", seconds); - updateLeds (); - if (seconds == 0) { + ++substepsec; + if (substepsec > secPerSubstep) { + --substep; + substepsec = 0; + } + if (substep == 0) { + --step; + substep = 3; + substepsec = 0; + } + printf("s:%uss:%u\n", step, substep); + if (step == 0) { /* blink all leds */ for (uint8_t i = 0; i < PWM_LED_COUNT; i++) { pwmSetBlink (i, 1); } - seconds = ALARM_TIME; + step = ALARM_TIME; mode = UIMODE_ALARM; printf ("run->alarm\n"); + } else { + for (uint8_t i = 0; i < step-1; i++) { + pwmSetBlink (horizonLed (i), PWM_BLINK_ON); + } + pwmSetBlink (horizonLed (step-1), PWM_BLINK_ON); + for (uint8_t i = step; i < PWM_LED_COUNT; i++) { + pwmSetBlink (horizonLed (i), PWM_BLINK_OFF); + } } } else if (horizonChanged) { /* stop timer */ @@ -193,11 +206,11 @@ static void doRun () { */ static void doAlarm () { if (timerHit ()) { - --seconds; + --step; } - if (horizonChanged || seconds == 0) { + if (horizonChanged || step == 0) { timerStop (); - seconds = 0; + step = 0; /* stop blinking */ for (uint8_t i = 0; i < PWM_LED_COUNT; i++) { pwmSetBlink (i, PWM_BLINK_OFF); @@ -214,7 +227,9 @@ static void doInit () { if (h != HORIZON_NONE) { mode = UIMODE_IDLE; printf ("init->idle\n"); - updateLeds (); + for (uint8_t i = 0; i < PWM_LED_COUNT; i++) { + pwmSetBlink (horizonLed (i), PWM_BLINK_OFF); + } } } @@ -245,8 +260,12 @@ void uiLoop () { doInit (); break; - case UIMODE_SELECT: - doSelect (); + case UIMODE_SELECT_COARSE: + doSelectCoarse (); + break; + + case UIMODE_SELECT_FINE: + doSelectFine (); break; case UIMODE_IDLE: -- cgit v1.2.3