diff options
| author | Selene ToyKeeper | 2023-10-13 14:29:57 -0600 |
|---|---|---|
| committer | Selene ToyKeeper | 2023-10-13 14:29:57 -0600 |
| commit | 1fdec464891262b06d19f53d1f152a560effa576 (patch) | |
| tree | 35475c9519a09191076581680cbf4b336c322b63 /spaghetti-monster | |
| parent | misc comments, spacing, documentation (diff) | |
| download | anduril-1fdec464891262b06d19f53d1f152a560effa576.tar.gz anduril-1fdec464891262b06d19f53d1f152a560effa576.tar.bz2 anduril-1fdec464891262b06d19f53d1f152a560effa576.zip | |
rewrote emisar-d4k-3ch to use delta-sigma modulation (PWM + DSM),
which gives much better resolution, especially for the 8-bit channel.
Also...
- set_channel_mode() aborts when going from/to the same channel,
to avoid unnecessary flicker
- hsv2rgb() uses 16-bit R/G/B and V now
- changed default channel to All
- reduced default channel modes to just A, B, C, and All
- smooth ramp floor defaults to 1/150
- raised level when aux LEDs turn on high during use
(for better compatibility with red main LEDs)
Diffstat (limited to 'spaghetti-monster')
| -rw-r--r-- | spaghetti-monster/anduril/cfg-emisar-d4k-3ch.h | 39 | ||||
| -rw-r--r-- | spaghetti-monster/fsm-channels.c | 11 | ||||
| -rw-r--r-- | spaghetti-monster/fsm-channels.h | 8 |
3 files changed, 30 insertions, 28 deletions
diff --git a/spaghetti-monster/anduril/cfg-emisar-d4k-3ch.h b/spaghetti-monster/anduril/cfg-emisar-d4k-3ch.h index 092ed2d..1e852a7 100644 --- a/spaghetti-monster/anduril/cfg-emisar-d4k-3ch.h +++ b/spaghetti-monster/anduril/cfg-emisar-d4k-3ch.h @@ -13,13 +13,13 @@ // turn on the aux LEDs while main LEDs are on // (in case there's a RGB button) -#define USE_AUX_RGB_LEDS_WHILE_ON 25 +#define USE_AUX_RGB_LEDS_WHILE_ON 40 #define USE_INDICATOR_LED_WHILE_RAMPING // channel modes... // CM_MAIN2, CM_LED3, CM_LED4, CM_ALL, // CM_BLEND34A, CM_BLEND34B, CM_HSV, CM_AUTO3 -#define DEFAULT_CHANNEL_MODE CM_MAIN2 +#define DEFAULT_CHANNEL_MODE CM_ALL #define FACTORY_RESET_WARN_CHANNEL CM_LED4 #define FACTORY_RESET_SUCCESS_CHANNEL CM_MAIN2 @@ -28,7 +28,7 @@ #define CONFIG_BLINK_CHANNEL CM_ALL // blink numbers on the main LEDs by default (but allow user to change it) -#define DEFAULT_BLINK_CHANNEL CM_MAIN2 +#define DEFAULT_BLINK_CHANNEL CM_MAIN2 // LEDs 3 and 4 make a nice police strobe #define POLICE_COLOR_STROBE_CH1 CM_LED3 @@ -46,29 +46,27 @@ // LED 3 / 4 // output: unknown, 1000 lm each? #define RAMP_SIZE 150 -// level_calc.py 5.01 1 150 7135 1 0.2 2000 --pwm dyn:69:16383:511 -// 8-bit PWM -#define PWM1_LEVELS 0,1,1,2,2,2,2,3,3,3,3,4,4,5,5,6,6,6,7,8,8,9,9,10,10,11,12,13,13,14,15,16,16,17,18,19,20,21,22,23,23,24,26,27,28,29,30,31,32,33,34,36,37,38,39,41,42,43,45,46,47,49,50,52,53,55,56,58,59,61,62,64,66,67,69,71,72,74,76,78,80,81,83,85,87,89,91,93,95,97,99,101,103,105,107,109,111,113,116,118,120,122,125,127,129,132,134,136,139,141,144,146,148,151,154,156,159,161,164,166,169,172,174,177,180,183,185,188,191,194,197,200,203,205,208,211,214,217,220,223,226,230,233,236,239,242,245,249,252,255 -// dynamic PWM -#define PWM2_LEVELS 0,1,1,2,2,2,3,4,4,5,6,6,7,8,9,10,11,13,14,15,17,18,20,21,23,25,27,29,31,33,35,38,40,42,45,47,50,52,55,57,60,62,65,67,70,72,74,76,78,79,81,82,83,84,84,85,84,84,82,81,78,76,72,68,63,58,51,44,35,26,27,29,30,32,33,35,37,38,40,42,44,46,48,50,53,55,57,60,63,65,68,71,74,77,80,83,87,90,94,98,102,106,110,114,118,123,128,132,137,142,148,153,159,164,170,176,183,189,196,202,209,216,224,231,239,247,255,263,272,281,290,299,309,318,328,339,349,360,371,382,394,406,418,430,443,456,469,483,497,511 -#define PWM_TOPS 16383,13662,10727,15413,11905,8157,12776,14730,12250,13437,13990,11928,12275,12360,12270,12060,11765,12450,11970,11470,11698,11138,11181,10600,10534,10404,10226,10014,9776,9519,9248,9220,8919,8617,8512,8203,8066,7760,7605,7308,7144,6860,6693,6426,6260,6009,5769,5539,5320,5046,4851,4607,4378,4163,3914,3727,3468,3268,3008,2803,2548,2345,2099,1874,1642,1430,1189,970,728,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511,511 -#define MIN_THERM_STEPDOWN 70 // should be above highest dyn_pwm level +// delta-sigma modulated PWM (0b0HHHHHHHHLLLLLLL = 0, 8xHigh, 7xLow bits) +// level_calc.py 5.01 1 150 7135 0 0.2 2000 --pwm 32640 +// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) +#define PWM1_LEVELS 0,1,2,3,4,5,6,7,9,10,12,14,17,19,22,25,28,32,36,41,45,50,56,62,69,76,84,92,101,110,121,132,143,156,169,184,199,215,232,251,270,291,313,336,360,386,414,442,473,505,539,574,612,651,693,736,782,829,880,932,987,1045,1105,1168,1233,1302,1374,1449,1527,1608,1693,1781,1873,1969,2068,2172,2279,2391,2507,2628,2753,2883,3018,3158,3303,3454,3609,3771,3938,4111,4289,4475,4666,4864,5068,5280,5498,5724,5957,6197,6445,6701,6965,7237,7518,7808,8106,8413,8730,9056,9392,9737,10093,10459,10835,11223,11621,12031,12452,12884,13329,13786,14255,14737,15232,15741,16262,16798,17347,17911,18489,19082,19691,20314,20954,21609,22281,22969,23674,24397,25137,25895,26671,27465,28279,29111,29963,30835,31727,32640 + +#define MIN_THERM_STEPDOWN 50 #define DEFAULT_LEVEL 70 #define MAX_1x7135 70 -#define HALFSPEED_LEVEL 10 -#define QUARTERSPEED_LEVEL 4 - -//#define DEFAULT_MANUAL_MEMORY DEFAULT_LEVEL -//#define DEFAULT_MANUAL_MEMORY_TIMER 10 +// always run at 1/4th speed, because 4 kHz PWM is enough for this circuit +// and speed changes make a big visible bump +#define HALFSPEED_LEVEL 255 +#define QUARTERSPEED_LEVEL 255 -#define RAMP_SMOOTH_FLOOR 10 +#define RAMP_SMOOTH_FLOOR 1 #define RAMP_SMOOTH_CEIL 130 -// 10, 30, 50, [70], 90, 110, [130] +// 10, 30, 50, [70], 90, 110, 130 #define RAMP_DISCRETE_FLOOR 10 #define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL #define RAMP_DISCRETE_STEPS 7 -// safe limit highest regulated power (no FET or turbo) +// 10 40 [70] 100 130 #define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR #define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL #define SIMPLE_UI_STEPS 5 @@ -84,8 +82,9 @@ #define STROBE_BRIGHTNESS MAX_LEVEL // slow down party strobe; this driver can't pulse for 1ms or less #define PARTY_STROBE_ONTIME 2 -// bike strobe needs a longer pulse too -#define BIKE_STROBE_ONTIME 8 +// #define STROBE_OFF_LEVEL 1 // nope, this makes strobe blurry +// bike strobe needs a longer pulse too? +//#define BIKE_STROBE_ONTIME 8 // the default of 26 looks a bit flat, so increase it #define CANDLE_AMPLITUDE 33 diff --git a/spaghetti-monster/fsm-channels.c b/spaghetti-monster/fsm-channels.c index 62b608c..cc78536 100644 --- a/spaghetti-monster/fsm-channels.c +++ b/spaghetti-monster/fsm-channels.c @@ -9,7 +9,10 @@ #if NUM_CHANNEL_MODES > 1 void set_channel_mode(uint8_t mode) { + if (mode == channel_mode) return; // abort if nothing to do + uint8_t cur_level = actual_level; + // turn off old LEDs before changing channel set_level(0); @@ -85,7 +88,7 @@ void calc_2ch_blend( #ifdef USE_HSV2RGB -RGB_t hsv2rgb(uint8_t h, uint8_t s, uint8_t v) { +RGB_t hsv2rgb(uint8_t h, uint8_t s, uint16_t v) { RGB_t color; if (s == 0) { // grey @@ -105,11 +108,11 @@ RGB_t hsv2rgb(uint8_t h, uint8_t s, uint8_t v) { // calculate graph segments, doing integer multiplication // TODO: calculate 16-bit results, not 8-bit high = v; - low = (v * (255 - s)) >> 8; + low = ((uint32_t)v * (255 - s)) >> 8; // TODO: use a cosine crossfade instead of linear // (because it looks better and feels more natural) - falling = (v * (255 - ((s * fpart) >> 8))) >> 8; - rising = (v * (255 - ((s * (255 - fpart)) >> 8))) >> 8; + falling = ((uint32_t)v * (255 - ((s * fpart) >> 8))) >> 8; + rising = ((uint32_t)v * (255 - ((s * (255 - fpart)) >> 8))) >> 8; // default floor color.r = low; diff --git a/spaghetti-monster/fsm-channels.h b/spaghetti-monster/fsm-channels.h index 113a85c..218f4f5 100644 --- a/spaghetti-monster/fsm-channels.h +++ b/spaghetti-monster/fsm-channels.h @@ -96,11 +96,11 @@ void calc_2ch_blend( #ifdef USE_HSV2RGB typedef struct RGB_t { - uint8_t r; - uint8_t g; - uint8_t b; + uint16_t r; + uint16_t g; + uint16_t b; } RGB_t; -RGB_t hsv2rgb(uint8_t h, uint8_t s, uint8_t v); +RGB_t hsv2rgb(uint8_t h, uint8_t s, uint16_t v); #endif // ifdef USE_HSV2RGB |
