aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSelene ToyKeeper2019-05-18 03:30:34 -0600
committerSelene ToyKeeper2019-05-18 03:30:34 -0600
commit2f46400dd5c13bf715331695a699a21da57aeb7f (patch)
tree6a00fdeaff532b558a7358b21c811ade29fe5a22
parentFixed an off-by-one error in lightning mode. (diff)
parentthe lantern middle-tint power correction factor wasn't quite right... (diff)
downloadanduril-2f46400dd5c13bf715331695a699a21da57aeb7f.tar.gz
anduril-2f46400dd5c13bf715331695a699a21da57aeb7f.tar.bz2
anduril-2f46400dd5c13bf715331695a699a21da57aeb7f.zip
merged in BLF Lantern branch, even though it's not quite finished, because it's a public project and long overdue for a merge
-rw-r--r--spaghetti-monster/anduril/anduril.c176
-rw-r--r--spaghetti-monster/anduril/cfg-blf-lantern.h78
-rw-r--r--spaghetti-monster/fsm-misc.c7
-rw-r--r--spaghetti-monster/fsm-misc.h3
-rw-r--r--spaghetti-monster/fsm-ramping.c41
-rw-r--r--spaghetti-monster/fsm-ramping.h5
6 files changed, 266 insertions, 44 deletions
diff --git a/spaghetti-monster/anduril/anduril.c b/spaghetti-monster/anduril/anduril.c
index 362dbeb..5878d47 100644
--- a/spaghetti-monster/anduril/anduril.c
+++ b/spaghetti-monster/anduril/anduril.c
@@ -145,6 +145,9 @@ typedef enum {
ramp_discrete_ceil_e,
ramp_discrete_steps_e,
#endif
+ #ifdef USE_TINT_RAMPING
+ tint_e,
+ #endif
#ifdef USE_STROBE_STATE
strobe_type_e,
#endif
@@ -182,6 +185,12 @@ typedef enum {
#define USE_PSEUDO_RAND
#endif
+#if defined(USE_CANDLE_MODE)
+#ifndef USE_TRIANGLE_WAVE
+#define USE_TRIANGLE_WAVE
+#endif
+#endif
+
#include "spaghetti-monster.h"
@@ -198,6 +207,10 @@ uint8_t steady_state(Event event, uint16_t arg);
#ifdef USE_RAMP_CONFIG
uint8_t ramp_config_state(Event event, uint16_t arg);
#endif
+#ifdef USE_TINT_RAMPING
+// not actually a mode, more of a fallback under other modes
+uint8_t tint_ramping_state(Event event, uint16_t arg);
+#endif
// party and tactical strobes
#ifdef USE_STROBE_STATE
uint8_t strobe_state(Event event, uint16_t arg);
@@ -243,6 +256,7 @@ uint8_t number_entry_state(Event event, uint16_t arg);
volatile uint8_t number_entry_value;
void blink_confirm(uint8_t num);
+void blip();
#if defined(USE_INDICATOR_LED) && defined(TICK_DURING_STANDBY)
void indicator_blink(uint8_t arg);
#endif
@@ -255,6 +269,9 @@ void save_config_wl();
#endif
// default ramp options if not overridden earlier per-driver
+#ifndef RAMP_STYLE
+#define RAMP_STYLE 0 // smooth default
+#endif
#ifndef RAMP_SMOOTH_FLOOR
#define RAMP_SMOOTH_FLOOR 1
#endif
@@ -298,7 +315,7 @@ void save_config_wl();
#endif
uint8_t memorized_level = DEFAULT_LEVEL;
// smooth vs discrete ramping
-volatile uint8_t ramp_style = 0; // 0 = smooth, 1 = discrete
+volatile uint8_t ramp_style = RAMP_STYLE; // 0 = smooth, 1 = discrete
volatile uint8_t ramp_smooth_floor = RAMP_SMOOTH_FLOOR;
volatile uint8_t ramp_smooth_ceil = RAMP_SMOOTH_CEIL;
volatile uint8_t ramp_discrete_floor = RAMP_DISCRETE_FLOOR;
@@ -376,6 +393,9 @@ volatile uint8_t bike_flasher_brightness = MAX_1x7135;
#ifdef USE_CANDLE_MODE
uint8_t candle_mode_state(Event event, uint16_t arg);
uint8_t triangle_wave(uint8_t phase);
+#ifndef CANDLE_AMPLITUDE
+#define CANDLE_AMPLITUDE 25
+#endif
#endif
#ifdef USE_BEACON_MODE
@@ -424,10 +444,7 @@ uint8_t off_state(Event event, uint16_t arg) {
#ifdef MOON_TIMING_HINT
if (arg == 0) {
// let the user know they can let go now to stay at moon
- uint8_t temp = actual_level;
- set_level(0);
- delay_4ms(3);
- set_level(temp);
+ blip();
} else
#endif
// don't start ramping immediately;
@@ -605,8 +622,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
#ifdef START_AT_MEMORIZED_LEVEL
save_config_wl();
#endif
- set_level(0);
- delay_4ms(20/4);
+ blip();
set_level(memorized_level);
return MISCHIEF_MANAGED;
}
@@ -657,8 +673,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
|| (memorized_level == mode_min)
#endif
)) {
- set_level(0);
- delay_4ms(8/4);
+ blip();
}
#endif
#if defined(BLINK_AT_STEPS)
@@ -672,8 +687,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
(memorized_level == nearest)
)
{
- set_level(0);
- delay_4ms(8/4);
+ blip();
}
#endif
set_level(memorized_level);
@@ -719,8 +733,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
|| (memorized_level == mode_min)
#endif
)) {
- set_level(0);
- delay_4ms(8/4);
+ blip();
}
#endif
#if defined(BLINK_AT_STEPS)
@@ -734,8 +747,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
(memorized_level == nearest)
)
{
- set_level(0);
- delay_4ms(8/4);
+ blip();
}
#endif
set_level(memorized_level);
@@ -806,10 +818,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
// overheating: drop by an amount proportional to how far we are above the ceiling
else if (event == EV_temperature_high) {
#if 0
- uint8_t foo = actual_level;
- set_level(0);
- delay_4ms(2);
- set_level(foo);
+ blip();
#endif
#ifdef THERM_HARD_TURBO_DROP
if (actual_level > THERM_FASTER_LEVEL) {
@@ -837,10 +846,7 @@ uint8_t steady_state(Event event, uint16_t arg) {
// (proportional to how low we are)
else if (event == EV_temperature_low) {
#if 0
- uint8_t foo = actual_level;
- set_level(0);
- delay_4ms(2);
- set_level(foo);
+ blip();
#endif
if (actual_level < target_level) {
//int16_t stepup = actual_level + (arg>>1);
@@ -860,6 +866,69 @@ uint8_t steady_state(Event event, uint16_t arg) {
}
+#ifdef USE_TINT_RAMPING
+uint8_t tint_ramping_state(Event event, uint16_t arg) {
+ static int8_t tint_ramp_direction = 1;
+ static uint8_t prev_tint = 0;
+ // don't activate auto-tint modes unless the user hits the edge
+ // and keeps pressing for a while
+ static uint8_t past_edge_counter = 0;
+ // bugfix: click-click-hold from off to strobes would invoke tint ramping
+ // in addition to changing state... so ignore any tint-ramp events which
+ // don't look like they were meant to be here
+ static uint8_t active = 0;
+
+ // click, click, hold: change the tint
+ if (event == EV_click3_hold) {
+ // reset at beginning of movement
+ if (! arg) {
+ active = 1; // first frame means this is for us
+ past_edge_counter = 0; // doesn't start until user hits the edge
+ }
+ // ignore event if we weren't the ones who handled the first frame
+ if (! active) return EVENT_HANDLED;
+
+ // change normal tints
+ if ((tint_ramp_direction > 0) && (tint < 254)) {
+ tint += 1;
+ }
+ else if ((tint_ramp_direction < 0) && (tint > 1)) {
+ tint -= 1;
+ }
+ // if the user kept pressing long enough, go the final step
+ if (past_edge_counter == 64) {
+ past_edge_counter ++;
+ tint ^= 1; // 0 -> 1, 254 -> 255
+ blip();
+ }
+ // if tint change stalled, let user know we hit the edge
+ else if (prev_tint == tint) {
+ if (past_edge_counter == 0) blip();
+ // count up but don't wrap back to zero
+ if (past_edge_counter < 255) past_edge_counter ++;
+ }
+ prev_tint = tint;
+ set_level(actual_level);
+ return EVENT_HANDLED;
+ }
+
+ // click, click, hold, release: reverse direction for next ramp
+ else if (event == EV_click3_hold_release) {
+ active = 0; // ignore next hold if it wasn't meant for us
+ // reverse
+ tint_ramp_direction = -tint_ramp_direction;
+ if (tint == 0) tint_ramp_direction = 1;
+ else if (tint == 255) tint_ramp_direction = -1;
+ // remember tint after battery change
+ save_config();
+ return EVENT_HANDLED;
+ }
+
+ return EVENT_NOT_HANDLED;
+}
+#endif // ifdef USE_TINT_RAMPING
+
+
#ifdef USE_STROBE_STATE
uint8_t strobe_state(Event event, uint16_t arg) {
// 'st' reduces ROM size by avoiding access to a volatile var
@@ -1060,17 +1129,18 @@ inline void bike_flasher_iter() {
#ifdef USE_CANDLE_MODE
uint8_t candle_mode_state(Event event, uint16_t arg) {
- // FIXME: make candle variance magnitude a compile-time option,
- // since 20 is sometimes too much or too little,
- // depending on the driver type and ramp shape
- //#define MAX_CANDLE_LEVEL (RAMP_SIZE-8-6-4)
- #define MAX_CANDLE_LEVEL (RAMP_SIZE/2)
+ #define MAX_CANDLE_LEVEL (RAMP_LENGTH-CANDLE_AMPLITUDE-15)
static uint8_t candle_wave1 = 0;
static uint8_t candle_wave2 = 0;
static uint8_t candle_wave3 = 0;
static uint8_t candle_wave2_speed = 0;
- static uint8_t candle_wave2_depth = 7;
- static uint8_t candle_wave3_depth = 4;
+ // these should add up to 100
+ #define CANDLE_WAVE1_MAXDEPTH 30
+ #define CANDLE_WAVE2_MAXDEPTH 45
+ #define CANDLE_WAVE3_MAXDEPTH 25
+ static const uint8_t candle_wave1_depth = CANDLE_WAVE1_MAXDEPTH * CANDLE_AMPLITUDE / 100;
+ static uint8_t candle_wave2_depth = CANDLE_WAVE2_MAXDEPTH * CANDLE_AMPLITUDE / 100;
+ static uint8_t candle_wave3_depth = CANDLE_WAVE3_MAXDEPTH * CANDLE_AMPLITUDE / 100;
static uint8_t candle_mode_brightness = 24;
static uint8_t candle_mode_timer = 0;
#define TICKS_PER_CANDLE_MINUTE 4096 // about 65 seconds
@@ -1115,7 +1185,7 @@ uint8_t candle_mode_state(Event event, uint16_t arg) {
// self-timer dims the light during the final minute
uint8_t subtract = 0;
if (candle_mode_timer == 1) {
- subtract = ((candle_mode_brightness+20)
+ subtract = ((candle_mode_brightness+CANDLE_AMPLITUDE)
* ((arg & (TICKS_PER_CANDLE_MINUTE-1)) >> 4))
>> 8;
}
@@ -1132,7 +1202,7 @@ uint8_t candle_mode_state(Event event, uint16_t arg) {
}
// 3-oscillator synth for a relatively organic pattern
uint8_t add;
- add = ((triangle_wave(candle_wave1) * 8) >> 8)
+ add = ((triangle_wave(candle_wave1) * candle_wave1_depth) >> 8)
+ ((triangle_wave(candle_wave2) * candle_wave2_depth) >> 8)
+ ((triangle_wave(candle_wave3) * candle_wave3_depth) >> 8);
int8_t brightness = candle_mode_brightness + add - subtract;
@@ -1140,6 +1210,7 @@ uint8_t candle_mode_state(Event event, uint16_t arg) {
set_level(brightness);
// wave1: slow random LFO
+ // TODO: make wave slower and more erratic?
if ((arg & 1) == 0) candle_wave1 += pseudo_rand() & 1;
// wave2: medium-speed erratic LFO
candle_wave2 += candle_wave2_speed;
@@ -1152,8 +1223,10 @@ uint8_t candle_mode_state(Event event, uint16_t arg) {
if ((candle_wave2_depth > 0) && ((pseudo_rand() & 0b00111111) == 0))
candle_wave2_depth --;
// random sawtooth retrigger
- if ((pseudo_rand()) == 0) {
- candle_wave2_depth = 7;
+ if (pseudo_rand() == 0) {
+ // random amplitude
+ //candle_wave2_depth = 2 + (pseudo_rand() % ((CANDLE_WAVE2_MAXDEPTH * CANDLE_AMPLITUDE / 100) - 2));
+ candle_wave2_depth = pseudo_rand() % (CANDLE_WAVE2_MAXDEPTH * CANDLE_AMPLITUDE / 100);
//candle_wave3_depth = 5;
candle_wave2 = 0;
}
@@ -1161,17 +1234,13 @@ uint8_t candle_mode_state(Event event, uint16_t arg) {
if ((candle_wave3_depth > 2) && ((pseudo_rand() & 0b00011111) == 0))
candle_wave3_depth --;
if ((pseudo_rand() & 0b01111111) == 0)
- candle_wave3_depth = 5;
+ // random amplitude
+ //candle_wave3_depth = 2 + (pseudo_rand() % ((CANDLE_WAVE3_MAXDEPTH * CANDLE_AMPLITUDE / 100) - 2));
+ candle_wave3_depth = pseudo_rand() % (CANDLE_WAVE3_MAXDEPTH * CANDLE_AMPLITUDE / 100);
return MISCHIEF_MANAGED;
}
return EVENT_NOT_HANDLED;
}
-
-uint8_t triangle_wave(uint8_t phase) {
- uint8_t result = phase << 1;
- if (phase > 127) result = 255 - result;
- return result;
-}
#endif // #ifdef USE_CANDLE_MODE
@@ -1767,9 +1836,9 @@ uint8_t beacon_config_state(Event event, uint16_t arg) {
inline void beacon_mode_iter() {
// one iteration of main loop()
set_level(memorized_level);
- nice_delay_ms(500);
+ nice_delay_ms(100);
set_level(0);
- nice_delay_ms(((beacon_seconds) * 1000) - 500);
+ nice_delay_ms(((beacon_seconds) * 1000) - 100);
}
#endif // #ifdef USE_BEACON_MODE
@@ -1901,6 +1970,14 @@ void blink_confirm(uint8_t num) {
}
}
+// Just go dark for a moment to indicate to user that something happened
+void blip() {
+ uint8_t temp = actual_level;
+ set_level(0);
+ delay_4ms(3);
+ set_level(temp);
+}
+
#if defined(USE_INDICATOR_LED) && defined(TICK_DURING_STANDBY)
// beacon-like mode for the indicator LED
@@ -1936,6 +2013,9 @@ void load_config() {
ramp_discrete_ceil = eeprom[ramp_discrete_ceil_e];
ramp_discrete_steps = eeprom[ramp_discrete_steps_e];
#endif
+ #ifdef USE_TINT_RAMPING
+ tint = eeprom[tint_e];
+ #endif
#if defined(USE_PARTY_STROBE_MODE) || defined(USE_TACTICAL_STROBE_MODE)
strobe_type = eeprom[strobe_type_e]; // TODO: move this to eeprom_wl?
strobe_delays[0] = eeprom[strobe_delays_0_e];
@@ -1974,6 +2054,9 @@ void save_config() {
eeprom[ramp_discrete_ceil_e] = ramp_discrete_ceil;
eeprom[ramp_discrete_steps_e] = ramp_discrete_steps;
#endif
+ #ifdef USE_TINT_RAMPING
+ eeprom[tint_e] = tint;
+ #endif
#if defined(USE_PARTY_STROBE_MODE) || defined(USE_TACTICAL_STROBE_MODE)
eeprom[strobe_type_e] = strobe_type; // TODO: move this to eeprom_wl?
eeprom[strobe_delays_0_e] = strobe_delays[0];
@@ -2073,14 +2156,19 @@ void setup() {
load_config();
+ #ifdef USE_TINT_RAMPING
+ // add tint ramping underneath every other state
+ push_state(tint_ramping_state, 0);
+ #endif // ifdef USE_TINT_RAMPING
+
#ifdef USE_MUGGLE_MODE
if (muggle_mode_active)
push_state(muggle_state, (MUGGLE_FLOOR+MUGGLE_CEILING)/2);
else
#endif
push_state(off_state, 0);
- #endif
+ #endif // ifdef START_AT_MEMORIZED_LEVEL
}
diff --git a/spaghetti-monster/anduril/cfg-blf-lantern.h b/spaghetti-monster/anduril/cfg-blf-lantern.h
new file mode 100644
index 0000000..9467397
--- /dev/null
+++ b/spaghetti-monster/anduril/cfg-blf-lantern.h
@@ -0,0 +1,78 @@
+// BLF Lantern config options for Anduril
+/* BLF Lantern pinout
+ * ----
+ * Reset -|1 8|- VCC
+ * eswitch -|2 7|- powerbank enable?
+ * aux LED -|3 6|- PWM (5000K)
+ * GND -|4 5|- PWM (3000K)
+ * ----
+ */
+
+// basically the same as a Q8... sort of
+#include "hwdef-BLF_Q8.h"
+
+// the button lights up
+#define USE_INDICATOR_LED
+// the button is visible while main LEDs are on
+#define USE_INDICATOR_LED_WHILE_RAMPING
+// enable blinking indicator LED while off
+#define TICK_DURING_STANDBY
+#define STANDBY_TICK_SPEED 3 // every 0.128 s
+#define USE_FANCIER_BLINKING_INDICATOR
+// off mode: high (2)
+// lockout: blinking (3)
+#define INDICATOR_LED_DEFAULT_MODE ((3<<2) + 2)
+
+// the lantern has two PWM channels, but they drive different sets of emitters
+// (one channel for warm emitters, one channel for cold)
+// so enable a special ramping mode which changes tint instead of brightness
+#define USE_TINT_RAMPING
+
+#ifdef RAMP_LENGTH
+#undef RAMP_LENGTH
+#endif
+
+// level_calc.py 1 150 7135 1 30 800
+#define RAMP_LENGTH 150
+#define PWM1_LEVELS 1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,11,11,12,13,13,14,15,15,16,17,18,18,19,20,21,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,43,44,45,46,48,49,50,51,53,54,56,57,58,60,61,63,64,66,67,69,70,72,74,75,77,79,80,82,84,85,87,89,91,93,95,97,98,100,102,104,106,108,111,113,115,117,119,121,124,126,128,130,133,135,137,140,142,145,147,150,152,155,157,160,163,165,168,171,173,176,179,182,185,188,190,193,196,199,202,205,209,212,215,218,221,224,228,231,234,238,241,245,248,251,255
+#define MAX_1x7135 65
+#define HALFSPEED_LEVEL 14
+#define QUARTERSPEED_LEVEL 5
+
+// the default of 26 looks a bit flat, so increase it
+#define CANDLE_AMPLITUDE 40
+
+// set floor and ceiling as far apart as possible
+// because this lantern isn't overpowered
+#define RAMP_STYLE 1 // 0 = smooth, 1 = stepped
+#define RAMP_SMOOTH_FLOOR 1
+#define RAMP_SMOOTH_CEIL 150
+#define RAMP_DISCRETE_FLOOR 10
+#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL
+#define RAMP_DISCRETE_STEPS 5
+
+// the sensor (attiny85) is nowhere near the emitters
+// so thermal regulation can't work
+#ifdef USE_THERMAL_REGULATION
+#undef USE_THERMAL_REGULATION
+#endif
+
+// also, the set_level_gradually() thing isn't compatible with tint ramping
+// (but unsetting it here doesn't actually do anything, because the thermal
+// regulation define enables it later... so this is mostly just a note to
+// make this compatibility issue explicit)
+#ifdef USE_SET_LEVEL_GRADUALLY
+#undef USE_SET_LEVEL_GRADUALLY
+#endif
+
+// don't blink while ramping
+#ifdef BLINK_AT_RAMP_MIDDLE
+#undef BLINK_AT_RAMP_MIDDLE
+#endif
+#ifdef BLINK_AT_RAMP_FLOOR
+#undef BLINK_AT_RAMP_FLOOR
+#endif
+// except the top... blink at the top
+#ifndef BLINK_AT_RAMP_CEILING
+#define BLINK_AT_RAMP_CEILING
+#endif
diff --git a/spaghetti-monster/fsm-misc.c b/spaghetti-monster/fsm-misc.c
index e61fe00..9f953fa 100644
--- a/spaghetti-monster/fsm-misc.c
+++ b/spaghetti-monster/fsm-misc.c
@@ -146,5 +146,12 @@ void indicator_led_auto() {
*/
#endif // USE_INDICATOR_LED
+#ifdef USE_TRIANGLE_WAVE
+uint8_t triangle_wave(uint8_t phase) {
+ uint8_t result = phase << 1;
+ if (phase > 127) result = 255 - result;
+ return result;
+}
+#endif
#endif
diff --git a/spaghetti-monster/fsm-misc.h b/spaghetti-monster/fsm-misc.h
index 4e0eb4f..6e41b6c 100644
--- a/spaghetti-monster/fsm-misc.h
+++ b/spaghetti-monster/fsm-misc.h
@@ -46,5 +46,8 @@ uint8_t blink(uint8_t num, uint8_t speed);
void indicator_led(uint8_t lvl);
#endif
+#ifdef USE_TRIANGLE_WAVE
+uint8_t triangle_wave(uint8_t phase);
+#endif
#endif
diff --git a/spaghetti-monster/fsm-ramping.c b/spaghetti-monster/fsm-ramping.c
index 6cdf5e6..082f8c9 100644
--- a/spaghetti-monster/fsm-ramping.c
+++ b/spaghetti-monster/fsm-ramping.c
@@ -25,9 +25,11 @@
void set_level(uint8_t level) {
actual_level = level;
+
#ifdef USE_SET_LEVEL_GRADUALLY
gradual_target = level;
#endif
+
#ifdef USE_INDICATOR_LED
#ifdef USE_INDICATOR_LED_WHILE_RAMPING
if (! go_to_standby)
@@ -40,6 +42,7 @@ void set_level(uint8_t level) {
indicator_led(0);
#endif
#endif
+
//TCCR0A = PHASE;
if (level == 0) {
#if PWM_CHANNELS >= 1
@@ -56,6 +59,42 @@ void set_level(uint8_t level) {
#endif
} else {
level --;
+
+ #ifdef USE_TINT_RAMPING
+ // calculate actual PWM levels based on a single-channel ramp
+ // and a global tint value
+ uint8_t brightness = pgm_read_byte(pwm1_levels + level);
+ uint8_t warm_PWM, cool_PWM;
+
+ // auto-tint modes
+ uint8_t mytint;
+ #if 1
+ // perceptual by ramp level
+ if (tint == 0) { mytint = 255 * (uint16_t)level / RAMP_SIZE; }
+ else if (tint == 255) { mytint = 255 - (255 * (uint16_t)level / RAMP_SIZE); }
+ #else
+ // linear with power level
+ //if (tint == 0) { mytint = brightness; }
+ //else if (tint == 255) { mytint = 255 - brightness; }
+ #endif
+ // stretch 1-254 to fit 0-255 range (hits every value except 98 and 198)
+ else { mytint = (tint * 100 / 99) - 1; }
+
+ // middle tints sag, so correct for that effect
+ uint16_t base_PWM = brightness;
+ // correction is only necessary when PWM is fast
+ if (level > HALFSPEED_LEVEL) {
+ base_PWM = brightness
+ + ((((uint16_t)brightness) * 26 / 64) * triangle_wave(mytint) / 255);
+ }
+
+ cool_PWM = (((uint16_t)mytint * (uint16_t)base_PWM) + 127) / 255;
+ warm_PWM = base_PWM - cool_PWM;
+
+ PWM1_LVL = warm_PWM;
+ PWM2_LVL = cool_PWM;
+ #else
+
#if PWM_CHANNELS >= 1
PWM1_LVL = pgm_read_byte(pwm1_levels + level);
#endif
@@ -68,6 +107,8 @@ void set_level(uint8_t level) {
#if PWM_CHANNELS >= 4
PWM4_LVL = pgm_read_byte(pwm4_levels + level);
#endif
+
+ #endif // ifdef USE_TINT_RAMPING
}
#ifdef USE_DYNAMIC_UNDERCLOCKING
auto_clock_speed();
diff --git a/spaghetti-monster/fsm-ramping.h b/spaghetti-monster/fsm-ramping.h
index 14c8dae..dcc3b74 100644
--- a/spaghetti-monster/fsm-ramping.h
+++ b/spaghetti-monster/fsm-ramping.h
@@ -26,6 +26,11 @@
// actual_level: last ramp level set by set_level()
volatile uint8_t actual_level = 0;
+#ifdef USE_TINT_RAMPING
+uint8_t tint = 128;
+#define USE_TRIANGLE_WAVE
+#endif
+
#ifdef USE_SET_LEVEL_GRADUALLY
// adjust brightness very smoothly
volatile uint8_t gradual_target;
If you find this content useful please consider a small donation via bitcoin: bitcoin:1mxKyQsHHugqRxPKgwaA7wUwJEGCNthn2?amount=0.001&message=Donation Scraping git contents via cgit is very resource intensive. The continued hosting of these git repositories is entirely financed by your bitcoin contributions. For donations of a least 1 mBTC you include your IP address in the message of your bitcoin donation. This will remove this message in the future for requests from your IP, which will significantly reduce token usage. In any case, any contributions to bitcoin address 1mxKyQsHHugqRxPKgwaA7wUwJEGCNthn2 are very welcome. Thanks in advance for you contribution to a self-sustaining ecosystem.