From 268b2deacc7b65c7d9d2805d1e504cf94f5734ac Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Fri, 12 Oct 2018 16:16:02 -0600
Subject: Moved "off" mode's aux LED to config to "7 clicks from off".
---
spaghetti-monster/anduril/anduril.c | 33 ++++++++++++++++++++++++++++++---
1 file changed, 30 insertions(+), 3 deletions(-)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index 6e33610..300e32b 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -139,13 +139,20 @@
#define RAMP_LENGTH 150 // default, if not overridden in a driver cfg file
#define MAX_BIKING_LEVEL 120 // should be 127 or less
#define USE_BATTCHECK
-#ifdef USE_MUGGLE_MODE
+
+// determine the highest number of clicks to handle
+#ifdef USE_INDICATOR_LED
+#define MAX_CLICKS 7
+#elif defined(USE_MUGGLE_MODE)
#define MAX_CLICKS 6
-#define MUGGLE_FLOOR 22
-#define MUGGLE_CEILING (MAX_1x7135+20)
#else
#define MAX_CLICKS 5
#endif
+
+#if defined(USE_MUGGLE_MODE)
+#define MUGGLE_FLOOR 22
+#define MUGGLE_CEILING (MAX_1x7135+20)
+#endif
#define USE_IDLE_MODE // reduce power use while awake and no tasks are pending
#define USE_DYNAMIC_UNDERCLOCKING // cut clock speed at very low modes for better efficiency
@@ -488,6 +495,24 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
return MISCHIEF_MANAGED;
}
#endif
+ #ifdef USE_INDICATOR_LED
+ // 7 clicks: change indicator LED mode
+ else if (event == EV_7clicks) {
+ uint8_t mode = (indicator_led_mode & 3) + 1;
+ #ifdef TICK_DURING_STANDBY
+ mode = mode & 3;
+ #else
+ mode = mode % 3;
+ #endif
+ #ifdef INDICATOR_LED_SKIP_LOW
+ if (mode == 1) { mode ++; }
+ #endif
+ indicator_led_mode = (indicator_led_mode & 0b11111100) | mode;
+ indicator_led(mode);
+ save_config();
+ return MISCHIEF_MANAGED;
+ }
+ #endif
return EVENT_NOT_HANDLED;
}
@@ -1198,6 +1223,7 @@ uint8_t lockout_state(EventPtr event, uint16_t arg) {
save_config();
return MISCHIEF_MANAGED;
}
+ #if 0 // old method, deprecated in favor of "7 clicks from off"
// click, click, hold: rotate through indicator LED modes (off mode)
else if (event == EV_click3_hold) {
#ifndef USE_INDICATOR_LED_WHILE_RAMPING
@@ -1230,6 +1256,7 @@ uint8_t lockout_state(EventPtr event, uint16_t arg) {
return MISCHIEF_MANAGED;
}
#endif
+ #endif
// 4 clicks: exit
else if (event == EV_4clicks) {
blink_confirm(1);
--
cgit v1.2.3
From 565fb109ec5e7cf195914834523b1723da374e40 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Mon, 15 Oct 2018 15:08:17 -0600
Subject: cleaned up fsm baton UI a little, added a short manual
---
spaghetti-monster/baton/baton-simpler.c | 40 +++++-------
spaghetti-monster/baton/baton.c | 112 ++++++++++++++++++--------------
spaghetti-monster/baton/baton.txt | 21 ++++++
3 files changed, 103 insertions(+), 70 deletions(-)
create mode 100644 spaghetti-monster/baton/baton.txt
diff --git a/spaghetti-monster/baton/baton-simpler.c b/spaghetti-monster/baton/baton-simpler.c
index 96b0ea7..d4725ef 100644
--- a/spaghetti-monster/baton/baton-simpler.c
+++ b/spaghetti-monster/baton/baton-simpler.c
@@ -20,7 +20,6 @@
#define FSM_EMISAR_D4_DRIVER
#define USE_LVP
#define USE_THERMAL_REGULATION
-#define DEFAULT_THERM_CEIL 45
#define USE_DELAY_MS
#include "spaghetti-monster.h"
@@ -59,6 +58,11 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
set_level(0);
return EVENT_HANDLED;
}
+ // hold (longer): go to lowest level
+ else if (event == EV_click1_hold) {
+ set_state(steady_state, 0);
+ return EVENT_HANDLED;
+ }
// 1 click (before timeout): go to memorized level, but allow abort for double click
else if (event == EV_click1_release) {
set_level(memorized_level);
@@ -79,11 +83,6 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
set_state(lockout_state, 0);
return EVENT_HANDLED;
}
- // hold: go to lowest level
- else if (event == EV_click1_hold) {
- set_state(steady_state, 0);
- return EVENT_HANDLED;
- }
return EVENT_NOT_HANDLED;
}
@@ -91,8 +90,8 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
// turn LED on when we first enter the mode
if (event == EV_enter_state) {
// remember this level, unless it's moon or turbo
- if ((arg > 0) && (arg < MAX_LEVEL))
- memorized_level = arg;
+ if ((arg > 0) && (arg < MAX_LEVEL)) memorized_level = arg;
+ // use the requested level even if not memorized
#ifdef USE_THERMAL_REGULATION
target_level = arg;
#endif
@@ -135,16 +134,12 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
#ifdef USE_THERMAL_REGULATION
// overheating: drop by 1 level
else if (event == EV_temperature_high) {
- if (actual_level > 1) {
- set_level(actual_level - 1);
- }
+ if (actual_level > 1) { set_level(actual_level - 1); }
return EVENT_HANDLED;
}
// underheating: increase by 1 level if we're lower than the target
else if (event == EV_temperature_low) {
- if (actual_level < target_level) {
- set_level(actual_level + 1);
- }
+ if (actual_level < target_level) { set_level(actual_level + 1); }
return EVENT_HANDLED;
}
#endif
@@ -152,18 +147,14 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
}
uint8_t lockout_state(EventPtr event, uint16_t arg) {
- // stay asleep while locked, but allow waking long enough to click 4 times
+ // stay asleep while locked
if (event == EV_tick) {
- static uint8_t ticks_spent_awake = 0;
- ticks_spent_awake ++;
- PWM1_LVL = 0; PWM2_LVL = 0;
- if (ticks_spent_awake > 3 * TICKS_PER_SECOND) {
- ticks_spent_awake = 0;
- go_to_standby = 1;
- }
+ PWM1_LVL = 0; PWM2_LVL = 0; // make sure emitters are off
+ // sleep 1 second after user stops pressing buttons
+ if (arg > TICKS_PER_SECOND) { go_to_standby = 1; }
return MISCHIEF_MANAGED;
}
- // 4 clicks: exit
+ // 4 clicks: exit, and turn on at "low" level
else if (event == EV_4clicks) {
set_state(steady_state, 1);
return MISCHIEF_MANAGED;
@@ -175,6 +166,9 @@ void low_voltage() {
// step down by one level or turn off
if (actual_level > 0) {
set_level(actual_level - 1);
+ #ifdef USE_THERMAL_REGULATION
+ target_level = actual_level; // don't let low temperature override LVP
+ #endif
}
else {
set_state(off_state, 0);
diff --git a/spaghetti-monster/baton/baton.c b/spaghetti-monster/baton/baton.c
index 1266ddd..59a7196 100644
--- a/spaghetti-monster/baton/baton.c
+++ b/spaghetti-monster/baton/baton.c
@@ -20,22 +20,17 @@
#define FSM_EMISAR_D4_DRIVER
#define USE_LVP
#define USE_THERMAL_REGULATION
-#define DEFAULT_THERM_CEIL 45
#define USE_DEBUG_BLINK
#define USE_DELAY_MS
#define USE_DELAY_4MS
#define USE_DELAY_ZERO
#include "spaghetti-monster.h"
-// moon + ../../bin/level_calc.py 2 6 7135 18 10 150 FET 1 10 1500
-uint8_t pwm1_modes[] = { 3, 18, 110, 255, 255, 255, 0, };
-uint8_t pwm2_modes[] = { 0, 0, 0, 9, 58, 138, 255, };
-#define MAX_LEVEL (sizeof(pwm1_modes)-1)
-
// FSM states
uint8_t off_state(EventPtr event, uint16_t arg);
uint8_t steady_state(EventPtr event, uint16_t arg);
uint8_t party_strobe_state(EventPtr event, uint16_t arg);
+uint8_t lockout_state(EventPtr event, uint16_t arg);
// brightness control
uint8_t memorized_level = 1;
@@ -44,93 +39,100 @@ uint8_t actual_level = 0;
uint8_t target_level = 0;
#endif
+// moon + ../../bin/level_calc.py 2 6 7135 18 10 150 FET 1 10 1500
+uint8_t pwm1_levels[] = { 3, 18, 110, 255, 255, 255, 0, };
+uint8_t pwm2_levels[] = { 0, 0, 0, 9, 58, 138, 255, };
+#define MAX_LEVEL (sizeof(pwm1_levels)-1)
+
+// set LED brightness
void set_level(uint8_t lvl) {
actual_level = lvl;
- PWM1_LVL = pwm1_modes[lvl];
- PWM2_LVL = pwm2_modes[lvl];
+ PWM1_LVL = pwm1_levels[lvl];
+ PWM2_LVL = pwm2_levels[lvl];
}
uint8_t off_state(EventPtr event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
- PWM1_LVL = 0;
- PWM2_LVL = 0;
- // sleep while off (lower power use)
- go_to_standby = 1;
- return 0;
+ go_to_standby = 1; // sleep while off (lower power use)
+ return EVENT_HANDLED;
}
// hold (initially): go to lowest level, but allow abort for regular click
else if (event == EV_click1_press) {
set_level(0);
- return 0;
+ return EVENT_HANDLED;
+ }
+ // hold (longer): go to lowest level
+ else if (event == EV_click1_hold) {
+ set_state(steady_state, 0);
+ return EVENT_HANDLED;
}
// 1 click (before timeout): go to memorized level, but allow abort for double click
else if (event == EV_click1_release) {
set_level(memorized_level);
- return 0;
+ return EVENT_HANDLED;
}
// 1 click: regular mode
else if (event == EV_1click) {
set_state(steady_state, memorized_level);
- return 0;
+ return EVENT_HANDLED;
}
// 2 clicks: highest mode
else if (event == EV_2clicks) {
set_state(steady_state, MAX_LEVEL);
- return 0;
+ return EVENT_HANDLED;
}
// 3 clicks: strobe mode
else if (event == EV_3clicks) {
set_state(party_strobe_state, 255);
- return 0;
+ return EVENT_HANDLED;
}
- // hold: go to lowest level
- else if (event == EV_click1_hold) {
- set_state(steady_state, 0);
- return 0;
+ // 4 clicks: soft lockout
+ else if (event == EV_4clicks) {
+ set_state(lockout_state, 0);
+ return EVENT_HANDLED;
}
- return 1;
+ return EVENT_NOT_HANDLED;
}
uint8_t steady_state(EventPtr event, uint16_t arg) {
// turn LED on when we first enter the mode
if (event == EV_enter_state) {
// remember this level, unless it's moon or turbo
- if ((arg > 0) && (arg < MAX_LEVEL))
- memorized_level = arg;
+ if ((arg > 0) && (arg < MAX_LEVEL)) memorized_level = arg;
// use the requested level even if not memorized
#ifdef USE_THERMAL_REGULATION
target_level = arg;
#endif
set_level(arg);
- return 0;
+ return EVENT_HANDLED;
}
// 1 click: off
else if (event == EV_1click) {
set_state(off_state, 0);
- return 0;
+ return EVENT_HANDLED;
}
// 2 clicks: go to/from highest level
else if (event == EV_2clicks) {
- if (actual_level < MAX_LEVEL) {
+ if (actual_level < MAX_LEVEL) { // go to turbo
memorized_level = actual_level; // in case we're on moon
#ifdef USE_THERMAL_REGULATION
target_level = MAX_LEVEL;
#endif
set_level(MAX_LEVEL);
}
- else {
+ else { // return from turbo
#ifdef USE_THERMAL_REGULATION
target_level = memorized_level;
#endif
set_level(memorized_level);
}
- return 0;
+ return EVENT_HANDLED;
}
// 3 clicks: go to strobe modes
else if (event == EV_3clicks) {
set_state(party_strobe_state, 0xff);
- return 0;
+ return EVENT_HANDLED;
}
// hold: change brightness
else if (event == EV_click1_hold) {
@@ -141,25 +143,21 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
#endif
set_level(memorized_level);
}
- return 0;
+ return EVENT_HANDLED;
}
#ifdef USE_THERMAL_REGULATION
// overheating: drop by 1 level
else if (event == EV_temperature_high) {
- if (actual_level > 1) {
- set_level(actual_level - 1);
- }
- return 0;
+ if (actual_level > 1) { set_level(actual_level - 1); }
+ return EVENT_HANDLED;
}
// underheating: increase by 1 level if we're lower than the target
else if (event == EV_temperature_low) {
- if (actual_level < target_level) {
- set_level(actual_level + 1);
- }
- return 0;
+ if (actual_level < target_level) { set_level(actual_level + 1); }
+ return EVENT_HANDLED;
}
#endif
- return 1;
+ return EVENT_NOT_HANDLED;
}
uint8_t party_strobe_state(EventPtr event, uint16_t arg) {
@@ -168,7 +166,7 @@ uint8_t party_strobe_state(EventPtr event, uint16_t arg) {
if (event == EV_enter_state) {
if (arg < 64) between = arg;
frames = 0;
- return 0;
+ return MISCHIEF_MANAGED;
}
// tick: strobe the emitter
else if (event == EV_tick) {
@@ -182,17 +180,17 @@ uint8_t party_strobe_state(EventPtr event, uint16_t arg) {
//frames = (frames + 1) % between;
frames++;
if (frames > between) frames = 0;
- return 0;
+ return MISCHIEF_MANAGED;
}
// 1 click: off
else if (event == EV_1click) {
set_state(off_state, 0);
- return 0;
+ return MISCHIEF_MANAGED;
}
// 2 clicks: go back to regular modes
else if (event == EV_2clicks) {
set_state(steady_state, memorized_level);
- return 0;
+ return MISCHIEF_MANAGED;
}
// hold: change speed
else if (event == EV_click1_hold) {
@@ -200,9 +198,25 @@ uint8_t party_strobe_state(EventPtr event, uint16_t arg) {
between = (between+1)%6;
frames = 0;
}
- return 0;
+ return MISCHIEF_MANAGED;
+ }
+ return EVENT_NOT_HANDLED;
+}
+
+uint8_t lockout_state(EventPtr event, uint16_t arg) {
+ // stay asleep while locked
+ if (event == EV_tick) {
+ PWM1_LVL = 0; PWM2_LVL = 0; // make sure emitters are off
+ // sleep 1 second after user stops pressing
+ if (arg > TICKS_PER_SECOND) { go_to_standby = 1; }
+ return MISCHIEF_MANAGED;
+ }
+ // 4 clicks: exit, and turn on at "low" level
+ else if (event == EV_4clicks) {
+ set_state(steady_state, 1);
+ return MISCHIEF_MANAGED;
}
- return 1;
+ return EVENT_NOT_HANDLED;
}
void low_voltage() {
@@ -214,6 +228,10 @@ void low_voltage() {
else if (current_state == steady_state) {
if (actual_level > 0) {
set_level(actual_level - 1);
+ #ifdef USE_THERMAL_REGULATION
+ target_level = actual_level; // don't let low temperature override LVP
+ #endif
+
}
else {
set_state(off_state, 0);
diff --git a/spaghetti-monster/baton/baton.txt b/spaghetti-monster/baton/baton.txt
new file mode 100644
index 0000000..2f0c22f
--- /dev/null
+++ b/spaghetti-monster/baton/baton.txt
@@ -0,0 +1,21 @@
+This is a very simple clone of the Olight Baton interface. It is not
+exact, but it has the basics. Mostly, it exists for the purposes of
+demonstrating how to create interfaces in FSM.
+
+While off:
+
+ - 1 click: Turn on (at memorized level).
+ - Hold: Turn on (at moon level).
+ - 2 clicks: Turn on (at highest level).
+ - 4 clicks: Soft lockout mode.
+
+While on:
+
+ - 1 click: Turn off.
+ - Hold: Change the brightness. Goes up in steps, then wraps around.
+ - 2 clicks: Go to/from highest level.
+
+While locked:
+
+ - 4 clicks: Exit lockout mode.
+
--
cgit v1.2.3
From fa9baf747b32e77e4a753dec99b7b6dc4795af1b Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Mon, 15 Oct 2018 15:09:34 -0600
Subject: removed more-complex baton UI (which only different by having a party
strobe mode), replaced it with the simpler version (since this UI exists
mostly as an example)
---
spaghetti-monster/baton/baton-simpler.c | 188 --------------------------------
spaghetti-monster/baton/baton.c | 86 +++------------
2 files changed, 13 insertions(+), 261 deletions(-)
delete mode 100644 spaghetti-monster/baton/baton-simpler.c
diff --git a/spaghetti-monster/baton/baton-simpler.c b/spaghetti-monster/baton/baton-simpler.c
deleted file mode 100644
index d4725ef..0000000
--- a/spaghetti-monster/baton/baton-simpler.c
+++ /dev/null
@@ -1,188 +0,0 @@
-/*
- * Baton: Olight Baton-like UI for SpaghettiMonster.
- *
- * Copyright (C) 2017 Selene ToyKeeper
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-#define FSM_EMISAR_D4_DRIVER
-#define USE_LVP
-#define USE_THERMAL_REGULATION
-#define USE_DELAY_MS
-#include "spaghetti-monster.h"
-
-// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
-uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t lockout_state(EventPtr event, uint16_t arg);
-
-// brightness control
-uint8_t memorized_level = 1;
-uint8_t actual_level = 0;
-#ifdef USE_THERMAL_REGULATION
-uint8_t target_level = 0;
-#endif
-
-// moon + ../../bin/level_calc.py 2 6 7135 18 10 150 FET 1 10 1500
-uint8_t pwm1_levels[] = { 3, 18, 110, 255, 255, 255, 0, };
-uint8_t pwm2_levels[] = { 0, 0, 0, 9, 58, 138, 255, };
-#define MAX_LEVEL (sizeof(pwm1_levels)-1)
-
-// set LED brightness
-void set_level(uint8_t lvl) {
- actual_level = lvl;
- PWM1_LVL = pwm1_levels[lvl];
- PWM2_LVL = pwm2_levels[lvl];
-}
-
-uint8_t off_state(EventPtr event, uint16_t arg) {
- // turn emitter off when entering state
- if (event == EV_enter_state) {
- go_to_standby = 1; // sleep while off (lower power use)
- return EVENT_HANDLED;
- }
- // hold (initially): go to lowest level, but allow abort for regular click
- else if (event == EV_click1_press) {
- set_level(0);
- return EVENT_HANDLED;
- }
- // hold (longer): go to lowest level
- else if (event == EV_click1_hold) {
- set_state(steady_state, 0);
- return EVENT_HANDLED;
- }
- // 1 click (before timeout): go to memorized level, but allow abort for double click
- else if (event == EV_click1_release) {
- set_level(memorized_level);
- return EVENT_HANDLED;
- }
- // 1 click: regular mode
- else if (event == EV_1click) {
- set_state(steady_state, memorized_level);
- return EVENT_HANDLED;
- }
- // 2 clicks: highest mode
- else if (event == EV_2clicks) {
- set_state(steady_state, MAX_LEVEL);
- return EVENT_HANDLED;
- }
- // 4 clicks: soft lockout
- else if (event == EV_4clicks) {
- set_state(lockout_state, 0);
- return EVENT_HANDLED;
- }
- return EVENT_NOT_HANDLED;
-}
-
-uint8_t steady_state(EventPtr event, uint16_t arg) {
- // turn LED on when we first enter the mode
- if (event == EV_enter_state) {
- // remember this level, unless it's moon or turbo
- if ((arg > 0) && (arg < MAX_LEVEL)) memorized_level = arg;
- // use the requested level even if not memorized
- #ifdef USE_THERMAL_REGULATION
- target_level = arg;
- #endif
- set_level(arg);
- return EVENT_HANDLED;
- }
- // 1 click: off
- else if (event == EV_1click) {
- set_state(off_state, 0);
- return EVENT_HANDLED;
- }
- // 2 clicks: go to/from highest level
- else if (event == EV_2clicks) {
- if (actual_level < MAX_LEVEL) { // go to turbo
- memorized_level = actual_level; // in case we're on moon
- #ifdef USE_THERMAL_REGULATION
- target_level = MAX_LEVEL;
- #endif
- set_level(MAX_LEVEL);
- }
- else { // return from turbo
- #ifdef USE_THERMAL_REGULATION
- target_level = memorized_level;
- #endif
- set_level(memorized_level);
- }
- return EVENT_HANDLED;
- }
- // hold: change brightness
- else if (event == EV_click1_hold) {
- if ((arg % HOLD_TIMEOUT) == 0) {
- memorized_level = (actual_level+1) % (MAX_LEVEL+1);
- #ifdef USE_THERMAL_REGULATION
- target_level = memorized_level;
- #endif
- set_level(memorized_level);
- }
- return EVENT_HANDLED;
- }
- #ifdef USE_THERMAL_REGULATION
- // overheating: drop by 1 level
- else if (event == EV_temperature_high) {
- if (actual_level > 1) { set_level(actual_level - 1); }
- return EVENT_HANDLED;
- }
- // underheating: increase by 1 level if we're lower than the target
- else if (event == EV_temperature_low) {
- if (actual_level < target_level) { set_level(actual_level + 1); }
- return EVENT_HANDLED;
- }
- #endif
- return EVENT_NOT_HANDLED;
-}
-
-uint8_t lockout_state(EventPtr event, uint16_t arg) {
- // stay asleep while locked
- if (event == EV_tick) {
- PWM1_LVL = 0; PWM2_LVL = 0; // make sure emitters are off
- // sleep 1 second after user stops pressing buttons
- if (arg > TICKS_PER_SECOND) { go_to_standby = 1; }
- return MISCHIEF_MANAGED;
- }
- // 4 clicks: exit, and turn on at "low" level
- else if (event == EV_4clicks) {
- set_state(steady_state, 1);
- return MISCHIEF_MANAGED;
- }
- return EVENT_NOT_HANDLED;
-}
-
-void low_voltage() {
- // step down by one level or turn off
- if (actual_level > 0) {
- set_level(actual_level - 1);
- #ifdef USE_THERMAL_REGULATION
- target_level = actual_level; // don't let low temperature override LVP
- #endif
- }
- else {
- set_state(off_state, 0);
- }
-}
-
-void setup() {
- // blink when power is connected
- set_level(MAX_LEVEL/2);
- delay_ms(10);
- set_level(0);
-
- push_state(off_state, 0);
-}
-
-void loop() {
-}
diff --git a/spaghetti-monster/baton/baton.c b/spaghetti-monster/baton/baton.c
index 59a7196..d4725ef 100644
--- a/spaghetti-monster/baton/baton.c
+++ b/spaghetti-monster/baton/baton.c
@@ -20,16 +20,12 @@
#define FSM_EMISAR_D4_DRIVER
#define USE_LVP
#define USE_THERMAL_REGULATION
-#define USE_DEBUG_BLINK
#define USE_DELAY_MS
-#define USE_DELAY_4MS
-#define USE_DELAY_ZERO
#include "spaghetti-monster.h"
// FSM states
uint8_t off_state(EventPtr event, uint16_t arg);
uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t party_strobe_state(EventPtr event, uint16_t arg);
uint8_t lockout_state(EventPtr event, uint16_t arg);
// brightness control
@@ -82,11 +78,6 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
set_state(steady_state, MAX_LEVEL);
return EVENT_HANDLED;
}
- // 3 clicks: strobe mode
- else if (event == EV_3clicks) {
- set_state(party_strobe_state, 255);
- return EVENT_HANDLED;
- }
// 4 clicks: soft lockout
else if (event == EV_4clicks) {
set_state(lockout_state, 0);
@@ -129,11 +120,6 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
}
return EVENT_HANDLED;
}
- // 3 clicks: go to strobe modes
- else if (event == EV_3clicks) {
- set_state(party_strobe_state, 0xff);
- return EVENT_HANDLED;
- }
// hold: change brightness
else if (event == EV_click1_hold) {
if ((arg % HOLD_TIMEOUT) == 0) {
@@ -160,54 +146,11 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t party_strobe_state(EventPtr event, uint16_t arg) {
- static volatile uint8_t frames = 0;
- static volatile uint8_t between = 2;
- if (event == EV_enter_state) {
- if (arg < 64) between = arg;
- frames = 0;
- return MISCHIEF_MANAGED;
- }
- // tick: strobe the emitter
- else if (event == EV_tick) {
- if (frames == 0) {
- PWM1_LVL = 0;
- PWM2_LVL = 255;
- if (between < 3) delay_zero();
- else delay_ms(1);
- PWM2_LVL = 0;
- }
- //frames = (frames + 1) % between;
- frames++;
- if (frames > between) frames = 0;
- return MISCHIEF_MANAGED;
- }
- // 1 click: off
- else if (event == EV_1click) {
- set_state(off_state, 0);
- return MISCHIEF_MANAGED;
- }
- // 2 clicks: go back to regular modes
- else if (event == EV_2clicks) {
- set_state(steady_state, memorized_level);
- return MISCHIEF_MANAGED;
- }
- // hold: change speed
- else if (event == EV_click1_hold) {
- if ((arg % HOLD_TIMEOUT) == 0) {
- between = (between+1)%6;
- frames = 0;
- }
- return MISCHIEF_MANAGED;
- }
- return EVENT_NOT_HANDLED;
-}
-
uint8_t lockout_state(EventPtr event, uint16_t arg) {
// stay asleep while locked
if (event == EV_tick) {
PWM1_LVL = 0; PWM2_LVL = 0; // make sure emitters are off
- // sleep 1 second after user stops pressing
+ // sleep 1 second after user stops pressing buttons
if (arg > TICKS_PER_SECOND) { go_to_standby = 1; }
return MISCHIEF_MANAGED;
}
@@ -220,29 +163,26 @@ uint8_t lockout_state(EventPtr event, uint16_t arg) {
}
void low_voltage() {
- // "step down" from strobe to level 2
- if (current_state == party_strobe_state) {
- set_state(steady_state, 1);
- }
- // in normal mode, step down by one level or turn off
- else if (current_state == steady_state) {
- if (actual_level > 0) {
- set_level(actual_level - 1);
+ // step down by one level or turn off
+ if (actual_level > 0) {
+ set_level(actual_level - 1);
#ifdef USE_THERMAL_REGULATION
target_level = actual_level; // don't let low temperature override LVP
#endif
-
- }
- else {
- set_state(off_state, 0);
- }
+ }
+ else {
+ set_state(off_state, 0);
}
}
void setup() {
- debug_blink(2);
+ // blink when power is connected
+ set_level(MAX_LEVEL/2);
+ delay_ms(10);
+ set_level(0);
push_state(off_state, 0);
}
-void loop() { }
+void loop() {
+}
--
cgit v1.2.3
From a58ba65298350e9e7a2f8ce33645cdf1db5916cd Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Wed, 17 Oct 2018 23:46:10 -0600
Subject: PL47 doesn't need "low" mode for aux LED / switch LED
---
spaghetti-monster/anduril/cfg-ff-pl47.h | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/spaghetti-monster/anduril/cfg-ff-pl47.h b/spaghetti-monster/anduril/cfg-ff-pl47.h
index d916e06..ef12964 100644
--- a/spaghetti-monster/anduril/cfg-ff-pl47.h
+++ b/spaghetti-monster/anduril/cfg-ff-pl47.h
@@ -17,7 +17,8 @@
// the "low" mode doesn't work on this light's aux LEDs
// (but it does work on the switch LEDs)
-//#define INDICATOR_LED_SKIP_LOW
+// Fireflies wants to skip aux LED mode 1 (low)
+#define INDICATOR_LED_SKIP_LOW
// ... or if TICK_DURING_STANDBY is turned off:
// off mode: high (2)
--
cgit v1.2.3
From a19560f92e0ead081e494d58dd6cf36c170c85c0 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Wed, 17 Oct 2018 23:47:12 -0600
Subject: Initial untested support for the Sofirn SP36 (like a Q8 but smaller).
---
spaghetti-monster/anduril/anduril.c | 4 ++++
spaghetti-monster/anduril/build-all.sh | 1 +
2 files changed, 5 insertions(+)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index 300e32b..085c674 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -32,6 +32,7 @@
//#define FSM_FF_ROT66_DRIVER
//#define FSM_FF_ROT66_219_DRIVER
//#define FSM_FW3A_DRIVER
+//#define FSM_SOFIRN_SP36_DRIVER
#define USE_LVP // FIXME: won't build when this option is turned off
@@ -114,6 +115,9 @@
#elif defined(FSM_FW3A_DRIVER)
#include "cfg-fw3a.h"
+#elif defined(FSM_SOFIRN_SP36_DRIVER)
+#include "cfg-sofirn-sp36.h"
+
#endif
diff --git a/spaghetti-monster/anduril/build-all.sh b/spaghetti-monster/anduril/build-all.sh
index 9e2a83c..1a1363c 100755
--- a/spaghetti-monster/anduril/build-all.sh
+++ b/spaghetti-monster/anduril/build-all.sh
@@ -16,6 +16,7 @@ for TARGET in \
FF_ROT66 \
FF_ROT66_219 \
FW3A \
+ SOFIRN_SP36 \
; do
echo "===== $TARGET ====="
../../../bin/build-85.sh "$UI" "-DFSM_${TARGET}_DRIVER"
--
cgit v1.2.3
From aab4ec0543a7563ff08fbc2013bd414c03e25648 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Tue, 30 Oct 2018 00:42:43 -0600
Subject: Adjusted FF PL47 config. Made muggle floor/ceiling configurable per
config file.
---
spaghetti-monster/anduril/anduril.c | 4 ++++
spaghetti-monster/anduril/cfg-ff-pl47.h | 18 +++++++++++++++---
2 files changed, 19 insertions(+), 3 deletions(-)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index 085c674..fd3c534 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -154,9 +154,13 @@
#endif
#if defined(USE_MUGGLE_MODE)
+#ifndef MUGGLE_FLOOR
#define MUGGLE_FLOOR 22
+#endif
+#ifndef MUGGLE_CEILING
#define MUGGLE_CEILING (MAX_1x7135+20)
#endif
+#endif
#define USE_IDLE_MODE // reduce power use while awake and no tasks are pending
#define USE_DYNAMIC_UNDERCLOCKING // cut clock speed at very low modes for better efficiency
diff --git a/spaghetti-monster/anduril/cfg-ff-pl47.h b/spaghetti-monster/anduril/cfg-ff-pl47.h
index ef12964..d9431a1 100644
--- a/spaghetti-monster/anduril/cfg-ff-pl47.h
+++ b/spaghetti-monster/anduril/cfg-ff-pl47.h
@@ -39,15 +39,27 @@
#define HALFSPEED_LEVEL 13
#define QUARTERSPEED_LEVEL 6
-// ceiling is level 120/150
-#define RAMP_SMOOTH_CEIL (MAX_LEVEL*4/5)
-
// thermal regulation parameters
#ifdef MIN_THERM_STEPDOWN
#undef MIN_THERM_STEPDOWN // this should be lower, because 3x7135 instead of 1x7135
#endif
#define MIN_THERM_STEPDOWN 60 // lowest value it'll step down to
+// ceiling is level 120/150
+#define RAMP_SMOOTH_CEIL 120
+
+// 10, 28, 46, 65, 83, 101, 120 (83 is highest regulated)
+#define RAMP_DISCRETE_FLOOR 10
+#define RAMP_DISCRETE_CEIL 120
+#define RAMP_DISCRETE_STEPS 7
+
+// ~25 lm to ~300 lm
+#define MUGGLE_FLOOR 30
+#define MUGGLE_CEILING MAX_1x7135
+// ~50 lm to ~500 lm
+//#define MUGGLE_FLOOR 40
+//#define MUGGLE_CEILING 90
+
// regulate down faster when the FET is active, slower otherwise
#define THERM_FASTER_LEVEL 130 // throttle back faster when high
--
cgit v1.2.3
From 0110aa7f7988d54119ae085b5366918783b32901 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Fri, 2 Nov 2018 15:41:00 -0600
Subject: Corrected anduril.txt with the new aux LED button mappings.
---
spaghetti-monster/anduril/anduril.txt | 7 +++++--
1 file changed, 5 insertions(+), 2 deletions(-)
diff --git a/spaghetti-monster/anduril/anduril.txt b/spaghetti-monster/anduril/anduril.txt
index 9cbef68..f0f0b4d 100644
--- a/spaghetti-monster/anduril/anduril.txt
+++ b/spaghetti-monster/anduril/anduril.txt
@@ -17,6 +17,9 @@ From off:
* 4 clicks: lock-out
* 5 clicks: momentary mode (disconnect power to exit)
* 6 clicks: muggle mode
+ * On hardware with an indicator LED...
+ * 7 clicks: Change aux LED mode used in "off" mode.
+ (the modes are usually off/low/high/blinking)
In steady mode:
* 1 click: off
@@ -111,8 +114,8 @@ Lockout mode:
* Hold: momentary moon
* 4 clicks: exit lockout (return to regular "off" mode)
* On hardware with an indicator LED...
- * 3 clicks: Change button brightness used in lockout mode. (low/high/off)
- * Click, click, hold: Change button brightness used in "off" mode.
+ * 3 clicks: Change aux LED brightness used in lockout mode.
+ (the modes are usually off/low/high/blinking)
Momentary mode:
* Press button: Light on (at memorized level).
--
cgit v1.2.3
From 9e3e7a8e6a7c0ed3abe21b9ae24c07d8c13e3e93 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sat, 3 Nov 2018 17:22:58 -0600
Subject: added missing ifdef which broke per-hardware ramp lengths
---
spaghetti-monster/anduril/anduril.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index fd3c534..df478ee 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -140,7 +140,9 @@
/********* Configure SpaghettiMonster *********/
#define USE_DELAY_ZERO
#define USE_RAMPING
+#ifndef RAMP_LENGTH
#define RAMP_LENGTH 150 // default, if not overridden in a driver cfg file
+#endif
#define MAX_BIKING_LEVEL 120 // should be 127 or less
#define USE_BATTCHECK
--
cgit v1.2.3
From 5699260c774749d9a6b1b5ad855a816806ed1be7 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sat, 3 Nov 2018 18:46:57 -0600
Subject: forgot to add the Sofirn SP36 config file earlier, oops
---
spaghetti-monster/anduril/cfg-sofirn-sp36.h | 16 ++++++++++++++++
1 file changed, 16 insertions(+)
create mode 100644 spaghetti-monster/anduril/cfg-sofirn-sp36.h
diff --git a/spaghetti-monster/anduril/cfg-sofirn-sp36.h b/spaghetti-monster/anduril/cfg-sofirn-sp36.h
new file mode 100644
index 0000000..11e3735
--- /dev/null
+++ b/spaghetti-monster/anduril/cfg-sofirn-sp36.h
@@ -0,0 +1,16 @@
+// Sofirn SP36 (small Q8) config options for Anduril
+
+#define FSM_BLF_Q8_DRIVER
+#include "cfg-blf-q8.h"
+
+// stop panicking at ~50% power or ~2000 lm
+#ifdef THERM_FASTER_LEVEL
+#undef THERM_FASTER_LEVEL
+#endif
+#define THERM_FASTER_LEVEL 125
+
+// be extra-careful at high levels
+#ifndef THERM_HARD_TURBO_DROP
+#define THERM_HARD_TURBO_DROP
+#endif
+
--
cgit v1.2.3
From 94ba77de5c2c4bf8df3f23ac9ab397a360a75e69 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sat, 3 Nov 2018 18:55:31 -0600
Subject: Made it easier to override hwdef-*.h values in cfg-*.h files.
---
hwdef-BLF_GT.h | 16 +++++++++++++++-
hwdef-BLF_GT_Mini.h | 6 ++++++
hwdef-BLF_Q8.h | 13 +++++++------
hwdef-Emisar_D4.h | 16 ++++++++++++----
hwdef-FF_PL47.h | 29 ++++++++++++++---------------
hwdef-FF_ROT66.h | 15 ++++++++-------
hwdef-FW3A.h | 22 +++++++++++++++++-----
spaghetti-monster/anduril/cfg-blf-gt.h | 4 ----
spaghetti-monster/anduril/cfg-blf-q8.h | 4 ----
spaghetti-monster/anduril/cfg-emisar-d4.h | 3 ---
spaghetti-monster/anduril/cfg-ff-pl47.h | 3 ---
spaghetti-monster/anduril/cfg-ff-rot66.h | 4 ----
spaghetti-monster/anduril/cfg-fw3a.h | 4 ----
13 files changed, 79 insertions(+), 60 deletions(-)
diff --git a/hwdef-BLF_GT.h b/hwdef-BLF_GT.h
index 1a05741..7dcc8a0 100644
--- a/hwdef-BLF_GT.h
+++ b/hwdef-BLF_GT.h
@@ -9,29 +9,43 @@
#define PWM_CHANNELS 2
+#ifndef AUXLED_PIN
#define AUXLED_PIN PB4 // pin 3
+#endif
+#ifndef SWITCH_PIN
#define SWITCH_PIN PB3 // pin 2
#define SWITCH_PCINT PCINT3 // pin 2 pin change interrupt
+#endif
+#ifndef PWM1_PIN
#define PWM1_PIN PB0 // pin 5, 1x7135 PWM
#define PWM1_LVL OCR0A // OCR0A is the output compare register for PB0
+#endif
+#ifndef PWM2_PIN
#define PWM2_PIN PB1 // pin 6, FET PWM
#define PWM2_LVL OCR0B // OCR0B is the output compare register for PB1
+#endif
#define USE_VOLTAGE_DIVIDER // use a voltage divider on pin 7, not VCC
+#ifndef VOLTAGE_PIN
#define VOLTAGE_PIN PB2 // pin 7, voltage ADC
#define VOLTAGE_CHANNEL 0x01 // MUX 01 corresponds with PB2
+#define VOLTAGE_ADC_DIDR ADC1D // Digital input disable bit corresponding with PB2
// 1.1V reference, left-adjust, ADC1/PB2
//#define ADMUX_VOLTAGE_DIVIDER ((1 << V_REF) | (1 << ADLAR) | VOLTAGE_CHANNEL)
// 1.1V reference, no left-adjust, ADC1/PB2
#define ADMUX_VOLTAGE_DIVIDER ((1 << V_REF) | VOLTAGE_CHANNEL)
-#define VOLTAGE_ADC_DIDR ADC1D // Digital input disable bit corresponding with PB2
+#endif
#define ADC_PRSCL 0x06 // clk/64
// Raw ADC readings at 4.4V and 2.2V (in-between, we assume values form a straight line)
+#ifndef ADC_44
#define ADC_44 184
+#endif
+#ifndef ADC_22
#define ADC_22 92
+#endif
#define TEMP_CHANNEL 0b00001111
diff --git a/hwdef-BLF_GT_Mini.h b/hwdef-BLF_GT_Mini.h
index 504c561..aacbca4 100644
--- a/hwdef-BLF_GT_Mini.h
+++ b/hwdef-BLF_GT_Mini.h
@@ -2,3 +2,9 @@
*/
// exactly the same as a D1S, but with a lighted button
#include "hwdef-Emisar_D1S.h"
+
+// lighted button
+#ifndef AUXLED_PIN
+#define AUXLED_PIN PB4 // pin 3
+#endif
+
diff --git a/hwdef-BLF_Q8.h b/hwdef-BLF_Q8.h
index f00c392..6e13faf 100644
--- a/hwdef-BLF_Q8.h
+++ b/hwdef-BLF_Q8.h
@@ -1,16 +1,17 @@
/* BLF Q8 driver layout
+ * Q8 driver is the same as a D4, basically
*/
-// Q8 driver is the same as a D4, basically
-#include "hwdef-Emisar_D4.h"
// ... except the Q8 has a lighted button
#ifndef AUXLED_PIN
#define AUXLED_PIN PB4 // pin 3
#endif
-// average drop across diode on this hardware
-#ifdef VOLTAGE_FUDGE_FACTOR
-#undef VOLTAGE_FUDGE_FACTOR
-#endif
+// ... and slightly different calibration
+#ifndef VOLTAGE_FUDGE_FACTOR
#define VOLTAGE_FUDGE_FACTOR 7 // add 0.35V
+#endif
+
+// Q8 driver is the same as a D4, basically
+#include "hwdef-Emisar_D4.h"
diff --git a/hwdef-Emisar_D4.h b/hwdef-Emisar_D4.h
index 105d3b9..0dfcab9 100644
--- a/hwdef-Emisar_D4.h
+++ b/hwdef-Emisar_D4.h
@@ -9,24 +9,32 @@
#define PWM_CHANNELS 2
-#define AUXLED_PIN PB4 // pin 3
+//#define AUXLED_PIN PB4 // pin 3
+#ifndef SWITCH_PIN
#define SWITCH_PIN PB3 // pin 2
#define SWITCH_PCINT PCINT3 // pin 2 pin change interrupt
+#endif
+#ifndef PWM1_PIN
#define PWM1_PIN PB0 // pin 5, 1x7135 PWM
#define PWM1_LVL OCR0A // OCR0A is the output compare register for PB0
+#endif
+#ifndef PWM2_PIN
#define PWM2_PIN PB1 // pin 6, FET PWM
#define PWM2_LVL OCR0B // OCR0B is the output compare register for PB1
+#endif
// (FIXME: remove? not used?)
-#define VOLTAGE_PIN PB2 // pin 7, voltage ADC
-#define ADC_CHANNEL 0x01 // MUX 01 corresponds with PB2
-#define ADC_DIDR ADC1D // Digital input disable bit corresponding with PB2
+//#define VOLTAGE_PIN PB2 // pin 7, voltage ADC
+//#define ADC_CHANNEL 0x01 // MUX 01 corresponds with PB2
+//#define ADC_DIDR ADC1D // Digital input disable bit corresponding with PB2
#define ADC_PRSCL 0x06 // clk/64
// average drop across diode on this hardware
+#ifndef VOLTAGE_FUDGE_FACTOR
#define VOLTAGE_FUDGE_FACTOR 5 // add 0.25V
+#endif
//#define TEMP_DIDR ADC4D
#define TEMP_CHANNEL 0b00001111
diff --git a/hwdef-FF_PL47.h b/hwdef-FF_PL47.h
index 4189220..217ce45 100644
--- a/hwdef-FF_PL47.h
+++ b/hwdef-FF_PL47.h
@@ -1,24 +1,23 @@
/* Fireflies PL47 driver layout
+ * same as a D4S, basically, except ...
*/
-// same as a D4S, basically
-#include "hwdef-Emisar_D4S.h"
-#undef FSM_EMISAR_D4S_DRIVER
-#undef FSM_EMISAR_D4_DRIVER
-// ... except the PL47 has aux LEDs on pin 7
-#ifdef AUXLED_PIN
-#undef AUXLED_PIN
-#endif
+// ... the PL47 has aux LEDs on pin 7
+#ifndef AUXLED_PIN
#define AUXLED_PIN PB2 // pin 7
+#endif
// ... and switch LEDs on pin 3
-#ifdef AUXLED2_PIN
-#undef AUXLED2_PIN
-#endif
+#ifndef AUXLED2_PIN
#define AUXLED2_PIN PB4 // pin 3
-
-// average drop across diode on this hardware
-#ifdef VOLTAGE_FUDGE_FACTOR
-#undef VOLTAGE_FUDGE_FACTOR
#endif
+
+// ... and slightly different calibration
+#ifndef VOLTAGE_FUDGE_FACTOR
#define VOLTAGE_FUDGE_FACTOR 7 // add 0.35V
+#endif
+
+#include "hwdef-Emisar_D4S.h"
+#undef FSM_EMISAR_D4S_DRIVER
+#undef FSM_EMISAR_D4_DRIVER
+
diff --git a/hwdef-FF_ROT66.h b/hwdef-FF_ROT66.h
index 49947ab..0913a76 100644
--- a/hwdef-FF_ROT66.h
+++ b/hwdef-FF_ROT66.h
@@ -1,20 +1,21 @@
/* Fireflies ROT66 driver layout
+ * same as a FW3A, basically, except ...
*/
-// same as a FW3A, basically
-#include "hwdef-FW3A.h"
// ... except the ROT66 has a lighted button
#ifndef AUXLED_PIN
#define AUXLED_PIN PB2 // pin 7
#endif
+// ... and slightly different calibration
+#ifndef VOLTAGE_FUDGE_FACTOR
+#define VOLTAGE_FUDGE_FACTOR 7 // add 0.35V
+#endif
+
+#include "hwdef-FW3A.h"
+
// ... and no optic nerve
#ifdef VISION_PIN
#undef VISION_PIN
#endif
-// average drop across diode on this hardware
-#ifdef VOLTAGE_FUDGE_FACTOR
-#undef VOLTAGE_FUDGE_FACTOR
-#endif
-#define VOLTAGE_FUDGE_FACTOR 7 // add 0.35V
diff --git a/hwdef-FW3A.h b/hwdef-FW3A.h
index 5e253c7..8abab9a 100644
--- a/hwdef-FW3A.h
+++ b/hwdef-FW3A.h
@@ -9,23 +9,35 @@
#define PWM_CHANNELS 3
+#ifndef SWITCH_PIN
#define SWITCH_PIN PB3 // pin 2
#define SWITCH_PCINT PCINT3 // pin 2 pin change interrupt
+#endif
+#ifndef PWM1_PIN
#define PWM1_PIN PB0 // pin 5, 1x7135 PWM
#define PWM1_LVL OCR0A // OCR0A is the output compare register for PB0
-#define PWM2_PIN PB1 // pin 6, FET PWM
+#endif
+#ifndef PWM2_PIN
+#define PWM2_PIN PB1 // pin 6, 7x7135 PWM
#define PWM2_LVL OCR0B // OCR0B is the output compare register for PB1
-#define PWM3_PIN PB4 // pin 3
-#define PWM3_LVL OCR1B
+#endif
+#ifndef PWM3_PIN
+#define PWM3_PIN PB4 // pin 3, FET PWM
+#define PWM3_LVL OCR1B // OCR1B is the output compare register for PB4
+#endif
+#ifndef VISION_PIN
#define VISION_PIN PB2 // pin 7, optic nerve
-#define ADC_CHANNEL 0x01 // MUX 01 corresponds with PB2
-#define ADC_DIDR ADC1D // Digital input disable bit corresponding with PB2
+//#define ADC_CHANNEL 0x01 // MUX 01 corresponds with PB2
+//#define ADC_DIDR ADC1D // Digital input disable bit corresponding with PB2
+#endif
#define ADC_PRSCL 0x06 // clk/64
// average drop across diode on this hardware
+#ifndef VOLTAGE_FUDGE_FACTOR
#define VOLTAGE_FUDGE_FACTOR 5 // add 0.25V
+#endif
//#define TEMP_DIDR ADC4D
#define TEMP_CHANNEL 0b00001111
diff --git a/spaghetti-monster/anduril/cfg-blf-gt.h b/spaghetti-monster/anduril/cfg-blf-gt.h
index 369d028..a29d7e7 100644
--- a/spaghetti-monster/anduril/cfg-blf-gt.h
+++ b/spaghetti-monster/anduril/cfg-blf-gt.h
@@ -14,10 +14,6 @@
//#undef USE_SET_LEVEL_GRADUALLY
-#ifdef RAMP_LENGTH
-#undef RAMP_LENGTH
-#endif
-
#define RAMP_LENGTH 150
// First 60 values: level_calc.py 1 60 7135 4 5.0 255
// Remainder: all 255 (buck driver at 100% duty cycle)
diff --git a/spaghetti-monster/anduril/cfg-blf-q8.h b/spaghetti-monster/anduril/cfg-blf-q8.h
index 269aae9..1b9b971 100644
--- a/spaghetti-monster/anduril/cfg-blf-q8.h
+++ b/spaghetti-monster/anduril/cfg-blf-q8.h
@@ -7,10 +7,6 @@
// enable blinking indicator LED while off
#define TICK_DURING_STANDBY
-#ifdef RAMP_LENGTH
-#undef RAMP_LENGTH
-#endif
-
// copied from Emisar D4 ramp
// ../../bin/level_calc.py 1 65 7135 1 0.8 150
// ... mixed with this:
diff --git a/spaghetti-monster/anduril/cfg-emisar-d4.h b/spaghetti-monster/anduril/cfg-emisar-d4.h
index 251f81d..e83c62d 100644
--- a/spaghetti-monster/anduril/cfg-emisar-d4.h
+++ b/spaghetti-monster/anduril/cfg-emisar-d4.h
@@ -1,8 +1,5 @@
// Emisar D4 config options for Anduril
-#ifdef RAMP_LENGTH
-#undef RAMP_LENGTH
-#endif
// ../../bin/level_calc.py 1 65 7135 1 0.8 150
// ... mixed with this:
// ../../bin/level_calc.py 2 150 7135 4 0.33 150 FET 1 10 1500
diff --git a/spaghetti-monster/anduril/cfg-ff-pl47.h b/spaghetti-monster/anduril/cfg-ff-pl47.h
index d9431a1..2e5647d 100644
--- a/spaghetti-monster/anduril/cfg-ff-pl47.h
+++ b/spaghetti-monster/anduril/cfg-ff-pl47.h
@@ -26,9 +26,6 @@
//#define INDICATOR_LED_DEFAULT_MODE ((0<<2) + 2)
-#ifdef RAMP_LENGTH
-#undef RAMP_LENGTH
-#endif
#define RAMP_LENGTH 150
// driver is a FET + 3x7135, ~400 lm at highest regulated level
diff --git a/spaghetti-monster/anduril/cfg-ff-rot66.h b/spaghetti-monster/anduril/cfg-ff-rot66.h
index c8e0d52..165b2ba 100644
--- a/spaghetti-monster/anduril/cfg-ff-rot66.h
+++ b/spaghetti-monster/anduril/cfg-ff-rot66.h
@@ -18,10 +18,6 @@
#define INDICATOR_LED_DEFAULT_MODE ((0<<2) + 2)
-#ifdef RAMP_LENGTH
-#undef RAMP_LENGTH
-#endif
-
// driver is a FET+N+1,
// where N=6 for the 219b version,
// or N=13 for the XP-L HI version (this version)
diff --git a/spaghetti-monster/anduril/cfg-fw3a.h b/spaghetti-monster/anduril/cfg-fw3a.h
index 65f1e48..efa70ae 100644
--- a/spaghetti-monster/anduril/cfg-fw3a.h
+++ b/spaghetti-monster/anduril/cfg-fw3a.h
@@ -1,9 +1,5 @@
// FW3A config options for Anduril
-#ifdef RAMP_LENGTH
-#undef RAMP_LENGTH
-#endif
-
// ../../bin/level_calc.py 1 65 7135 1 0.8 150
// ... mixed with this:
// ../../../bin/level_calc.py 3 150 7135 1 0.33 150 7135 1 1 850 FET 1 10 1500
--
cgit v1.2.3
From 387cb35e8f9e2ca74cfc019d06a0051bc7b11aea Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sat, 10 Nov 2018 01:13:42 -0700
Subject: calibrated Sofirn SP36 config
---
spaghetti-monster/anduril/cfg-sofirn-sp36.h | 28 +++++++++++++++++++++++-----
1 file changed, 23 insertions(+), 5 deletions(-)
diff --git a/spaghetti-monster/anduril/cfg-sofirn-sp36.h b/spaghetti-monster/anduril/cfg-sofirn-sp36.h
index 11e3735..f6f7447 100644
--- a/spaghetti-monster/anduril/cfg-sofirn-sp36.h
+++ b/spaghetti-monster/anduril/cfg-sofirn-sp36.h
@@ -1,16 +1,34 @@
// Sofirn SP36 (small Q8) config options for Anduril
+// voltage readings were a little high with the Q8 value
+#define VOLTAGE_FUDGE_FACTOR 5 // add 0.25V, not 0.35V
+
#define FSM_BLF_Q8_DRIVER
#include "cfg-blf-q8.h"
-// stop panicking at ~50% power or ~2000 lm
+// the high button LED mode on this light uses too much power
+// off mode: low (1)
+// lockout: blinking (3)
+#define INDICATOR_LED_DEFAULT_MODE ((3<<2) + 1)
+
+// don't blink during the ramp; the button LED brightness is sufficient
+// to indicate which power channel(s) are being used
+#ifdef BLINK_AT_CHANNEL_BOUNDARIES
+#undef BLINK_AT_CHANNEL_BOUNDARIES
+#endif
+#ifdef BLINK_AT_RAMP_CEILING
+#undef BLINK_AT_RAMP_CEILING
+#endif
+
+// stop panicking at ~60% power or ~3000 lm
#ifdef THERM_FASTER_LEVEL
#undef THERM_FASTER_LEVEL
#endif
-#define THERM_FASTER_LEVEL 125
+#define THERM_FASTER_LEVEL 130
// be extra-careful at high levels
-#ifndef THERM_HARD_TURBO_DROP
-#define THERM_HARD_TURBO_DROP
-#endif
+// (or not... this host seems to heat up pretty slowly)
+//#ifndef THERM_HARD_TURBO_DROP
+//#define THERM_HARD_TURBO_DROP
+//#endif
--
cgit v1.2.3
From e942fa7c47f446891e3bb0a07316d22cc32c00c2 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 05:14:47 -0700
Subject: Rewrote the event system to use a single byte for each event instead
of an array of actions. Not thoroughly tested yet, not done yet, have only
updated Anduril to fit, and only partially.
---
spaghetti-monster/anduril/anduril.c | 116 ++++---
spaghetti-monster/fsm-events.c | 96 ++----
spaghetti-monster/fsm-events.h | 607 ++++++++----------------------------
spaghetti-monster/fsm-pcint.c | 4 +-
spaghetti-monster/fsm-states.c | 4 +-
spaghetti-monster/fsm-states.h | 6 +-
spaghetti-monster/fsm-wdt.c | 38 +--
7 files changed, 253 insertions(+), 618 deletions(-)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index df478ee..de4f996 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -226,45 +226,45 @@ typedef enum {
// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
+uint8_t off_state(Event event, uint16_t arg);
// simple numeric entry config menu
-uint8_t config_state_base(EventPtr event, uint16_t arg,
+uint8_t config_state_base(Event event, uint16_t arg,
uint8_t num_config_steps,
void (*savefunc)());
#define MAX_CONFIG_VALUES 3
uint8_t config_state_values[MAX_CONFIG_VALUES];
// ramping mode and its related config mode
-uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t ramp_config_state(EventPtr event, uint16_t arg);
+uint8_t steady_state(Event event, uint16_t arg);
+uint8_t ramp_config_state(Event event, uint16_t arg);
// party and tactical strobes
#ifdef USE_STROBE_STATE
-uint8_t strobe_state(EventPtr event, uint16_t arg);
+uint8_t strobe_state(Event event, uint16_t arg);
#endif
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg);
+uint8_t battcheck_state(Event event, uint16_t arg);
#endif
#ifdef USE_THERMAL_REGULATION
-uint8_t tempcheck_state(EventPtr event, uint16_t arg);
-uint8_t thermal_config_state(EventPtr event, uint16_t arg);
+uint8_t tempcheck_state(Event event, uint16_t arg);
+uint8_t thermal_config_state(Event event, uint16_t arg);
#endif
// 1-hour ramp down from low, then automatic off
-uint8_t goodnight_state(EventPtr event, uint16_t arg);
+uint8_t goodnight_state(Event event, uint16_t arg);
// beacon mode and its related config mode
-uint8_t beacon_state(EventPtr event, uint16_t arg);
-uint8_t beacon_config_state(EventPtr event, uint16_t arg);
+uint8_t beacon_state(Event event, uint16_t arg);
+uint8_t beacon_config_state(Event event, uint16_t arg);
// soft lockout
#define MOON_DURING_LOCKOUT_MODE
-uint8_t lockout_state(EventPtr event, uint16_t arg);
+uint8_t lockout_state(Event event, uint16_t arg);
// momentary / signalling mode
-uint8_t momentary_state(EventPtr event, uint16_t arg);
+uint8_t momentary_state(Event event, uint16_t arg);
#ifdef USE_MUGGLE_MODE
// muggle mode, super-simple, hard to exit
-uint8_t muggle_state(EventPtr event, uint16_t arg);
+uint8_t muggle_state(Event event, uint16_t arg);
uint8_t muggle_mode_active = 0;
#endif
// general helper function for config modes
-uint8_t number_entry_state(EventPtr event, uint16_t arg);
+uint8_t number_entry_state(Event event, uint16_t arg);
// return value from number_entry_state()
volatile uint8_t number_entry_value;
@@ -387,7 +387,7 @@ uint8_t triangle_wave(uint8_t phase);
volatile uint8_t beacon_seconds = 2;
-uint8_t off_state(EventPtr event, uint16_t arg) {
+uint8_t off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
set_level(0);
@@ -527,7 +527,7 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
}
-uint8_t steady_state(EventPtr event, uint16_t arg) {
+uint8_t steady_state(Event event, uint16_t arg) {
uint8_t mode_min = ramp_smooth_floor;
uint8_t mode_max = ramp_smooth_ceil;
uint8_t ramp_step_size = 1;
@@ -846,7 +846,7 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
#ifdef USE_STROBE_STATE
-uint8_t strobe_state(EventPtr event, uint16_t arg) {
+uint8_t strobe_state(Event event, uint16_t arg) {
// 'st' reduces ROM size by avoiding access to a volatile var
// (maybe I should just make it nonvolatile?)
strobe_mode_te st = strobe_type;
@@ -1059,7 +1059,7 @@ uint8_t strobe_state(EventPtr event, uint16_t arg) {
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg) {
+uint8_t battcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -1076,7 +1076,7 @@ uint8_t battcheck_state(EventPtr event, uint16_t arg) {
#ifdef USE_THERMAL_REGULATION
-uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
+uint8_t tempcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -1097,7 +1097,7 @@ uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
#endif
-uint8_t beacon_state(EventPtr event, uint16_t arg) {
+uint8_t beacon_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -1124,7 +1124,7 @@ uint8_t beacon_state(EventPtr event, uint16_t arg) {
#define GOODNIGHT_TICKS_PER_STEPDOWN (GOODNIGHT_TIME*TICKS_PER_SECOND*60L/GOODNIGHT_LEVEL)
-uint8_t goodnight_state(EventPtr event, uint16_t arg) {
+uint8_t goodnight_state(Event event, uint16_t arg) {
static uint16_t ticks_since_stepdown = 0;
// blink on start
if (event == EV_enter_state) {
@@ -1163,28 +1163,27 @@ uint8_t goodnight_state(EventPtr event, uint16_t arg) {
}
-uint8_t lockout_state(EventPtr event, uint16_t arg) {
+uint8_t lockout_state(Event event, uint16_t arg) {
#ifdef MOON_DURING_LOCKOUT_MODE
// momentary(ish) moon mode during lockout
// not all presses will be counted;
// it depends on what is in the master event_sequences table
- uint8_t last = 0;
- for(uint8_t i=0; pgm_read_byte(event + i) && (i TICKS_PER_SECOND*15) { // sleep after 15 seconds
go_to_standby = 1; // sleep while light is off
+ // TODO: lighted button should use lockout config?
}
return MISCHIEF_MANAGED;
}
@@ -1311,7 +1323,7 @@ uint8_t momentary_state(EventPtr event, uint16_t arg) {
#ifdef USE_MUGGLE_MODE
-uint8_t muggle_state(EventPtr event, uint16_t arg) {
+uint8_t muggle_state(Event event, uint16_t arg) {
static int8_t ramp_direction;
static int8_t muggle_off_mode;
@@ -1461,7 +1473,7 @@ uint8_t muggle_state(EventPtr event, uint16_t arg) {
// ask the user for a sequence of numbers, then save them and return to caller
-uint8_t config_state_base(EventPtr event, uint16_t arg,
+uint8_t config_state_base(Event event, uint16_t arg,
uint8_t num_config_steps,
void (*savefunc)()) {
static uint8_t config_step;
@@ -1520,7 +1532,7 @@ void ramp_config_save() {
}
}
-uint8_t ramp_config_state(EventPtr event, uint16_t arg) {
+uint8_t ramp_config_state(Event event, uint16_t arg) {
uint8_t num_config_steps;
num_config_steps = 2 + ramp_style;
return config_state_base(event, arg,
@@ -1548,7 +1560,7 @@ void thermal_config_save() {
if (therm_ceil > MAX_THERM_CEIL) therm_ceil = MAX_THERM_CEIL;
}
-uint8_t thermal_config_state(EventPtr event, uint16_t arg) {
+uint8_t thermal_config_state(Event event, uint16_t arg) {
return config_state_base(event, arg,
2, thermal_config_save);
}
@@ -1563,13 +1575,13 @@ void beacon_config_save() {
}
}
-uint8_t beacon_config_state(EventPtr event, uint16_t arg) {
+uint8_t beacon_config_state(Event event, uint16_t arg) {
return config_state_base(event, arg,
1, beacon_config_save);
}
-uint8_t number_entry_state(EventPtr event, uint16_t arg) {
+uint8_t number_entry_state(Event event, uint16_t arg) {
static uint8_t value;
static uint8_t blinks_left;
static uint8_t entry_step;
diff --git a/spaghetti-monster/fsm-events.c b/spaghetti-monster/fsm-events.c
index ee7bc97..091d4cf 100644
--- a/spaghetti-monster/fsm-events.c
+++ b/spaghetti-monster/fsm-events.c
@@ -20,25 +20,8 @@
#ifndef FSM_EVENTS_C
#define FSM_EVENTS_C
-// TODO: maybe compare events by number instead of pointer?
-// (number = index in event types array)
-// (comparison would use full event content, but send off index to callbacks)
-// (saves space by using uint8_t instead of a pointer)
-// (also eliminates the need to duplicate single-entry events like for voltage or timer tick)
-
-// return 1 if (a == b), 0 otherwise
-uint8_t compare_event_sequences(uint8_t *a, const uint8_t *b) {
- for(uint8_t i=0; (i= offset) return current_event[i-offset];
- return 0;
-}
-*/
+ return 0; // unexpected event type
-inline uint8_t last_event_num() {
- uint8_t i;
- for(i=0; current_event[i] && (i=0; i--) {
uint8_t err = state_stack[i](event, arg);
if (! err) return 0;
@@ -210,26 +188,10 @@ uint8_t emit_now(EventPtr event, uint16_t arg) {
return 1; // event not handled
}
-void emit(EventPtr event, uint16_t arg) {
+void emit(Event event, uint16_t arg) {
// add this event to the queue for later,
// so we won't use too much time during an interrupt
append_emission(event, arg);
}
-// Search the pre-defined event list for one matching what the user just did,
-// and emit it if one was found.
-void emit_current_event(uint16_t arg) {
- //uint8_t err = 1;
- for (uint8_t i=0; i<(sizeof(event_sequences)/sizeof(EventPtr)); i++) {
- if (events_match(current_event, event_sequences[i])) {
- //DEBUG_FLASH;
- //err = emit(event_sequences[i], arg);
- //return err;
- emit(event_sequences[i], arg);
- return;
- }
- }
- //return err;
-}
-
#endif
diff --git a/spaghetti-monster/fsm-events.h b/spaghetti-monster/fsm-events.h
index 0212c2c..d838800 100644
--- a/spaghetti-monster/fsm-events.h
+++ b/spaghetti-monster/fsm-events.h
@@ -23,10 +23,9 @@
#include
// typedefs
-typedef PROGMEM const uint8_t Event;
-typedef Event * EventPtr;
+typedef uint8_t Event;
typedef struct Emission {
- EventPtr event;
+ Event event;
uint16_t arg;
} Emission;
@@ -36,11 +35,11 @@ typedef struct Emission {
#define MISCHIEF_NOT_MANAGED EVENT_NOT_HANDLED
#ifndef MAX_CLICKS
-#define MAX_CLICKS 4
+#define MAX_CLICKS 15
#endif
#define EV_MAX_LEN ((MAX_CLICKS*2)+3)
-uint8_t current_event[EV_MAX_LEN];
+Event current_event;
// at 0.016 ms per tick, 255 ticks = 4.08 s
static volatile uint16_t ticks_since_last_event = 0;
@@ -52,509 +51,175 @@ static volatile uint16_t ticks_since_last_event = 0;
#define RELEASE_TIMEOUT 24
#endif
-#define A_ENTER_STATE 1
-#define A_LEAVE_STATE 2
-#define A_REENTER_STATE 3
-#define A_TICK 4
-#define A_SLEEP_TICK 5
-#define A_PRESS 6
-#define A_HOLD 7
-#define A_RELEASE 8
-#define A_RELEASE_TIMEOUT 9
-#define A_OVERHEATING 10
-#define A_UNDERHEATING 11
-#define A_VOLTAGE_LOW 12
-//#define A_VOLTAGE_CRITICAL 13
-#define A_DEBUG 255 // test event for debugging
+/* Event structure
+ * Bit 7: 1 for a button input event, 0 for all others.
+ * If bit 7 is 1:
+ * Bits 0,1,2,3: Click counter. Up to 15 clicks.
+ * Bit 4: 1 for a "press" event, 0 for a "release" event.
+ * Bit 5: 1 for a "hold" event, 0 otherwise.
+ * Bit 6: 1 for a "timeout" event, 0 otherwise.
+ * If bit 7 is 0:
+ * Not yet defined.
+ */
+
+// event masks / bits
+#define B_SYSTEM 0b10000000
+#define B_CLICK 0b00000000
+#define B_TIMEOUT 0b01000000
+#define B_HOLD 0b00100000
+#define B_PRESS 0b00010000
+#define B_RELEASE 0b00000000
+#define B_COUNT 0b00001111
+#define B_FLAGS 0b11110000
// Event types
-// TODO: make these progmem-only?
-Event EV_debug[] = {
- A_DEBUG,
- 0 } ;
-Event EV_enter_state[] = {
- A_ENTER_STATE,
- 0 } ;
-Event EV_leave_state[] = {
- A_LEAVE_STATE,
- 0 } ;
-Event EV_reenter_state[] = {
- A_REENTER_STATE,
- 0 } ;
-Event EV_tick[] = {
- A_TICK,
- 0 } ;
+#define EV_debug (B_SYSTEM|0b01111111)
+#define EV_enter_state (B_SYSTEM|0b00001000)
+#define EV_leave_state (B_SYSTEM|0b00001001)
+#define EV_reenter_state (B_SYSTEM|0b00001010)
+#define EV_tick (B_SYSTEM|0b00000001)
#ifdef TICK_DURING_STANDBY
-Event EV_sleep_tick[] = {
- A_SLEEP_TICK,
- 0 } ;
+#define EV_sleep_tick (B_SYSTEM|0b00000011)
#endif
#ifdef USE_LVP
-Event EV_voltage_low[] = {
- A_VOLTAGE_LOW,
- 0 } ;
+#define EV_voltage_low (B_SYSTEM|0b00000100)
#endif
#ifdef USE_THERMAL_REGULATION
-Event EV_temperature_high[] = {
- A_OVERHEATING,
- 0 } ;
-Event EV_temperature_low[] = {
- A_UNDERHEATING,
- 0 } ;
+#define EV_temperature_high (B_SYSTEM|0b00000101)
+#define EV_temperature_low (B_SYSTEM|0b00000110)
#endif
-Event EV_click1_press[] = {
- A_PRESS,
- 0 };
+
+#define EV_none 0
+
// shouldn't normally happen, but UI might reset event while button is down
// so a release with no recorded prior hold could be possible
-Event EV_release[] = {
- A_RELEASE,
- 0 };
-Event EV_click1_release[] = {
- A_PRESS,
- A_RELEASE,
- 0 };
+#define EV_release (B_CLICK|B_RELEASE|0)
+
+#define EV_click1_press (B_CLICK|B_PRESS|1)
+#define EV_click1_hold (B_CLICK|B_HOLD|B_PRESS|1)
+#define EV_click1_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|1)
+#define EV_click1_release (B_CLICK|B_RELEASE|1)
+#define EV_click1_complete (B_CLICK|B_TIMEOUT|1)
#define EV_1click EV_click1_complete
-Event EV_click1_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
#define EV_hold EV_click1_hold
-// FIXME: Should holds use "start+tick" or just "tick" with a tick number?
-// Or "start+tick" with a tick number?
-Event EV_click1_hold[] = {
- A_PRESS,
- A_HOLD,
- 0 };
-Event EV_click1_hold_release[] = {
- A_PRESS,
- A_HOLD,
- A_RELEASE,
- 0 };
-#if MAX_CLICKS >= 2
-Event EV_click2_press[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- 0 };
-Event EV_click2_hold[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_HOLD,
- 0 };
-Event EV_click2_hold_release[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_HOLD,
- A_RELEASE,
- 0 };
-Event EV_click2_release[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- 0 };
+
+#define EV_click2_press (B_CLICK|B_PRESS|2)
+#define EV_click2_hold (B_CLICK|B_HOLD|B_PRESS|2)
+#define EV_click2_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|2)
+#define EV_click2_release (B_CLICK|B_RELEASE|2)
+#define EV_click2_complete (B_CLICK|B_TIMEOUT|2)
#define EV_2clicks EV_click2_complete
-Event EV_click2_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif // MAX_CLICKS >= 2
-#if MAX_CLICKS >= 3
-Event EV_click3_press[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- 0 };
-Event EV_click3_hold[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_HOLD,
- 0 };
-Event EV_click3_hold_release[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_HOLD,
- A_RELEASE,
- 0 };
-Event EV_click3_release[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- 0 };
+
+#define EV_click3_press (B_CLICK|B_PRESS|3)
+#define EV_click3_hold (B_CLICK|B_HOLD|B_PRESS|3)
+#define EV_click3_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|3)
+#define EV_click3_release (B_CLICK|B_RELEASE|3)
+#define EV_click3_complete (B_CLICK|B_TIMEOUT|3)
#define EV_3clicks EV_click3_complete
-Event EV_click3_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif // MAX_CLICKS >= 3
-#if MAX_CLICKS >= 4
+
+#define EV_click4_press (B_CLICK|B_PRESS|4)
+#define EV_click4_hold (B_CLICK|B_HOLD|B_PRESS|4)
+#define EV_click4_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|4)
+#define EV_click4_release (B_CLICK|B_RELEASE|4)
+#define EV_click4_complete (B_CLICK|B_TIMEOUT|4)
#define EV_4clicks EV_click4_complete
-Event EV_click4_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 5
+
+#define EV_click5_press (B_CLICK|B_PRESS|5)
+#define EV_click5_hold (B_CLICK|B_HOLD|B_PRESS|5)
+#define EV_click5_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|5)
+#define EV_click5_release (B_CLICK|B_RELEASE|5)
+#define EV_click5_complete (B_CLICK|B_TIMEOUT|5)
#define EV_5clicks EV_click5_complete
-Event EV_click5_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 6
+
+#define EV_click6_press (B_CLICK|B_PRESS|6)
+#define EV_click6_hold (B_CLICK|B_HOLD|B_PRESS|6)
+#define EV_click6_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|6)
+#define EV_click6_release (B_CLICK|B_RELEASE|6)
+#define EV_click6_complete (B_CLICK|B_TIMEOUT|6)
#define EV_6clicks EV_click6_complete
-Event EV_click6_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 7
+
+#define EV_click7_press (B_CLICK|B_PRESS|7)
+#define EV_click7_hold (B_CLICK|B_HOLD|B_PRESS|7)
+#define EV_click7_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|7)
+#define EV_click7_release (B_CLICK|B_RELEASE|7)
+#define EV_click7_complete (B_CLICK|B_TIMEOUT|7)
#define EV_7clicks EV_click7_complete
-Event EV_click7_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 8
+
+#define EV_click8_press (B_CLICK|B_PRESS|8)
+#define EV_click8_hold (B_CLICK|B_HOLD|B_PRESS|8)
+#define EV_click8_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|8)
+#define EV_click8_release (B_CLICK|B_RELEASE|8)
+#define EV_click8_complete (B_CLICK|B_TIMEOUT|8)
#define EV_8clicks EV_click8_complete
-Event EV_click8_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 9
+
+#define EV_click9_press (B_CLICK|B_PRESS|9)
+#define EV_click9_hold (B_CLICK|B_HOLD|B_PRESS|9)
+#define EV_click9_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|9)
+#define EV_click9_release (B_CLICK|B_RELEASE|9)
+#define EV_click9_complete (B_CLICK|B_TIMEOUT|9)
#define EV_9clicks EV_click9_complete
-Event EV_click9_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 10
+
+#define EV_click10_press (B_CLICK|B_PRESS|10)
+#define EV_click10_hold (B_CLICK|B_HOLD|B_PRESS|10)
+#define EV_click10_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|10)
+#define EV_click10_release (B_CLICK|B_RELEASE|10)
+#define EV_click10_complete (B_CLICK|B_TIMEOUT|10)
#define EV_10clicks EV_click10_complete
-Event EV_click10_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 11
+
+#define EV_click11_press (B_CLICK|B_PRESS|11)
+#define EV_click11_hold (B_CLICK|B_HOLD|B_PRESS|11)
+#define EV_click11_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|11)
+#define EV_click11_release (B_CLICK|B_RELEASE|11)
+#define EV_click11_complete (B_CLICK|B_TIMEOUT|11)
#define EV_11clicks EV_click11_complete
-Event EV_click11_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 12
+
+#define EV_click12_press (B_CLICK|B_PRESS|12)
+#define EV_click12_hold (B_CLICK|B_HOLD|B_PRESS|12)
+#define EV_click12_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|12)
+#define EV_click12_release (B_CLICK|B_RELEASE|12)
+#define EV_click12_complete (B_CLICK|B_TIMEOUT|12)
#define EV_12clicks EV_click12_complete
-Event EV_click12_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 13
+
+#define EV_click13_press (B_CLICK|B_PRESS|13)
+#define EV_click13_hold (B_CLICK|B_HOLD|B_PRESS|13)
+#define EV_click13_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|13)
+#define EV_click13_release (B_CLICK|B_RELEASE|13)
+#define EV_click13_complete (B_CLICK|B_TIMEOUT|13)
#define EV_13clicks EV_click13_complete
-Event EV_click13_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-#if MAX_CLICKS >= 14
+
+#define EV_click14_press (B_CLICK|B_PRESS|14)
+#define EV_click14_hold (B_CLICK|B_HOLD|B_PRESS|14)
+#define EV_click14_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|14)
+#define EV_click14_release (B_CLICK|B_RELEASE|14)
+#define EV_click14_complete (B_CLICK|B_TIMEOUT|14)
#define EV_14clicks EV_click14_complete
-Event EV_click14_complete[] = {
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_PRESS,
- A_RELEASE,
- A_RELEASE_TIMEOUT,
- 0 };
-#endif
-// ... and so on
-
-// A list of button event types for easy iteration
-// TODO: make this progmem-only?
-EventPtr event_sequences[] = {
- EV_click1_press,
- EV_release,
- EV_click1_release,
- EV_click1_complete,
- EV_click1_hold,
- EV_click1_hold_release,
- #if MAX_CLICKS >= 2
- EV_click2_press,
- EV_click2_hold,
- EV_click2_hold_release,
- EV_click2_release,
- EV_click2_complete,
- #endif
- #if MAX_CLICKS >= 3
- EV_click3_press,
- EV_click3_hold,
- EV_click3_hold_release,
- EV_click3_release,
- EV_click3_complete,
- #endif
- #if MAX_CLICKS >= 4
- EV_click4_complete,
- #endif
- #if MAX_CLICKS >= 5
- EV_click5_complete,
- #endif
- #if MAX_CLICKS >= 6
- EV_click6_complete,
- #endif
- #if MAX_CLICKS >= 7
- EV_click7_complete,
- #endif
- #if MAX_CLICKS >= 8
- EV_click8_complete,
- #endif
- #if MAX_CLICKS >= 9
- EV_click9_complete,
- #endif
- #if MAX_CLICKS >= 10
- EV_click10_complete,
- #endif
- #if MAX_CLICKS >= 11
- EV_click11_complete,
- #endif
- #if MAX_CLICKS >= 12
- EV_click12_complete,
- #endif
- #if MAX_CLICKS >= 13
- EV_click13_complete,
- #endif
- #if MAX_CLICKS >= 14
- EV_click14_complete,
- #endif
- // ...
-};
-
-#define events_match(a,b) compare_event_sequences(a,b)
+
+#define EV_click15_press (B_CLICK|B_PRESS|15)
+#define EV_click15_hold (B_CLICK|B_HOLD|B_PRESS|15)
+#define EV_click15_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|15)
+#define EV_click15_release (B_CLICK|B_RELEASE|15)
+#define EV_click15_complete (B_CLICK|B_TIMEOUT|15)
+#define EV_15clicks EV_click15_complete
+
+
+#define events_match(a,b) (a == b)
// return 1 if (a == b), 0 otherwise
-uint8_t compare_event_sequences(uint8_t *a, const uint8_t *b);
+#define compare_event_sequences(a,b) (a == b)
void empty_event_sequence();
uint8_t push_event(uint8_t ev_type);
-// uint8_t last_event(uint8_t offset);
-inline uint8_t last_event_num();
#define EMISSION_QUEUE_LEN 16
// no comment about "volatile emissions"
volatile Emission emissions[EMISSION_QUEUE_LEN];
-void append_emission(EventPtr event, uint16_t arg);
+void append_emission(Event event, uint16_t arg);
void delete_first_emission();
void process_emissions();
//#define emit_now emit
-uint8_t emit_now(EventPtr event, uint16_t arg);
-void emit(EventPtr event, uint16_t arg);
-void emit_current_event(uint16_t arg);
+uint8_t emit_now(Event event, uint16_t arg);
+void emit(Event event, uint16_t arg);
+#define emit_current_event(arg) emit(current_event, arg)
uint8_t nice_delay_ms(uint16_t ms);
//uint8_t nice_delay_4ms(uint8_t ms);
diff --git a/spaghetti-monster/fsm-pcint.c b/spaghetti-monster/fsm-pcint.c
index a79572d..acb627d 100644
--- a/spaghetti-monster/fsm-pcint.c
+++ b/spaghetti-monster/fsm-pcint.c
@@ -75,9 +75,9 @@ void PCINT_inner(uint8_t pressed) {
uint8_t pushed;
if (pressed) {
- pushed = push_event(A_PRESS);
+ pushed = push_event(B_PRESS);
} else {
- pushed = push_event(A_RELEASE);
+ pushed = push_event(B_RELEASE);
}
// check if sequence matches any defined sequences
diff --git a/spaghetti-monster/fsm-states.c b/spaghetti-monster/fsm-states.c
index 09ae804..f91dc4b 100644
--- a/spaghetti-monster/fsm-states.c
+++ b/spaghetti-monster/fsm-states.c
@@ -32,7 +32,7 @@
// TODO: function to call stacked callbacks until one returns "handled"
void _set_state(StatePtr new_state, uint16_t arg,
- EventPtr exit_event, EventPtr enter_event) {
+ Event exit_event, Event enter_event) {
// call old state-exit hook (don't use stack)
if (current_state != NULL) current_state(exit_event, arg);
// set new state
@@ -82,7 +82,7 @@ uint8_t set_state(StatePtr new_state, uint16_t arg) {
#ifndef DONT_USE_DEFAULT_STATE
// bottom state on stack
// handles default actions for LVP, thermal regulation, etc
-uint8_t default_state(EventPtr event, uint16_t arg) {
+uint8_t default_state(Event event, uint16_t arg) {
if (0) {} // this should get compiled out
#ifdef USE_LVP
diff --git a/spaghetti-monster/fsm-states.h b/spaghetti-monster/fsm-states.h
index 6e4a2a0..7d9361b 100644
--- a/spaghetti-monster/fsm-states.h
+++ b/spaghetti-monster/fsm-states.h
@@ -23,7 +23,7 @@
#include "fsm-adc.h"
// typedefs
-typedef uint8_t State(EventPtr event, uint16_t arg);
+typedef uint8_t State(Event event, uint16_t arg);
typedef State * StatePtr;
// top of the stack
@@ -36,12 +36,12 @@ StatePtr state_stack[STATE_STACK_SIZE];
uint8_t state_stack_len = 0;
void _set_state(StatePtr new_state, uint16_t arg,
- EventPtr exit_event, EventPtr enter_event);
+ Event exit_event, Event enter_event);
int8_t push_state(StatePtr new_state, uint16_t arg);
StatePtr pop_state();
uint8_t set_state(StatePtr new_state, uint16_t arg);
#ifndef DONT_USE_DEFAULT_STATE
-uint8_t default_state(EventPtr event, uint16_t arg);
+uint8_t default_state(Event event, uint16_t arg);
#endif
#endif
diff --git a/spaghetti-monster/fsm-wdt.c b/spaghetti-monster/fsm-wdt.c
index e8419bc..cfff1fa 100644
--- a/spaghetti-monster/fsm-wdt.c
+++ b/spaghetti-monster/fsm-wdt.c
@@ -85,15 +85,8 @@ ISR(WDT_vect) {
// append timeout to current event sequence, then
// send event to current state callback
- // preload recent events
- uint8_t le_num = last_event_num();
- uint8_t last_event = 0;
- uint8_t prev_event = 0;
- if (le_num >= 1) last_event = current_event[le_num-1];
- if (le_num >= 2) prev_event = current_event[le_num-2];
-
// callback on each timer tick
- if (last_event == A_HOLD) {
+ if ((current_event & B_FLAGS) == (B_HOLD | B_PRESS)) {
emit(EV_tick, 0); // override tick counter while holding button
}
else {
@@ -101,29 +94,32 @@ ISR(WDT_vect) {
}
// user held button long enough to count as a long click?
- if (last_event == A_PRESS) {
- if (ticks_since_last_event >= HOLD_TIMEOUT) {
- push_event(A_HOLD);
- emit_current_event(0);
+ if (current_event & B_PRESS) {
+ // during a "hold", send a hold event each tick, with a timer
+ if (current_event & B_HOLD) {
+ emit_current_event(ticks_since_last_event);
+ }
+ // has button been down long enough to become a "hold"?
+ else {
+ if (ticks_since_last_event >= HOLD_TIMEOUT) {
+ current_event |= B_HOLD;
+ emit_current_event(0);
+ }
}
}
- // user is still holding button, so tick
- else if (last_event == A_HOLD) {
- emit_current_event(ticks_since_last_event);
- }
-
- // detect completed button presses with expired timeout
- else if (last_event == A_RELEASE) {
+ // event in progress, but button not currently down
+ else if (current_event) {
+ // "hold" event just ended
// no timeout required when releasing a long-press
// TODO? move this logic to PCINT() and simplify things here?
- if (prev_event == A_HOLD) {
+ if (current_event & B_HOLD) {
//emit_current_event(0); // should have been emitted by PCINT
empty_event_sequence();
}
// end and clear event after release timeout
else if (ticks_since_last_event >= RELEASE_TIMEOUT) {
- push_event(A_RELEASE_TIMEOUT);
+ current_event |= B_TIMEOUT;
emit_current_event(0);
empty_event_sequence();
}
--
cgit v1.2.3
From 6b41b5df92128c8810cbe14fd56258d90c3bb2b2 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 06:09:07 -0700
Subject: Several fixes... - Made momentary+lockout modes smaller and work
better. - Fixed buggy timing on hold events; made ticks_since_last_event
reset when it should. - Reduced ROM size by caching volatile
ticks_since_last_event sometimes. - Swapped what the top Event bit means,
because it makes event handlers easier to write. - Made the maximum click
event keep triggering if user keeps pressing, instead of dropping
everything after the limit.
---
spaghetti-monster/anduril/anduril.c | 54 +++++++++++++------------------------
spaghetti-monster/fsm-events.c | 13 ++++++---
spaghetti-monster/fsm-events.h | 6 ++---
spaghetti-monster/fsm-wdt.c | 23 ++++++++++------
4 files changed, 46 insertions(+), 50 deletions(-)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index de4f996..4c3ccd7 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -1166,25 +1166,21 @@ uint8_t goodnight_state(Event event, uint16_t arg) {
uint8_t lockout_state(Event event, uint16_t arg) {
#ifdef MOON_DURING_LOCKOUT_MODE
// momentary(ish) moon mode during lockout
- // not all presses will be counted;
- // it depends on what is in the master event_sequences table
- if (arg == 0) { // Only turn on/off when button state changes
- if (! (event & B_SYSTEM)) { // event is a button click type
- if (event & B_PRESS) { // button is being held
- #ifdef LOCKOUT_MOON_LOWEST
- // Use lowest moon configured
- uint8_t lvl = ramp_smooth_floor;
- if (ramp_discrete_floor < lvl) lvl = ramp_discrete_floor;
- set_level(lvl);
- #else
- // Use moon from current ramp
- set_level(nearest_level(1));
- #endif
- }
- else { // button not being held
- set_level(0);
- }
- }
+ // button is being held
+ if ((event & (B_CLICK | B_PRESS)) == (B_CLICK | B_PRESS)) {
+ #ifdef LOCKOUT_MOON_LOWEST
+ // Use lowest moon configured
+ uint8_t lvl = ramp_smooth_floor;
+ if (ramp_discrete_floor < lvl) lvl = ramp_discrete_floor;
+ set_level(lvl);
+ #else
+ // Use moon from current ramp
+ set_level(nearest_level(1));
+ #endif
+ }
+ // button was released
+ else if ((event & (B_CLICK | B_PRESS)) == (B_CLICK)) {
+ set_level(0);
}
#endif
@@ -1281,29 +1277,17 @@ uint8_t momentary_state(Event event, uint16_t arg) {
// TODO: momentary strobe here? (for light painting)
// light up when the button is pressed; go dark otherwise
- #if 0
- if ((event ^ B_SYSTEM) & B_PRESS) {
+ // button is being held
+ if ((event & (B_CLICK | B_PRESS)) == (B_CLICK | B_PRESS)) {
set_level(memorized_level);
return MISCHIEF_MANAGED;
}
- else if (((event ^ B_SYSTEM) & B_PRESS) == 0) {
+ // button was released
+ else if ((event & (B_CLICK | B_PRESS)) == (B_CLICK)) {
set_level(0);
- empty_event_sequence();
//go_to_standby = 1; // sleep while light is off
return MISCHIEF_MANAGED;
}
- #else
- if (! (event & B_SYSTEM)) { // is a button-related event
- if (event & B_PRESS) { // button is pressed
- set_level(memorized_level);
- } else { // button was released
- set_level(0);
- empty_event_sequence();
- //go_to_standby = 1; // sleep while light is off
- }
- return MISCHIEF_MANAGED;
- }
- #endif
// Sleep, dammit! (but wait a few seconds first)
// (because standby mode uses such little power that it can interfere
diff --git a/spaghetti-monster/fsm-events.c b/spaghetti-monster/fsm-events.c
index 091d4cf..b36c9f4 100644
--- a/spaghetti-monster/fsm-events.c
+++ b/spaghetti-monster/fsm-events.c
@@ -21,7 +21,7 @@
#define FSM_EVENTS_C
void empty_event_sequence() {
- current_event = 0;
+ current_event = EV_none;
// when the user completes an input sequence, interrupt any running timers
// to cancel any delays currently in progress
// This eliminates a whole bunch of extra code:
@@ -34,7 +34,7 @@ uint8_t push_event(uint8_t ev_type) {
ticks_since_last_event = 0; // something happened
// only click events are sent to this function
- //current_event |= B_CLICK;
+ current_event |= B_CLICK;
// handle button presses
if (ev_type == B_PRESS) {
@@ -43,9 +43,9 @@ uint8_t push_event(uint8_t ev_type) {
// increase click counter
if ((current_event & B_COUNT) < (B_COUNT-1)) {
current_event ++;
- return 1; // event pushed
}
- return 0; // maximum number of clicks reached
+ return 1; // event pushed, even if max clicks already reached
+ // (will just repeat the max over and over)
}
// handle button releases
else if (ev_type == B_RELEASE) {
@@ -194,4 +194,9 @@ void emit(Event event, uint16_t arg) {
append_emission(event, arg);
}
+void emit_current_event(uint16_t arg) {
+ ticks_since_last_event = arg;
+ emit(current_event, arg);
+}
+
#endif
diff --git a/spaghetti-monster/fsm-events.h b/spaghetti-monster/fsm-events.h
index d838800..45c95ee 100644
--- a/spaghetti-monster/fsm-events.h
+++ b/spaghetti-monster/fsm-events.h
@@ -63,8 +63,8 @@ static volatile uint16_t ticks_since_last_event = 0;
*/
// event masks / bits
-#define B_SYSTEM 0b10000000
-#define B_CLICK 0b00000000
+#define B_SYSTEM 0b00000000
+#define B_CLICK 0b10000000
#define B_TIMEOUT 0b01000000
#define B_HOLD 0b00100000
#define B_PRESS 0b00010000
@@ -219,7 +219,7 @@ void process_emissions();
//#define emit_now emit
uint8_t emit_now(Event event, uint16_t arg);
void emit(Event event, uint16_t arg);
-#define emit_current_event(arg) emit(current_event, arg)
+void emit_current_event(uint16_t arg);
uint8_t nice_delay_ms(uint16_t ms);
//uint8_t nice_delay_4ms(uint8_t ms);
diff --git a/spaghetti-monster/fsm-wdt.c b/spaghetti-monster/fsm-wdt.c
index cfff1fa..3606c67 100644
--- a/spaghetti-monster/fsm-wdt.c
+++ b/spaghetti-monster/fsm-wdt.c
@@ -76,32 +76,38 @@ ISR(WDT_vect) {
uint8_t pressed = button_is_pressed();
if (was_pressed != pressed) PCINT_inner(pressed);
- //if (ticks_since_last_event < 0xff) ticks_since_last_event ++;
+ // cache this here to reduce ROM size, because it's volatile
+ uint16_t ticks_since_last = ticks_since_last_event;
+
// increment, but loop from max back to half
- ticks_since_last_event = (ticks_since_last_event + 1) \
- | (ticks_since_last_event & 0x8000);
+ //if (ticks_since_last < 0xff) ticks_since_last ++;
+ ticks_since_last = (ticks_since_last + 1) \
+ | (ticks_since_last & 0x8000);
+ // copy back to the original
+ ticks_since_last_event = ticks_since_last;
// if time since last event exceeds timeout,
// append timeout to current event sequence, then
// send event to current state callback
// callback on each timer tick
- if ((current_event & B_FLAGS) == (B_HOLD | B_PRESS)) {
+ if ((current_event & B_FLAGS) == (B_CLICK | B_HOLD | B_PRESS)) {
emit(EV_tick, 0); // override tick counter while holding button
}
else {
- emit(EV_tick, ticks_since_last_event);
+ emit(EV_tick, ticks_since_last);
}
// user held button long enough to count as a long click?
if (current_event & B_PRESS) {
// during a "hold", send a hold event each tick, with a timer
if (current_event & B_HOLD) {
- emit_current_event(ticks_since_last_event);
+ emit_current_event(ticks_since_last);
}
// has button been down long enough to become a "hold"?
else {
- if (ticks_since_last_event >= HOLD_TIMEOUT) {
+ if (ticks_since_last >= HOLD_TIMEOUT) {
+ //ticks_since_last_event = 0;
current_event |= B_HOLD;
emit_current_event(0);
}
@@ -118,8 +124,9 @@ ISR(WDT_vect) {
empty_event_sequence();
}
// end and clear event after release timeout
- else if (ticks_since_last_event >= RELEASE_TIMEOUT) {
+ else if (ticks_since_last >= RELEASE_TIMEOUT) {
current_event |= B_TIMEOUT;
+ //ticks_since_last_event = 0;
emit_current_event(0);
empty_event_sequence();
}
--
cgit v1.2.3
From a71c92e1f27a1ffe513bd0488011f3b6097455da Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 16:00:12 -0700
Subject: Fixed the corner case of a button release when the previous state was
already released.
---
spaghetti-monster/fsm-events.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/spaghetti-monster/fsm-events.c b/spaghetti-monster/fsm-events.c
index b36c9f4..72216ae 100644
--- a/spaghetti-monster/fsm-events.c
+++ b/spaghetti-monster/fsm-events.c
@@ -50,7 +50,7 @@ uint8_t push_event(uint8_t ev_type) {
// handle button releases
else if (ev_type == B_RELEASE) {
// clear the press flag
- current_event ^= B_PRESS;
+ current_event &= (~B_PRESS);
// if a "hold" event just ended, set the timeout flag
// to indicate that the event is done and can be cleared
if (current_event & B_HOLD) { current_event |= B_TIMEOUT; }
--
cgit v1.2.3
From 69d0d92c7902aa27510ab52a533bf91c37363910 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 16:01:12 -0700
Subject: Fixed the sleep tick counter wrapping around to 0 instead of 32768.
---
spaghetti-monster/fsm-events.h | 15 +++++----------
spaghetti-monster/fsm-wdt.c | 4 +++-
2 files changed, 8 insertions(+), 11 deletions(-)
diff --git a/spaghetti-monster/fsm-events.h b/spaghetti-monster/fsm-events.h
index 45c95ee..2fd47b6 100644
--- a/spaghetti-monster/fsm-events.h
+++ b/spaghetti-monster/fsm-events.h
@@ -34,11 +34,6 @@ typedef struct Emission {
#define MISCHIEF_MANAGED EVENT_HANDLED
#define MISCHIEF_NOT_MANAGED EVENT_NOT_HANDLED
-#ifndef MAX_CLICKS
-#define MAX_CLICKS 15
-#endif
-
-#define EV_MAX_LEN ((MAX_CLICKS*2)+3)
Event current_event;
// at 0.016 ms per tick, 255 ticks = 4.08 s
static volatile uint16_t ticks_since_last_event = 0;
@@ -59,7 +54,7 @@ static volatile uint16_t ticks_since_last_event = 0;
* Bit 5: 1 for a "hold" event, 0 otherwise.
* Bit 6: 1 for a "timeout" event, 0 otherwise.
* If bit 7 is 0:
- * Not yet defined.
+ * Sort of ad-hoc, shown in #defines below.
*/
// event masks / bits
@@ -73,6 +68,9 @@ static volatile uint16_t ticks_since_last_event = 0;
#define B_FLAGS 0b11110000
// Event types
+#define EV_none 0
+
+// Events which aren't button presses
#define EV_debug (B_SYSTEM|0b01111111)
#define EV_enter_state (B_SYSTEM|0b00001000)
#define EV_leave_state (B_SYSTEM|0b00001001)
@@ -89,7 +87,7 @@ static volatile uint16_t ticks_since_last_event = 0;
#define EV_temperature_low (B_SYSTEM|0b00000110)
#endif
-#define EV_none 0
+// Button press events
// shouldn't normally happen, but UI might reset event while button is down
// so a release with no recorded prior hold could be possible
@@ -202,9 +200,6 @@ static volatile uint16_t ticks_since_last_event = 0;
#define EV_15clicks EV_click15_complete
-#define events_match(a,b) (a == b)
-// return 1 if (a == b), 0 otherwise
-#define compare_event_sequences(a,b) (a == b)
void empty_event_sequence();
uint8_t push_event(uint8_t ev_type);
diff --git a/spaghetti-monster/fsm-wdt.c b/spaghetti-monster/fsm-wdt.c
index 3606c67..d5bbdb9 100644
--- a/spaghetti-monster/fsm-wdt.c
+++ b/spaghetti-monster/fsm-wdt.c
@@ -64,7 +64,9 @@ ISR(WDT_vect) {
// handle standby mode specially
if (go_to_standby) {
// emit a halfsleep tick, and process it
- emit(EV_sleep_tick, sleep_counter++);
+ emit(EV_sleep_tick, sleep_counter);
+ // wrap around from 65535 to 32768, not 0
+ sleep_counter = (sleep_counter + 1) | (sleep_counter & 0x8000);
process_emissions();
return;
}
--
cgit v1.2.3
From 699a304bdaf67b89b1f7657f15071aeefbebd46b Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 16:01:40 -0700
Subject: Updated the documentation to reflect recent changes to the event
system.
---
spaghetti-monster/spaghetti-monster.txt | 103 ++++++++++++++++++++------------
1 file changed, 64 insertions(+), 39 deletions(-)
diff --git a/spaghetti-monster/spaghetti-monster.txt b/spaghetti-monster/spaghetti-monster.txt
index 0401224..9e051f1 100644
--- a/spaghetti-monster/spaghetti-monster.txt
+++ b/spaghetti-monster/spaghetti-monster.txt
@@ -112,6 +112,11 @@ Event types:
entering the state. When 'arg' exceeds 65535, it wraps around
to 32768.
+ - EV_sleep_tick: This happens every 0.5s during standby, if
+ enabled at compile time. The 'arg' is the number of ticks since
+ entering the state. When 'arg' exceeds 65535, it wraps around
+ to 32768.
+
LVP and thermal regulation:
- EV_voltage_low: Sent whenever the input power drops below the
@@ -130,57 +135,81 @@ Event types:
Button presses:
- - EV_1click: The user clicked the e-switch, released it, and
- enough time passed that no more clicks were detected.
+ Button events can be referred to either by pre-defined symbols, or
+ by teasing out the flags manually. The structure of a button
+ event is as follows:
+
+ - Bit 7: 1 for button events, 0 otherwise.
+
+ - Bit 6: 1 for a "timeout" event (signals the end of a
+ sequence), or 0 otherwise.
+
+ - Bit 5: 1 for a "hold" event, 0 otherwise. This flag is only
+ necessary because, without it, it would be impossible to
+ distinguish between "click, click, timeout" and "click, hold,
+ release".
- - EV_2clicks: The user clicked and released the e-switch twice, then
- enough time passed that no more clicks were detected.
+ - Bit 4: 1 if button is currently pressed, 0 otherwise. Button
+ release events look just like button press events, except this
+ is not set.
- - EV_3clicks: The user clicked and released the e-switch three
- times, then enough time passed that no more clicks were detected.
+ - Bits 0,1,2,3: Counter for how many clicks there have been.
+ The first click is 1, second is 2, and it goes up to 15 clicks
+ in a row. Clicks after 15 are coded as 15.
- - EV_4clicks: The user clicked and released the e-switch four times,
- then enough time passed that no more clicks were detected.
+ The pre-defined button event symbols are like the following:
- - EV_click1_hold: The user pressed the button and is still holding
- it. The 'arg' indicates how many clock ticks since the "hold"
- state started.
+ - EV_click1_press: The user pressed the button, but no time has
+ passed since then.
- - EV_click1_hold_release: The user pressed the button, held it for a
- while, and then released it. No timeout is attempted after this.
+ - EV_click1_release: The user pressed and released the button,
+ but no time has passed since then.
- - EV_click2_hold: The user clicked once, then pressed the button and
- is still holding it. The 'arg' indicates how many clock ticks
- since the "hold" state started.
+ - EV_click1_complete: The user clicked the e-switch, released
+ it, and enough time passed that no more clicks were detected.
+ (a.k.a. EV_1click)
- - EV_click2_hold_release: The user clicked once, then pressed the
- button, held it for a while, and released it. No timeout is
- attempted after this.
+ - EV_click1_hold: The user pressed the button, and continued
+ holding it long enough to count as a "hold" event. This event
+ is sent once per timer tick as long as the button is held, and
+ the 'arg' value indicates how many timer ticks since the
+ button state went from 'press' to 'hold'.
- - EV_click1_press: The user pressed the button and it's still down.
- No time has yet passed.
+ - EV_click1_hold_release: The button was released at the end of
+ a "hold" event. This is the end of the input sequence,
+ because no timeout period is used after a hold.
- - EV_click1_release: The user quickly pressed and released the
- button. The click timeout has not yet expired, so they might
- still click again.
+ It's worth noting that a "hold" event can only happen at the
+ end of an input sequence, and the sequence will reset to empty
+ after the hold is released.
- - EV_click2_press: The user pressed the button, released it, pressed
- again, and it's still down. No time has yet passed since then.
+ If the user pressed the button more than once, events follow the
+ same pattern. These are the same as above, except with a full
+ short-press and release first.
- - EV_click2_release: The quickly pressed and released the button
- twice. The click timeout has not yet expired, so they might still
- click again.
+ - EV_click2_press
+ - EV_click2_release
+ - EV_click2_complete (a.k.a. EV_2clicks)
+ - EV_click2_hold
+ - EV_click2_hold_release
+
+ Each of the above patterns continues up to 15 clicks.
+
+ To match entire categories of events, use the bitmasks provided.
+ For example, to match button events where the button is down or
+ the button is up, the code would look like this:
+
+ if ((event & (B_CLICK | B_PRESS)) == (B_CLICK | B_PRESS)) {
+ // button is down (can be a press event or a hold event)
+ }
+ else if ((event & (B_CLICK | B_PRESS)) == (B_CLICK)) {
+ // button was just released
+ }
In theory, you could also define your own arbitrary event types, and
emit() them as necessary, and handle them in State functions the same
as any other event.
- One thing to note if you create your own Event types: The copy which
- gets sent to States must be in the 'event_sequences' array, meaning
- the State gets a const PROGMEM version of the Event. It cannot simply
- send the dynamic 'current_event' object, because it has probably
- already changed by the time the callback happens.
-
Cooperative multitasking:
@@ -287,10 +316,6 @@ Useful #defines:
becomes a "click" event? Basically, the maximum time between
clicks in a double-click or triple-click.
- - MAX_CLICKS N: Convenience define to limit the size of the
- recognized Event arrays. Click sequences longer than N won't be
- recognized or sent to State functions.
-
- USE_BATTCHECK: Enable the battcheck function. Also define one of
the following to select a display style:
--
cgit v1.2.3
From 453199bfab1b9c431ce07b5b32aabdd115dcd6e6 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 16:03:07 -0700
Subject: Updated most of the UIs to use the new event API.
---
spaghetti-monster/baton/baton.c | 12 +++---
spaghetti-monster/darkhorse/darkhorse.c | 28 +++++++-------
spaghetti-monster/meteor/meteor.c | 62 +++++++++++++++----------------
spaghetti-monster/momentary/momentary.c | 2 +-
spaghetti-monster/ramping-ui/ramping-ui.c | 20 +++++-----
spaghetti-monster/werner/werner.c | 33 ++++++++--------
6 files changed, 78 insertions(+), 79 deletions(-)
diff --git a/spaghetti-monster/baton/baton.c b/spaghetti-monster/baton/baton.c
index d4725ef..d138297 100644
--- a/spaghetti-monster/baton/baton.c
+++ b/spaghetti-monster/baton/baton.c
@@ -24,9 +24,9 @@
#include "spaghetti-monster.h"
// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
-uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t lockout_state(EventPtr event, uint16_t arg);
+uint8_t off_state(Event event, uint16_t arg);
+uint8_t steady_state(Event event, uint16_t arg);
+uint8_t lockout_state(Event event, uint16_t arg);
// brightness control
uint8_t memorized_level = 1;
@@ -47,7 +47,7 @@ void set_level(uint8_t lvl) {
PWM2_LVL = pwm2_levels[lvl];
}
-uint8_t off_state(EventPtr event, uint16_t arg) {
+uint8_t off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
go_to_standby = 1; // sleep while off (lower power use)
@@ -86,7 +86,7 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t steady_state(EventPtr event, uint16_t arg) {
+uint8_t steady_state(Event event, uint16_t arg) {
// turn LED on when we first enter the mode
if (event == EV_enter_state) {
// remember this level, unless it's moon or turbo
@@ -146,7 +146,7 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t lockout_state(EventPtr event, uint16_t arg) {
+uint8_t lockout_state(Event event, uint16_t arg) {
// stay asleep while locked
if (event == EV_tick) {
PWM1_LVL = 0; PWM2_LVL = 0; // make sure emitters are off
diff --git a/spaghetti-monster/darkhorse/darkhorse.c b/spaghetti-monster/darkhorse/darkhorse.c
index 97053b5..d76afc2 100644
--- a/spaghetti-monster/darkhorse/darkhorse.c
+++ b/spaghetti-monster/darkhorse/darkhorse.c
@@ -32,16 +32,16 @@
#include "spaghetti-monster.h"
// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
-uint8_t low_mode_state(EventPtr event, uint16_t arg);
-uint8_t med_mode_state(EventPtr event, uint16_t arg);
-uint8_t hi_mode_state(EventPtr event, uint16_t arg);
-uint8_t strobe_beacon_state(EventPtr event, uint16_t arg);
+uint8_t off_state(Event event, uint16_t arg);
+uint8_t low_mode_state(Event event, uint16_t arg);
+uint8_t med_mode_state(Event event, uint16_t arg);
+uint8_t hi_mode_state(Event event, uint16_t arg);
+uint8_t strobe_beacon_state(Event event, uint16_t arg);
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg);
+uint8_t battcheck_state(Event event, uint16_t arg);
#endif
// Not a FSM state, just handles stuff common to all low/med/hi states
-uint8_t any_mode_state(EventPtr event, uint16_t arg, uint8_t *primary, uint8_t *secondary, uint8_t *modes);
+uint8_t any_mode_state(Event event, uint16_t arg, uint8_t *primary, uint8_t *secondary, uint8_t *modes);
void load_config();
void save_config();
@@ -89,7 +89,7 @@ inline void set_med_mode() { set_any_mode(M1, M2, med_modes); }
inline void set_hi_mode() { set_any_mode(H1, H2, hi_modes); }
-uint8_t off_state(EventPtr event, uint16_t arg) {
+uint8_t off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
set_level(0);
@@ -163,7 +163,7 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
}
-uint8_t any_mode_state(EventPtr event, uint16_t arg, uint8_t *primary, uint8_t *secondary, uint8_t *modes) {
+uint8_t any_mode_state(Event event, uint16_t arg, uint8_t *primary, uint8_t *secondary, uint8_t *modes) {
// turn on LED when entering the mode
if (event == EV_enter_state) {
set_any_mode(*primary, *secondary, modes);
@@ -236,27 +236,27 @@ uint8_t any_mode_state(EventPtr event, uint16_t arg, uint8_t *primary, uint8_t *
return EVENT_NOT_HANDLED;
}
-uint8_t low_mode_state(EventPtr event, uint16_t arg) {
+uint8_t low_mode_state(Event event, uint16_t arg) {
return any_mode_state(event, arg, &L1, &L2, low_modes);
}
-uint8_t med_mode_state(EventPtr event, uint16_t arg) {
+uint8_t med_mode_state(Event event, uint16_t arg) {
return any_mode_state(event, arg, &M1, &M2, med_modes);
}
-uint8_t hi_mode_state(EventPtr event, uint16_t arg) {
+uint8_t hi_mode_state(Event event, uint16_t arg) {
return any_mode_state(event, arg, &H1, &H2, hi_modes);
}
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg) {
+uint8_t battcheck_state(Event event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
#endif
-uint8_t strobe_beacon_state(EventPtr event, uint16_t arg) {
+uint8_t strobe_beacon_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
diff --git a/spaghetti-monster/meteor/meteor.c b/spaghetti-monster/meteor/meteor.c
index b2467d7..a50b034 100644
--- a/spaghetti-monster/meteor/meteor.c
+++ b/spaghetti-monster/meteor/meteor.c
@@ -1,5 +1,6 @@
/*
* Meteor: Meteor M43 clone UI for SpaghettiMonster.
+ * (in progress, not really in a usable state yet)
*
* Copyright (C) 2017 Selene ToyKeeper
*
@@ -29,26 +30,25 @@
#define DONT_DELAY_AFTER_BATTCHECK
//#define USE_EEPROM
//#define EEPROM_BYTES 5
-#define MAX_CLICKS 11
#include "spaghetti-monster.h"
// FSM states
-uint8_t base_off_state(EventPtr event, uint16_t arg);
-uint8_t ui1_off_state(EventPtr event, uint16_t arg);
-uint8_t ui2_off_state(EventPtr event, uint16_t arg);
-uint8_t ui3_off_state(EventPtr event, uint16_t arg);
-uint8_t base_on_state(EventPtr event, uint16_t arg, uint8_t *mode, uint8_t *group);
-uint8_t ui1_on_state(EventPtr event, uint16_t arg);
-uint8_t ui2_on_state(EventPtr event, uint16_t arg);
-uint8_t ui3_on_state(EventPtr event, uint16_t arg);
-uint8_t beacon_state(EventPtr event, uint16_t arg);
-uint8_t battcheck_state(EventPtr event, uint16_t arg);
-uint8_t strobe_state(EventPtr event, uint16_t arg);
-uint8_t biking_state(EventPtr event, uint16_t arg);
-uint8_t lockout_state(EventPtr event, uint16_t arg);
-uint8_t momentary_state(EventPtr event, uint16_t arg);
+uint8_t base_off_state(Event event, uint16_t arg);
+uint8_t ui1_off_state(Event event, uint16_t arg);
+uint8_t ui2_off_state(Event event, uint16_t arg);
+uint8_t ui3_off_state(Event event, uint16_t arg);
+uint8_t base_on_state(Event event, uint16_t arg, uint8_t *mode, uint8_t *group);
+uint8_t ui1_on_state(Event event, uint16_t arg);
+uint8_t ui2_on_state(Event event, uint16_t arg);
+uint8_t ui3_on_state(Event event, uint16_t arg);
+uint8_t beacon_state(Event event, uint16_t arg);
+uint8_t battcheck_state(Event event, uint16_t arg);
+uint8_t strobe_state(Event event, uint16_t arg);
+uint8_t biking_state(Event event, uint16_t arg);
+uint8_t lockout_state(Event event, uint16_t arg);
+uint8_t momentary_state(Event event, uint16_t arg);
// Not a FSM state, just handles stuff common to all low/med/hi states
-uint8_t any_mode_state(EventPtr event, uint16_t arg, uint8_t *primary, uint8_t *secondary, uint8_t *modes);
+uint8_t any_mode_state(Event event, uint16_t arg, uint8_t *primary, uint8_t *secondary, uint8_t *modes);
#ifdef USE_EEPROM
void load_config();
@@ -99,7 +99,7 @@ void blink_fast() {
set_level(0);
}
-uint8_t base_off_state(EventPtr event, uint16_t arg) {
+uint8_t base_off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
set_level(0);
@@ -154,7 +154,7 @@ uint8_t base_off_state(EventPtr event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t ui1_off_state(EventPtr event, uint16_t arg) {
+uint8_t ui1_off_state(Event event, uint16_t arg) {
UI = 1;
if (event == EV_enter_state) {
return EVENT_HANDLED;
@@ -187,7 +187,7 @@ uint8_t ui1_off_state(EventPtr event, uint16_t arg) {
return base_off_state(event, arg);
}
-uint8_t ui2_off_state(EventPtr event, uint16_t arg) {
+uint8_t ui2_off_state(Event event, uint16_t arg) {
UI = 2;
if (event == EV_enter_state) {
return EVENT_HANDLED;
@@ -220,7 +220,7 @@ uint8_t ui2_off_state(EventPtr event, uint16_t arg) {
return base_off_state(event, arg);
}
-uint8_t ui3_off_state(EventPtr event, uint16_t arg) {
+uint8_t ui3_off_state(Event event, uint16_t arg) {
UI = 3;
if (event == EV_enter_state) {
return EVENT_HANDLED;
@@ -259,7 +259,7 @@ uint8_t ui3_off_state(EventPtr event, uint16_t arg) {
return base_off_state(event, arg);
}
-uint8_t base_on_state(EventPtr event, uint16_t arg, uint8_t *mode, uint8_t *group) {
+uint8_t base_on_state(Event event, uint16_t arg, uint8_t *mode, uint8_t *group) {
// 1 click: off
if (event == EV_1click) {
set_state(base_off_state, 0);
@@ -289,7 +289,7 @@ uint8_t base_on_state(EventPtr event, uint16_t arg, uint8_t *mode, uint8_t *grou
return EVENT_NOT_HANDLED;
}
-uint8_t ui1_on_state(EventPtr event, uint16_t arg) {
+uint8_t ui1_on_state(Event event, uint16_t arg) {
// turn on LED when entering the mode
static uint8_t *mode = &UI1_mode1;
static uint8_t *group = UI1_group1;
@@ -328,7 +328,7 @@ uint8_t ui1_on_state(EventPtr event, uint16_t arg) {
return base_on_state(event, arg, mode, group);
}
-uint8_t ui2_on_state(EventPtr event, uint16_t arg) {
+uint8_t ui2_on_state(Event event, uint16_t arg) {
// turn on LED when entering the mode
static uint8_t *mode = &UI2_mode1;
static uint8_t *group = UI2_group1;
@@ -377,7 +377,7 @@ uint8_t ui2_on_state(EventPtr event, uint16_t arg) {
return base_on_state(event, arg, mode, group);
}
-uint8_t ui3_on_state(EventPtr event, uint16_t arg) {
+uint8_t ui3_on_state(Event event, uint16_t arg) {
// turn on LED when entering the mode
static uint8_t *mode = &UI3_mode1;
if (event == EV_enter_state) {
@@ -424,7 +424,7 @@ uint8_t ui3_on_state(EventPtr event, uint16_t arg) {
}
-uint8_t blinky_base_state(EventPtr event, uint16_t arg) {
+uint8_t blinky_base_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(base_off_state, 0);
@@ -433,27 +433,27 @@ uint8_t blinky_base_state(EventPtr event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t beacon_state(EventPtr event, uint16_t arg) {
+uint8_t beacon_state(Event event, uint16_t arg) {
return blinky_base_state(event, arg);
}
-uint8_t battcheck_state(EventPtr event, uint16_t arg) {
+uint8_t battcheck_state(Event event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t strobe_state(EventPtr event, uint16_t arg) {
+uint8_t strobe_state(Event event, uint16_t arg) {
return blinky_base_state(event, arg);
}
-uint8_t biking_state(EventPtr event, uint16_t arg) {
+uint8_t biking_state(Event event, uint16_t arg) {
return blinky_base_state(event, arg);
}
-uint8_t lockout_state(EventPtr event, uint16_t arg) {
+uint8_t lockout_state(Event event, uint16_t arg) {
return blinky_base_state(event, arg);
}
-uint8_t momentary_state(EventPtr event, uint16_t arg) {
+uint8_t momentary_state(Event event, uint16_t arg) {
return blinky_base_state(event, arg);
}
diff --git a/spaghetti-monster/momentary/momentary.c b/spaghetti-monster/momentary/momentary.c
index d4ac1db..0372b3d 100644
--- a/spaghetti-monster/momentary/momentary.c
+++ b/spaghetti-monster/momentary/momentary.c
@@ -40,7 +40,7 @@ void light_off() {
PWM2_LVL = 0;
}
-uint8_t momentary_state(EventPtr event, uint16_t arg) {
+uint8_t momentary_state(Event event, uint16_t arg) {
if (event == EV_click1_press) {
brightness = 255;
diff --git a/spaghetti-monster/ramping-ui/ramping-ui.c b/spaghetti-monster/ramping-ui/ramping-ui.c
index e6f571d..234cdf4 100644
--- a/spaghetti-monster/ramping-ui/ramping-ui.c
+++ b/spaghetti-monster/ramping-ui/ramping-ui.c
@@ -31,12 +31,12 @@
#include "spaghetti-monster.h"
// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
-uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t strobe_state(EventPtr event, uint16_t arg);
+uint8_t off_state(Event event, uint16_t arg);
+uint8_t steady_state(Event event, uint16_t arg);
+uint8_t strobe_state(Event event, uint16_t arg);
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg);
-uint8_t tempcheck_state(EventPtr event, uint16_t arg);
+uint8_t battcheck_state(Event event, uint16_t arg);
+uint8_t tempcheck_state(Event event, uint16_t arg);
#endif
// brightness control
@@ -54,7 +54,7 @@ volatile uint8_t strobe_delay = 67;
volatile uint8_t strobe_type = 0; // 0 == party strobe, 1 == tactical strobe
-uint8_t off_state(EventPtr event, uint16_t arg) {
+uint8_t off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
set_level(0);
@@ -121,7 +121,7 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
}
-uint8_t steady_state(EventPtr event, uint16_t arg) {
+uint8_t steady_state(Event event, uint16_t arg) {
// turn LED on when we first enter the mode
if (event == EV_enter_state) {
// remember this level, unless it's moon or turbo
@@ -243,7 +243,7 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
}
-uint8_t strobe_state(EventPtr event, uint16_t arg) {
+uint8_t strobe_state(Event event, uint16_t arg) {
if (event == EV_enter_state) {
return MISCHIEF_MANAGED;
}
@@ -281,7 +281,7 @@ uint8_t strobe_state(EventPtr event, uint16_t arg) {
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg) {
+uint8_t battcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -295,7 +295,7 @@ uint8_t battcheck_state(EventPtr event, uint16_t arg) {
return EVENT_NOT_HANDLED;
}
-uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
+uint8_t tempcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
diff --git a/spaghetti-monster/werner/werner.c b/spaghetti-monster/werner/werner.c
index 3c55d98..b6cdf12 100644
--- a/spaghetti-monster/werner/werner.c
+++ b/spaghetti-monster/werner/werner.c
@@ -73,7 +73,6 @@
#define USE_RAMPING
#define RAMP_LENGTH 150 // default, if not overridden in a driver cfg file
#define USE_BATTCHECK
-#define MAX_CLICKS 4
#define USE_IDLE_MODE // reduce power use while awake and no tasks are pending
#define USE_DYNAMIC_UNDERCLOCKING // cut clock speed at very low modes for better efficiency
@@ -92,26 +91,26 @@
// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
+uint8_t off_state(Event event, uint16_t arg);
// simple numeric entry config menu
-uint8_t config_state_base(EventPtr event, uint16_t arg,
+uint8_t config_state_base(Event event, uint16_t arg,
uint8_t num_config_steps,
void (*savefunc)());
#define MAX_CONFIG_VALUES 3
uint8_t config_state_values[MAX_CONFIG_VALUES];
// ramping mode and its related config mode
-uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t ramp_config_state(EventPtr event, uint16_t arg);
+uint8_t steady_state(Event event, uint16_t arg);
+uint8_t ramp_config_state(Event event, uint16_t arg);
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg);
+uint8_t battcheck_state(Event event, uint16_t arg);
#endif
#ifdef USE_THERMAL_REGULATION
-uint8_t tempcheck_state(EventPtr event, uint16_t arg);
-uint8_t thermal_config_state(EventPtr event, uint16_t arg);
+uint8_t tempcheck_state(Event event, uint16_t arg);
+uint8_t thermal_config_state(Event event, uint16_t arg);
#endif
// general helper function for config modes
-uint8_t number_entry_state(EventPtr event, uint16_t arg);
+uint8_t number_entry_state(Event event, uint16_t arg);
// return value from number_entry_state()
volatile uint8_t number_entry_value;
@@ -152,7 +151,7 @@ uint8_t target_level = 0;
#endif
-uint8_t off_state(EventPtr event, uint16_t arg) {
+uint8_t off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if ((event == EV_enter_state) || (event == EV_reenter_state)) {
// let the user know the power is connected
@@ -230,7 +229,7 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
}
-uint8_t steady_state(EventPtr event, uint16_t arg) {
+uint8_t steady_state(Event event, uint16_t arg) {
uint8_t mode_min = ramp_discrete_floor;
uint8_t mode_max = ramp_discrete_ceil;
uint8_t ramp_step_size = ramp_discrete_step_size;
@@ -375,7 +374,7 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg) {
+uint8_t battcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -392,7 +391,7 @@ uint8_t battcheck_state(EventPtr event, uint16_t arg) {
#endif
#ifdef USE_THERMAL_REGULATION
-uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
+uint8_t tempcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -415,7 +414,7 @@ uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
// ask the user for a sequence of numbers, then save them and return to caller
-uint8_t config_state_base(EventPtr event, uint16_t arg,
+uint8_t config_state_base(Event event, uint16_t arg,
uint8_t num_config_steps,
void (*savefunc)()) {
static uint8_t config_step;
@@ -463,7 +462,7 @@ void ramp_config_save() {
if (val) ramp_discrete_steps = val;
}
-uint8_t ramp_config_state(EventPtr event, uint16_t arg) {
+uint8_t ramp_config_state(Event event, uint16_t arg) {
uint8_t num_config_steps;
num_config_steps = 3;
return config_state_base(event, arg,
@@ -491,14 +490,14 @@ void thermal_config_save() {
if (therm_ceil > MAX_THERM_CEIL) therm_ceil = MAX_THERM_CEIL;
}
-uint8_t thermal_config_state(EventPtr event, uint16_t arg) {
+uint8_t thermal_config_state(Event event, uint16_t arg) {
return config_state_base(event, arg,
2, thermal_config_save);
}
#endif
-uint8_t number_entry_state(EventPtr event, uint16_t arg) {
+uint8_t number_entry_state(Event event, uint16_t arg) {
static uint8_t value;
static uint8_t blinks_left;
static uint8_t entry_step;
--
cgit v1.2.3
From 7f199d9e52a73393530b296e5ff1e0fcaf0140bf Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 16:03:39 -0700
Subject: Added a README for the Werner UI. Fixed its build script.
---
spaghetti-monster/werner/README | 56 +++++++++++++++++++++++++++++++++++
spaghetti-monster/werner/build-all.sh | 2 +-
2 files changed, 57 insertions(+), 1 deletion(-)
create mode 100644 spaghetti-monster/werner/README
diff --git a/spaghetti-monster/werner/README b/spaghetti-monster/werner/README
new file mode 100644
index 0000000..5fe392d
--- /dev/null
+++ b/spaghetti-monster/werner/README
@@ -0,0 +1,56 @@
+This is a Werner-style interface for dual-switch lights
+(e-switch + clicky switch). What that means is:
+
+While the clicky switch is off:
+
+ - Click the clicky switch: Turn on, at the last-used level. The clicky
+ switch works as a momentary mode.
+
+ - Click the clicky switch while holding the e-switch: Go into sort of a
+ utility mode.
+
+While on, in a normal steady mode:
+
+ - Click the clicky switch: Turn off.
+
+ - Click the e-switch: Brighter. One step per click.
+
+ - Hold the e-switch: Dimmer. Keep holding to go down multiple steps.
+
+While in standby, in utility mode:
+
+ - Click the e-switch: Turn on.
+
+ - Hold the e-switch: Turn on at lowest level.
+
+ - Double-click the e-switch: Turn on at highest level.
+
+ - Triple-click the e-switch: Battery check mode.
+
+ - Quad-click the e-switch: Ramp config mode.
+
+While in battery check mode:
+
+ - Click either switch: Turn off.
+
+ - Double-click the e-switch: Go to temperature check mode.
+
+While in temperature check mode:
+
+ - Click either switch: Turn off.
+
+ - Double-click the e-switch: Go to battery check mode.
+
+ - Quad-click the e-switch: Go to thermal config mode.
+
+Ramp config mode and thermal config mode work the same as in Anduril or
+RampingIOS V3. The options are:
+
+ - Ramp config mode:
+ 1. Floor level.
+ 2. Ceiling level.
+ 3. Number of steps.
+
+ - Thermal config mode:
+ 1. Calibrate sensor by entering current temperature in C.
+ 2. Set temperature limit to 30 C + N clicks.
diff --git a/spaghetti-monster/werner/build-all.sh b/spaghetti-monster/werner/build-all.sh
index 944b31d..43879bb 100755
--- a/spaghetti-monster/werner/build-all.sh
+++ b/spaghetti-monster/werner/build-all.sh
@@ -14,6 +14,6 @@ for TARGET in \
FW3A \
; do
echo "===== $TARGET ====="
- ../../../bin/build-85.sh "$UI" "-DFSM_${TARGET}_DRIVER"
+ ../../../bin/build.sh 85 "$UI" "-DFSM_${TARGET}_DRIVER"
mv -f "$UI".hex "$UI".$TARGET.hex
done
--
cgit v1.2.3
From 741b29e7b31ca460674a5cc11ac00628c8bf8e1b Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 16:04:43 -0700
Subject: Updated RampingIOS V3 to new event API. Applied recent changes from
Anduril too.
---
spaghetti-monster/anduril/anduril.c | 9 ---
spaghetti-monster/rampingios/rampingiosv3.c | 109 ++++++++++++++--------------
2 files changed, 56 insertions(+), 62 deletions(-)
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index 4c3ccd7..ec16497 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -146,15 +146,6 @@
#define MAX_BIKING_LEVEL 120 // should be 127 or less
#define USE_BATTCHECK
-// determine the highest number of clicks to handle
-#ifdef USE_INDICATOR_LED
-#define MAX_CLICKS 7
-#elif defined(USE_MUGGLE_MODE)
-#define MAX_CLICKS 6
-#else
-#define MAX_CLICKS 5
-#endif
-
#if defined(USE_MUGGLE_MODE)
#ifndef MUGGLE_FLOOR
#define MUGGLE_FLOOR 22
diff --git a/spaghetti-monster/rampingios/rampingiosv3.c b/spaghetti-monster/rampingios/rampingiosv3.c
index 2aeeddf..4142121 100644
--- a/spaghetti-monster/rampingios/rampingiosv3.c
+++ b/spaghetti-monster/rampingios/rampingiosv3.c
@@ -112,9 +112,10 @@
/********* Configure SpaghettiMonster *********/
#define USE_DELAY_ZERO
#define USE_RAMPING
+#ifndef RAMP_LENGTH
#define RAMP_LENGTH 150 // default, if not overridden in a driver cfg file
+#endif
#define USE_BATTCHECK
-#define MAX_CLICKS 10
#define USE_IDLE_MODE // reduce power use while awake and no tasks are pending
#define USE_DYNAMIC_UNDERCLOCKING // cut clock speed at very low modes for better efficiency
@@ -141,34 +142,34 @@
// FSM states
-uint8_t off_state(EventPtr event, uint16_t arg);
+uint8_t off_state(Event event, uint16_t arg);
// simple numeric entry config menu
-uint8_t config_state_base(EventPtr event, uint16_t arg,
+uint8_t config_state_base(Event event, uint16_t arg,
uint8_t num_config_steps,
void (*savefunc)());
#define MAX_CONFIG_VALUES 3
uint8_t config_state_values[MAX_CONFIG_VALUES];
// ramping mode and its related config mode
-uint8_t steady_state(EventPtr event, uint16_t arg);
-uint8_t ramp_config_state(EventPtr event, uint16_t arg);
+uint8_t steady_state(Event event, uint16_t arg);
+uint8_t ramp_config_state(Event event, uint16_t arg);
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg);
+uint8_t battcheck_state(Event event, uint16_t arg);
#endif
#ifdef USE_THERMAL_REGULATION
-uint8_t tempcheck_state(EventPtr event, uint16_t arg);
-uint8_t thermal_config_state(EventPtr event, uint16_t arg);
+uint8_t tempcheck_state(Event event, uint16_t arg);
+uint8_t thermal_config_state(Event event, uint16_t arg);
#endif
// beacon mode and its related config mode
-uint8_t beacon_state(EventPtr event, uint16_t arg);
-uint8_t beacon_config_state(EventPtr event, uint16_t arg);
+uint8_t beacon_state(Event event, uint16_t arg);
+uint8_t beacon_config_state(Event event, uint16_t arg);
// soft lockout
#define MOON_DURING_LOCKOUT_MODE
-uint8_t lockout_state(EventPtr event, uint16_t arg);
+uint8_t lockout_state(Event event, uint16_t arg);
// momentary / signalling mode
-uint8_t momentary_state(EventPtr event, uint16_t arg);
+uint8_t momentary_state(Event event, uint16_t arg);
// general helper function for config modes
-uint8_t number_entry_state(EventPtr event, uint16_t arg);
+uint8_t number_entry_state(Event event, uint16_t arg);
// return value from number_entry_state()
volatile uint8_t number_entry_value;
@@ -177,7 +178,7 @@ void blink_confirm(uint8_t num);
void indicator_blink(uint8_t arg);
#endif
#ifdef USE_INDICATOR_LED
-uint8_t auxled_next_state(EventPtr event, uint16_t arg);
+uint8_t auxled_next_state(Event event, uint16_t arg);
#endif
// remember stuff even after battery was changed
@@ -246,7 +247,7 @@ uint8_t target_level = 0;
volatile uint8_t beacon_seconds = 2;
-uint8_t off_state(EventPtr event, uint16_t arg) {
+uint8_t off_state(Event event, uint16_t arg) {
// turn emitter off when entering state
if (event == EV_enter_state) {
set_level(0);
@@ -371,7 +372,7 @@ uint8_t off_state(EventPtr event, uint16_t arg) {
}
-uint8_t steady_state(EventPtr event, uint16_t arg) {
+uint8_t steady_state(Event event, uint16_t arg) {
uint8_t mode_min = ramp_smooth_floor;
uint8_t mode_max = ramp_smooth_ceil;
uint8_t ramp_step_size = 1;
@@ -677,7 +678,7 @@ uint8_t steady_state(EventPtr event, uint16_t arg) {
#ifdef USE_BATTCHECK
-uint8_t battcheck_state(EventPtr event, uint16_t arg) {
+uint8_t battcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -694,7 +695,7 @@ uint8_t battcheck_state(EventPtr event, uint16_t arg) {
#ifdef USE_THERMAL_REGULATION
-uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
+uint8_t tempcheck_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -710,7 +711,7 @@ uint8_t tempcheck_state(EventPtr event, uint16_t arg) {
#endif
-uint8_t beacon_state(EventPtr event, uint16_t arg) {
+uint8_t beacon_state(Event event, uint16_t arg) {
// 1 click: off
if (event == EV_1click) {
set_state(off_state, 0);
@@ -727,29 +728,24 @@ uint8_t beacon_state(EventPtr event, uint16_t arg) {
}
-uint8_t lockout_state(EventPtr event, uint16_t arg) {
+uint8_t lockout_state(Event event, uint16_t arg) {
#ifdef MOON_DURING_LOCKOUT_MODE
// momentary(ish) moon mode during lockout
- // not all presses will be counted;
- // it depends on what is in the master event_sequences table
- uint8_t last = 0;
- for(uint8_t i=0; pgm_read_byte(event + i) && (i TICKS_PER_SECOND*15) { // sleep after 15 seconds
go_to_standby = 1; // sleep while light is off
+ // TODO: lighted button should use lockout config?
}
return MISCHIEF_MANAGED;
}
@@ -863,7 +866,7 @@ uint8_t momentary_state(EventPtr event, uint16_t arg) {
// ask the user for a sequence of numbers, then save them and return to caller
-uint8_t config_state_base(EventPtr event, uint16_t arg,
+uint8_t config_state_base(Event event, uint16_t arg,
uint8_t num_config_steps,
void (*savefunc)()) {
static uint8_t config_step;
@@ -922,7 +925,7 @@ void ramp_config_save() {
}
}
-uint8_t ramp_config_state(EventPtr event, uint16_t arg) {
+uint8_t ramp_config_state(Event event, uint16_t arg) {
uint8_t num_config_steps;
num_config_steps = 2 + ramp_style;
return config_state_base(event, arg,
@@ -950,7 +953,7 @@ void thermal_config_save() {
if (therm_ceil > MAX_THERM_CEIL) therm_ceil = MAX_THERM_CEIL;
}
-uint8_t thermal_config_state(EventPtr event, uint16_t arg) {
+uint8_t thermal_config_state(Event event, uint16_t arg) {
return config_state_base(event, arg,
2, thermal_config_save);
}
@@ -965,13 +968,13 @@ void beacon_config_save() {
}
}
-uint8_t beacon_config_state(EventPtr event, uint16_t arg) {
+uint8_t beacon_config_state(Event event, uint16_t arg) {
return config_state_base(event, arg,
1, beacon_config_save);
}
-uint8_t number_entry_state(EventPtr event, uint16_t arg) {
+uint8_t number_entry_state(Event event, uint16_t arg) {
static uint8_t value;
static uint8_t blinks_left;
static uint8_t entry_step;
--
cgit v1.2.3
From ec34acd89d80c5a26c68e873a006f602a2d9e598 Mon Sep 17 00:00:00 2001
From: Selene ToyKeeper
Date: Sun, 11 Nov 2018 18:02:40 -0700
Subject: Made event definitions a little cleaner.
---
spaghetti-monster/fsm-events.h | 64 +++++++++++++++++++++---------------------
1 file changed, 32 insertions(+), 32 deletions(-)
diff --git a/spaghetti-monster/fsm-events.h b/spaghetti-monster/fsm-events.h
index 2fd47b6..0ebcfd0 100644
--- a/spaghetti-monster/fsm-events.h
+++ b/spaghetti-monster/fsm-events.h
@@ -89,115 +89,115 @@ static volatile uint16_t ticks_since_last_event = 0;
// Button press events
-// shouldn't normally happen, but UI might reset event while button is down
-// so a release with no recorded prior hold could be possible
+// shouldn't normally happen, but UI might empty_event_sequence() while button
+// is down so a release with no recorded prior hold could be possible
#define EV_release (B_CLICK|B_RELEASE|0)
#define EV_click1_press (B_CLICK|B_PRESS|1)
-#define EV_click1_hold (B_CLICK|B_HOLD|B_PRESS|1)
-#define EV_click1_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|1)
#define EV_click1_release (B_CLICK|B_RELEASE|1)
#define EV_click1_complete (B_CLICK|B_TIMEOUT|1)
#define EV_1click EV_click1_complete
+#define EV_click1_hold (B_CLICK|B_HOLD|B_PRESS|1)
+#define EV_click1_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|1)
#define EV_hold EV_click1_hold
#define EV_click2_press (B_CLICK|B_PRESS|2)
-#define EV_click2_hold (B_CLICK|B_HOLD|B_PRESS|2)
-#define EV_click2_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|2)
#define EV_click2_release (B_CLICK|B_RELEASE|2)
#define EV_click2_complete (B_CLICK|B_TIMEOUT|2)
#define EV_2clicks EV_click2_complete
+#define EV_click2_hold (B_CLICK|B_HOLD|B_PRESS|2)
+#define EV_click2_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|2)
#define EV_click3_press (B_CLICK|B_PRESS|3)
-#define EV_click3_hold (B_CLICK|B_HOLD|B_PRESS|3)
-#define EV_click3_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|3)
#define EV_click3_release (B_CLICK|B_RELEASE|3)
#define EV_click3_complete (B_CLICK|B_TIMEOUT|3)
#define EV_3clicks EV_click3_complete
+#define EV_click3_hold (B_CLICK|B_HOLD|B_PRESS|3)
+#define EV_click3_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|3)
#define EV_click4_press (B_CLICK|B_PRESS|4)
-#define EV_click4_hold (B_CLICK|B_HOLD|B_PRESS|4)
-#define EV_click4_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|4)
#define EV_click4_release (B_CLICK|B_RELEASE|4)
#define EV_click4_complete (B_CLICK|B_TIMEOUT|4)
#define EV_4clicks EV_click4_complete
+#define EV_click4_hold (B_CLICK|B_HOLD|B_PRESS|4)
+#define EV_click4_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|4)
#define EV_click5_press (B_CLICK|B_PRESS|5)
-#define EV_click5_hold (B_CLICK|B_HOLD|B_PRESS|5)
-#define EV_click5_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|5)
#define EV_click5_release (B_CLICK|B_RELEASE|5)
#define EV_click5_complete (B_CLICK|B_TIMEOUT|5)
#define EV_5clicks EV_click5_complete
+#define EV_click5_hold (B_CLICK|B_HOLD|B_PRESS|5)
+#define EV_click5_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|5)
#define EV_click6_press (B_CLICK|B_PRESS|6)
-#define EV_click6_hold (B_CLICK|B_HOLD|B_PRESS|6)
-#define EV_click6_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|6)
#define EV_click6_release (B_CLICK|B_RELEASE|6)
#define EV_click6_complete (B_CLICK|B_TIMEOUT|6)
#define EV_6clicks EV_click6_complete
+#define EV_click6_hold (B_CLICK|B_HOLD|B_PRESS|6)
+#define EV_click6_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|6)
#define EV_click7_press (B_CLICK|B_PRESS|7)
-#define EV_click7_hold (B_CLICK|B_HOLD|B_PRESS|7)
-#define EV_click7_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|7)
#define EV_click7_release (B_CLICK|B_RELEASE|7)
#define EV_click7_complete (B_CLICK|B_TIMEOUT|7)
#define EV_7clicks EV_click7_complete
+#define EV_click7_hold (B_CLICK|B_HOLD|B_PRESS|7)
+#define EV_click7_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|7)
#define EV_click8_press (B_CLICK|B_PRESS|8)
-#define EV_click8_hold (B_CLICK|B_HOLD|B_PRESS|8)
-#define EV_click8_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|8)
#define EV_click8_release (B_CLICK|B_RELEASE|8)
#define EV_click8_complete (B_CLICK|B_TIMEOUT|8)
#define EV_8clicks EV_click8_complete
+#define EV_click8_hold (B_CLICK|B_HOLD|B_PRESS|8)
+#define EV_click8_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|8)
#define EV_click9_press (B_CLICK|B_PRESS|9)
-#define EV_click9_hold (B_CLICK|B_HOLD|B_PRESS|9)
-#define EV_click9_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|9)
#define EV_click9_release (B_CLICK|B_RELEASE|9)
#define EV_click9_complete (B_CLICK|B_TIMEOUT|9)
#define EV_9clicks EV_click9_complete
+#define EV_click9_hold (B_CLICK|B_HOLD|B_PRESS|9)
+#define EV_click9_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|9)
#define EV_click10_press (B_CLICK|B_PRESS|10)
-#define EV_click10_hold (B_CLICK|B_HOLD|B_PRESS|10)
-#define EV_click10_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|10)
#define EV_click10_release (B_CLICK|B_RELEASE|10)
#define EV_click10_complete (B_CLICK|B_TIMEOUT|10)
#define EV_10clicks EV_click10_complete
+#define EV_click10_hold (B_CLICK|B_HOLD|B_PRESS|10)
+#define EV_click10_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|10)
#define EV_click11_press (B_CLICK|B_PRESS|11)
-#define EV_click11_hold (B_CLICK|B_HOLD|B_PRESS|11)
-#define EV_click11_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|11)
#define EV_click11_release (B_CLICK|B_RELEASE|11)
#define EV_click11_complete (B_CLICK|B_TIMEOUT|11)
#define EV_11clicks EV_click11_complete
+#define EV_click11_hold (B_CLICK|B_HOLD|B_PRESS|11)
+#define EV_click11_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|11)
#define EV_click12_press (B_CLICK|B_PRESS|12)
-#define EV_click12_hold (B_CLICK|B_HOLD|B_PRESS|12)
-#define EV_click12_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|12)
#define EV_click12_release (B_CLICK|B_RELEASE|12)
#define EV_click12_complete (B_CLICK|B_TIMEOUT|12)
#define EV_12clicks EV_click12_complete
+#define EV_click12_hold (B_CLICK|B_HOLD|B_PRESS|12)
+#define EV_click12_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|12)
#define EV_click13_press (B_CLICK|B_PRESS|13)
-#define EV_click13_hold (B_CLICK|B_HOLD|B_PRESS|13)
-#define EV_click13_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|13)
#define EV_click13_release (B_CLICK|B_RELEASE|13)
#define EV_click13_complete (B_CLICK|B_TIMEOUT|13)
#define EV_13clicks EV_click13_complete
+#define EV_click13_hold (B_CLICK|B_HOLD|B_PRESS|13)
+#define EV_click13_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|13)
#define EV_click14_press (B_CLICK|B_PRESS|14)
-#define EV_click14_hold (B_CLICK|B_HOLD|B_PRESS|14)
-#define EV_click14_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|14)
#define EV_click14_release (B_CLICK|B_RELEASE|14)
#define EV_click14_complete (B_CLICK|B_TIMEOUT|14)
#define EV_14clicks EV_click14_complete
+#define EV_click14_hold (B_CLICK|B_HOLD|B_PRESS|14)
+#define EV_click14_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|14)
#define EV_click15_press (B_CLICK|B_PRESS|15)
-#define EV_click15_hold (B_CLICK|B_HOLD|B_PRESS|15)
-#define EV_click15_hold_release (B_CLICK|B_TIMEOUT|B_HOLD|B_RELEASE|15)
#define EV_click15_release (B_CLICK|B_RELEASE|15)
#define EV_click15_complete (B_CLICK|B_TIMEOUT|15)
#define EV_15clicks EV_click15_complete
+#define EV_click15_hold (B_CLICK|B_HOLD|B_PRESS|15)
+#define EV_click15_hold_release (B_CLICK|B_HOLD|B_RELEASE|B_TIMEOUT|15)
void empty_event_sequence();
--
cgit v1.2.3