diff options
| author | Gabriel Hart | 2021-08-12 11:15:48 -0500 |
|---|---|---|
| committer | Gabriel Hart | 2021-08-12 11:15:48 -0500 |
| commit | 1d3a4d7996ca5b046287f28db145eb3d09c9c495 (patch) | |
| tree | 91aa3228f2781f9e43b2ee0f721778db9678ccce | |
| parent | Finalized SP10S and renamed to SP10 Pro. Updated Sofirn settings to include SOS. (diff) | |
| parent | got PFM / dynamic PWM actually working on Noctigon KR4 (diff) | |
| download | anduril-1d3a4d7996ca5b046287f28db145eb3d09c9c495.tar.gz anduril-1d3a4d7996ca5b046287f28db145eb3d09c9c495.tar.bz2 anduril-1d3a4d7996ca5b046287f28db145eb3d09c9c495.zip | |
Merge updates from TKs main branch
21 files changed, 323 insertions, 68 deletions
diff --git a/bin/build.sh b/bin/build.sh index c733320..aa983c8 100755 --- a/bin/build.sh +++ b/bin/build.sh @@ -12,9 +12,18 @@ fi export ATTINY=$1 ; shift export PROGRAM=$1 ; shift -# path to the Atmel ATtiny device family pack: (for attiny1616 support) +# give a more useful error message when AVR DFP is needed but not installed +# (Atmel ATtiny device family pack, for attiny1616 support) # http://packs.download.atmel.com/ -if [ -z "$ATTINY_DFP" ]; then export ATTINY_DFP=~/avr/attiny_dfp ; fi +#if [ -z "$ATTINY_DFP" ]; then export ATTINY_DFP=~/avr/attiny_dfp ; fi +SERIES1=' 416 417 816 817 1616 1617 3216 3217 ' +if [[ $SERIES1 =~ " $ATTINY " ]]; then + if [ -z "$ATTINY_DFP" ]; then + echo "ATtiny$ATTINY support requires Atmel attiny device family pack." + echo "More info is in /README under tiny1616 support." + exit 1 + fi +fi export MCU=attiny$ATTINY export CC=avr-gcc diff --git a/bin/level_calc.py b/bin/level_calc.py index a780405..acac332 100755 --- a/bin/level_calc.py +++ b/bin/level_calc.py @@ -9,11 +9,29 @@ interactive = False #ramp_shape = 'cube' max_pwm = 255 +max_pwms = [] +dyn_pwm = False def main(args): """Calculates PWM levels for visually-linear steps. """ + cli_answers = [] + global max_pwm, max_pwms, dyn_pwm + pwm_arg = str(max_pwm) + + i = 0 + while i < len(args): + a = args[i] + if a in ('--pwm',): + i += 1 + pwm_arg = args[i] + else: + #print('unrecognized option: "%s"' % (a,)) + cli_answers.append(a) + + i += 1 + # Get parameters from the user questions_main = [ (str, 'ramp_shape', 'cube', 'Ramp shape? [cube, square, fifth, seventh, ninth, log, N.NN]'), @@ -30,7 +48,7 @@ def main(args): def ask(questions, ans): for typ, name, default, text in questions: - value = get_value(text, default, args) + value = get_value(text, default, cli_answers) if not value: value = default else: @@ -40,14 +58,33 @@ def main(args): answers = Empty() ask(questions_main, answers) - global ramp_shape + if pwm_arg: + if pwm_arg.startswith('dyn:'): + dyn_pwm = True + parts = pwm_arg.split(':') + dpwm_steps = int(parts[1]) + dpwn_max = int(parts[2]) + dpwn_min = int(parts[3]) + max_pwms = [dpwn_min] * answers.num_levels + for i in range(dpwm_steps): + span = dpwn_max - dpwn_min + x = dpwn_min + (span * (float(dpwm_steps - i) / dpwm_steps)) + max_pwms[i] = int(x) + max_pwm = dpwn_min + + else: + val = int(pwm_arg) + max_pwm = val + max_pwms = [val] * answers.num_levels + + global ramp_shape ramp_shape = answers.ramp_shape channels = [] - if not args: + if not answers: print('Describe the channels in order of lowest to highest power.') for chan_num in range(answers.num_channels): - if not args: + if not answers: print('===== Channel %s =====' % (chan_num+1)) chan = Empty() chan.pwm_max = max_pwm @@ -119,7 +156,7 @@ def multi_pwm(answers, channels): channel.modes.append(0.0) # Normal non-turbo mode or non-FET turbo else: - channel.modes.append(channel.pwm_max) + channel.modes.append(max_pwms[i]) # This channel's active ramp-up range #elif goal_lm > (channel.prev_lm + channel.lm_min): elif goal_lm > channel.prev_lm: @@ -132,7 +169,27 @@ def multi_pwm(answers, channels): needed = goal_lm - channel.prev_lm - channel.lm_min - ratio = needed / diff * (channel.pwm_max-channel.pwm_min) + ceil = max_pwms[i] + ratio = needed / diff * (ceil-channel.pwm_min) + # if there's wiggle room, adjust ceiling to reduce error + #if dyn_pwm: + # this_step = max(1, math.floor(ratio)) + # next_step = this_step + 0.5 + # limit = float(this_step) / next_step * ceil + # limit = max(limit, max_pwm) + #while (ceil > limit) and ((ratio - math.floor(ratio)) > 0.1): + # ceil -= 1 + # ratio = needed / diff * (ceil-channel.pwm_min) + # max_pwms[i] = ceil + if dyn_pwm and (ceil > max_pwm): + this_step = max(1, math.floor(ratio)) + next_step = this_step + 1 + fpart = ratio - math.floor(ratio) + correction = (next_step - fpart) / next_step + ceil = int(ceil * correction) + ratio = needed / diff * (ceil-channel.pwm_min) + max_pwms[i] = ceil + # save the result pwm = max(0, ratio + channel.pwm_min) channel.modes.append(pwm) # This channel isn't active yet, output too low @@ -144,7 +201,7 @@ def multi_pwm(answers, channels): goal_vis, goal_lm = goals[i] pwms = [] for channel in channels: - pwms.append('%.2f/%i' % (channel.modes[i], channel.pwm_max)) + pwms.append('%.2f/%i' % (channel.modes[i], max_pwms[i])) print('%i: visually %.2f (%.2f lm): %s' % (i+1, goal_vis, goal_lm, ', '.join(pwms))) @@ -154,15 +211,19 @@ def multi_pwm(answers, channels): (cnum+1, ','.join([str(int(round(i))) for i in channel.modes]))) + # Show PFM values (PWM TOP) + if dyn_pwm: + print('PWM_TOP: %s' % (','.join(str(x) for x in max_pwms))) + # Show highest level for each channel before next channel starts for cnum, channel in enumerate(channels[:-1]): prev = 0 i = 1 while (i < answers.num_levels) \ - and (channel.modes[i] >= channel.modes[i-1]) \ and (channels[cnum+1].modes[i] == 0): + #and (channel.modes[i] >= channel.modes[i-1]) \ i += 1 - print('Ch%i max: %i (%.2f/%s)' % (cnum, i, channel.modes[i-1], max_pwm)) + print('Ch%i max: %i (%.2f/%s)' % (cnum, i, channel.modes[i-1], max_pwms[i])) def get_value(text, default, args): diff --git a/hwdef-Noctigon_KR4.h b/hwdef-Noctigon_KR4.h index feb49e6..eee4e08 100644 --- a/hwdef-Noctigon_KR4.h +++ b/hwdef-Noctigon_KR4.h @@ -41,8 +41,9 @@ #include <avr/io.h> #define PWM_CHANNELS 2 -#define PWM_BITS 10 // 0 to 1023 at 4 kHz, not 0 to 255 at 16 kHz -#define PWM_TOP 1023 +#define PWM_BITS 16 // data type needs 16 bits, not 8 +#define PWM_TOP 255 // highest value used in top half of ramp +#define USE_DYN_PWM // dynamic frequency and speed #define SWITCH_PIN PB2 // pin 17 #define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt @@ -58,10 +59,14 @@ #define PWM1_PIN PB3 // pin 16, Opamp reference #define PWM1_LVL OCR1A // OCR1A is the output compare register for PB3 +#define PWM1_CNT TCNT1 // for dynamic PWM, reset phase #define PWM2_PIN PA6 // pin 1, DD FET PWM #define PWM2_LVL OCR1B // OCR1B is the output compare register for PA6 +// PWM parameters of both channels are tied together because they share a counter +#define PWM1_TOP ICR1 // holds the TOP value for for variable-resolution PWM + #define LED_ENABLE_PIN PB0 // pin 19, Opamp power #define LED_ENABLE_PORT PORTB // control port for PB0 @@ -131,14 +136,17 @@ inline void hwdef_setup() { // CS1[2:0]: 0,0,1: clk/1 (No prescaling) (DS table 12-6) // COM1A[1:0]: 1,0: PWM OC1A in the normal direction (DS table 12-4) // COM1B[1:0]: 1,0: PWM OC1B in the normal direction (DS table 12-4) - TCCR1A = (1<<WGM11) | (1<<WGM10) // 10-bit (TOP=0x03FF) (DS table 12-5) + TCCR1A = (1<<WGM11) | (0<<WGM10) // adjustable PWM (TOP=ICR1) (DS table 12-5) | (1<<COM1A1) | (0<<COM1A0) // PWM 1A in normal direction (DS table 12-4) | (1<<COM1B1) | (0<<COM1B0) // PWM 1B in normal direction (DS table 12-4) ; TCCR1B = (0<<CS12) | (0<<CS11) | (1<<CS10) // clk/1 (no prescaling) (DS table 12-6) - | (0<<WGM13) | (0<<WGM12) // phase-correct PWM (DS table 12-5) + | (1<<WGM13) | (0<<WGM12) // phase-correct adjustable PWM (DS table 12-5) ; + // set PWM resolution + PWM1_TOP = PWM_TOP; + // set up e-switch //PORTB = (1 << SWITCH_PIN); // TODO: configure PORTA / PORTB / PORTC? PUEB = (1 << SWITCH_PIN); // pull-up for e-switch diff --git a/spaghetti-monster/anduril/MODELS b/spaghetti-monster/anduril/MODELS index aa35833..1a3c9d3 100644 --- a/spaghetti-monster/anduril/MODELS +++ b/spaghetti-monster/anduril/MODELS @@ -12,14 +12,17 @@ Model numbers: 0133 emisar-d4sv2 0134 emisar-d4sv2-219 0141 emisar-d18 +0142 emisar-d18-219 0211 noctigon-kr4 0212 noctigon-kr4-nofet 0213 noctigon-kr4-219 +0214 noctigon-kr4-219b 0251 noctigon-k1 0252 noctigon-k1-sbt90 0253 noctigon-k1-12v 0261 noctigon-k9.3 0262 noctigon-k9.3-nofet +0263 noctigon-k9.3-219 0311 fw3a 0312 fw3a-219 0313 fw3a-nofet diff --git a/spaghetti-monster/anduril/anduril-manual.txt b/spaghetti-monster/anduril/anduril-manual.txt index e3b3cf5..57f1986 100644 --- a/spaghetti-monster/anduril/anduril-manual.txt +++ b/spaghetti-monster/anduril/anduril-manual.txt @@ -182,13 +182,15 @@ Memory determines which brightness level the light goes to with 1 click from off. There are three types of brightness memory to choose from: - Automatic: Always uses the last-ramped brightness. + (does not memorize levels accessed by a shortcut, + like turbo, 2C for ceiling, or 1H-from-off for floor) - Manual: Always uses the user's saved brightness. - Hybrid: Uses the automatic memory brightness if the light was only off for a short time, or resets to the manual memory level if it was off for a longer time. - The timer for this is configurable from 0 to 255 minutes. + The timer for this is configurable from 0 to ~140 minutes. Another way to think of it is: There are three styles of memory for the last-ramped brightness level... diff --git a/spaghetti-monster/anduril/build-all.sh b/spaghetti-monster/anduril/build-all.sh index 42a36fd..b9f6d15 100755 --- a/spaghetti-monster/anduril/build-all.sh +++ b/spaghetti-monster/anduril/build-all.sh @@ -1,15 +1,57 @@ #!/bin/sh +# Usage: build-all.sh [pattern] +# If pattern given, only build targets which match. + +if [ ! -z "$1" ]; then + SEARCH="$1" +fi + UI=anduril date '+#define VERSION_NUMBER "%Y%m%d"' > version.h +PASS=0 +FAIL=0 +PASSED='' +FAILED='' + for TARGET in cfg-*.h ; do + + # maybe limit builds to a specific pattern + if [ ! -z "$SEARCH" ]; then + echo "$TARGET" | grep -i "$SEARCH" > /dev/null + if [ 0 != $? ]; then continue ; fi + fi + + # friendly name for this build NAME=$(echo "$TARGET" | perl -ne '/cfg-(.*).h/ && print "$1\n";') echo "===== $NAME =====" + + # figure out MCU type ATTINY=$(grep 'ATTINY:' $TARGET | awk '{ print $3 }') if [ -z "$ATTINY" ]; then ATTINY=85 ; fi + + # try to compile echo ../../../bin/build.sh $ATTINY "$UI" "-DCONFIGFILE=${TARGET}" ../../../bin/build.sh $ATTINY "$UI" "-DCONFIGFILE=${TARGET}" - mv -f "$UI".hex "$UI".$NAME.hex + + # track result, and rename compiled files + if [ 0 = $? ] ; then + mv -f "$UI".hex "$UI".$NAME.hex + PASS=$(($PASS + 1)) + PASSED="$PASSED $NAME" + else + echo "ERROR: build failed" + FAIL=$(($FAIL + 1)) + FAILED="$FAILED $NAME" + fi + done + +# summary +echo "===== $PASS builds succeeded, $FAIL failed =====" +#echo "PASS: $PASSED" +if [ 0 != $FAIL ]; then + echo "FAIL:$FAILED" +fi diff --git a/spaghetti-monster/anduril/cfg-emisar-d18-219.h b/spaghetti-monster/anduril/cfg-emisar-d18-219.h new file mode 100644 index 0000000..1f3a3c2 --- /dev/null +++ b/spaghetti-monster/anduril/cfg-emisar-d18-219.h @@ -0,0 +1,14 @@ +// Emisar D18 (FET+13+1) reduced-FET config options for Anduril +#include "cfg-emisar-d18.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0142" + +// don't turn off first channels at turbo level +#undef PWM1_LEVELS +#undef PWM2_LEVELS +#define PWM1_LEVELS 1,1,2,2,3,4,4,5,6,7,8,9,10,11,15,16,18,20,22,24,26,28,30,33,36,39,43,47,51,56,61,66,72,78,85,92,99,107,116,125,135,145,156,168,180,194,208,222,238,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,7,8,10,11,13,14,16,18,19,21,23,26,28,30,33,35,38,41,44,47,51,54,58,62,66,70,75,79,84,90,95,101,106,112,119,126,133,140,147,155,164,172,181,190,200,210,221,232,243,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 85% FET power +#undef PWM3_LEVELS +#define PWM3_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,5,6,8,10,12,13,16,17,20,22,24,27,29,32,34,38,40,44,46,50,53,57,60,64,68,72,76,80,85,89,94,98,103,108,114,119,125,131,137,143,150,156,163,170,177,185,193,200,209,217 + diff --git a/spaghetti-monster/anduril/cfg-emisar-d4-219c.h b/spaghetti-monster/anduril/cfg-emisar-d4-219c.h index 1f07008..e525d86 100644 --- a/spaghetti-monster/anduril/cfg-emisar-d4-219c.h +++ b/spaghetti-monster/anduril/cfg-emisar-d4-219c.h @@ -5,5 +5,9 @@ #undef MODEL_NUMBER #define MODEL_NUMBER "0112" +// don't turn off first channel at turbo level +#undef PWM1_LEVELS +#define PWM1_LEVELS 1,1,2,2,3,3,4,4,5,6,7,8,9,10,12,13,14,15,17,19,20,22,24,26,29,31,34,36,39,42,45,48,51,55,59,62,66,70,75,79,84,89,93,99,104,110,115,121,127,134,140,147,154,161,168,176,184,192,200,209,217,226,236,245,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 65% FET power #undef PWM2_LEVELS -#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,4,5,6,7,8,9,11,12,13,15,16,17,19,20,21,23,24,26,28,29,31,32,34,36,38,40,41,44,45,47,49,51,53,56,57,60,62,64,67,69,72,74,76,79,81,84,87,89,92,95,97,100,103,106,109,112,115,118,121,124,128,132,135,138,141,145,148,152,156,160,164,167,171,175,179,183,187,191,195,200,204 +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,13,15,16,17,18,19,21,22,23,25,26,27,28,30,32,33,34,36,38,39,41,42,44,46,47,49,51,53,55,57,59,61,63,65,67,69,71,73,75,78,80,82,84,87,90,92,94,97,99,102,104,108,110,113,116,119,121,125,127,130,134,136,140,143,146,149,153,156,159,163,166 diff --git a/spaghetti-monster/anduril/cfg-emisar-d4s-219c.h b/spaghetti-monster/anduril/cfg-emisar-d4s-219c.h index ef783d8..6489b34 100644 --- a/spaghetti-monster/anduril/cfg-emisar-d4s-219c.h +++ b/spaghetti-monster/anduril/cfg-emisar-d4s-219c.h @@ -5,5 +5,9 @@ #undef MODEL_NUMBER #define MODEL_NUMBER "0132" +// don't turn off first channel at turbo level +#undef PWM1_LEVELS +#define PWM1_LEVELS 1,1,2,2,3,3,4,4,5,5,6,6,7,8,8,9,10,10,11,12,13,14,15,16,17,18,19,21,22,23,25,26,27,29,31,32,34,36,38,40,42,44,46,49,51,54,56,59,62,65,68,71,74,78,81,85,89,93,97,101,106,110,115,120,125,130,136,141,147,153,160,166,173,180,187,195,202,210,219,227,236,245,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 65% FET power #undef PWM2_LEVELS -#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,4,5,6,8,8,10,11,12,14,15,16,18,20,21,23,24,27,28,30,32,34,36,38,40,43,45,48,50,52,55,57,60,63,66,69,72,76,79,82,85,89,92,96,100,104,108,112,116,121,126,130,135,140,145,150,156,161,167,172,178,184,191,197,204 +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,17,18,19,21,23,24,25,27,28,30,32,34,36,38,39,41,43,45,47,50,52,54,57,60,62,65,67,70,73,76,79,82,86,89,92,95,99,103,106,110,114,119,123,127,132,136,141,145,151,156,161,166 diff --git a/spaghetti-monster/anduril/cfg-emisar-d4sv2-219.h b/spaghetti-monster/anduril/cfg-emisar-d4sv2-219.h index 65bf116..54a2e6b 100644 --- a/spaghetti-monster/anduril/cfg-emisar-d4sv2-219.h +++ b/spaghetti-monster/anduril/cfg-emisar-d4sv2-219.h @@ -4,9 +4,11 @@ #define MODEL_NUMBER "0134" // ATTINY: 1634 +// don't turn off first channel at turbo level #undef PWM1_LEVELS #undef PWM2_LEVELS -#undef PWM3_LEVELS #define PWM1_LEVELS 1,1,2,2,3,3,4,5,5,6,7,8,9,10,11,12,13,17,18,19,20,21,22,24,26,28,30,33,35,38,41,44,47,50,54,57,61,65,69,74,79,84,89,94,100,106,113,119,126,134,142,150,158,167,176,186,196,207,218,230,242,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 #define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,12,16,21,25,30,35,41,46,52,58,64,71,77,84,92,99,107,115,124,133,142,151,161,172,182,193,205,217,229,242,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 -#define PWM3_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,4,6,7,9,10,12,13,15,17,18,20,22,24,26,28,30,33,35,37,40,43,45,48,50,53,56,59,62,65,69,72,76,80,83,87,91,95,99,104,108,113,117,123,127,132,138,143,148,154,160,166,172,178,185,192 +// 65% FET power +#undef PWM3_LEVELS +#define PWM3_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,4,6,7,8,10,11,12,13,15,17,18,20,21,23,25,27,29,31,33,35,38,39,42,44,47,49,52,54,57,60,63,66,69,73,76,79,83,86,90,94,98,102,106,110,115,119,124,129,134,139,144,149,155,160,166 diff --git a/spaghetti-monster/anduril/cfg-emisar-d4v2-219.h b/spaghetti-monster/anduril/cfg-emisar-d4v2-219.h index cef89be..414971a 100644 --- a/spaghetti-monster/anduril/cfg-emisar-d4v2-219.h +++ b/spaghetti-monster/anduril/cfg-emisar-d4v2-219.h @@ -4,7 +4,9 @@ #define MODEL_NUMBER "0114" // ATTINY: 1634 +// don't turn off first channel at turbo level #undef PWM1_LEVELS -#undef PWM2_LEVELS #define PWM1_LEVELS 1,1,2,2,3,3,4,4,5,6,7,8,9,10,12,13,14,15,17,19,20,22,24,26,29,31,34,36,39,42,45,48,51,55,59,62,66,70,75,79,84,89,93,99,104,110,115,121,127,134,140,147,154,161,168,176,184,192,200,209,217,226,236,245,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 -#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,3,5,6,6,8,9,10,11,12,14,15,16,18,18,20,21,23,24,26,27,29,30,32,33,36,37,39,41,43,44,46,48,50,52,54,56,58,61,63,65,67,70,72,74,77,79,82,84,86,89,92,95,97,100,103,106,108,111,114,117,120,124,127,130,133,137,140,144,147,151,154,157,161,165,169,172,176,180,184,188,192 +// 65% FET power +#undef PWM2_LEVELS +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,13,15,16,17,18,19,21,22,23,25,26,27,28,30,32,33,34,36,38,39,41,42,44,46,47,49,51,53,55,57,59,61,63,65,67,69,71,73,75,78,80,82,84,87,90,92,94,97,99,102,104,108,110,113,116,119,121,125,127,130,134,136,140,143,146,149,153,156,159,163,166 diff --git a/spaghetti-monster/anduril/cfg-noctigon-k9.3-219.h b/spaghetti-monster/anduril/cfg-noctigon-k9.3-219.h new file mode 100644 index 0000000..a88ad2c --- /dev/null +++ b/spaghetti-monster/anduril/cfg-noctigon-k9.3-219.h @@ -0,0 +1,18 @@ +// Noctigon K9.3 (reduced FET) config options for Anduril +#include "cfg-noctigon-k9.3.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0263" +// ATTINY: 1634 + +// main LEDs +#undef PWM1_LEVELS +#undef PWM2_LEVELS +// don't turn off first channel at turbo level +#define PWM1_LEVELS 0,0,1,1,2,2,3,3,4,4,5,6,7,8,9,10,11,13,14,15,17,19,20,22,24,26,28,30,33,35,38,40,43,46,49,52,55,59,62,66,70,74,78,82,86,91,96,100,105,111,116,121,127,133,139,145,151,158,165,172,179,186,193,201,209,217,225,234,243,251,261,270,280,289,299,310,320,331,342,353,364,376,388,400,412,425,438,451,464,478,492,506,521,536,551,566,582,597,614,630,647,664,681,699,717,735,754,772,792,811,831,851,871,892,913,935,956,978,1001,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023 +// 65% FET power +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,15,34,52,71,90,110,129,149,169,190,211,233,254,275,298,320,343,366,389,413,437,461,485,510,535,560,586,612,639,665 + +// 2nd LEDs (unchanged) +//#undef PWM3_LEVELS +//#define PWM3_LEVELS 0,0,1,1,2,2,3,3,4,4,5,5,6,7,8,9,10,11,12,13,15,16,17,18,20,21,23,24,26,27,29,31,33,35,37,39,41,43,45,48,50,53,55,58,61,63,66,69,72,75,79,82,85,89,92,96,100,104,108,112,116,120,125,129,134,138,143,148,153,158,163,169,174,180,185,191,197,203,209,215,222,228,235,242,248,255,263,270,277,285,292,300,308,316,324,333,341,350,359,368,377,386,395,405,414,424,434,444,454,465,475,486,497,508,519,531,542,554,566,578,590,603,615,628,641,654,667,680,694,708,722,736,750,765,779,794,809,825,840,856,872,888,904,920,937,954,971,988,1005,1023 + diff --git a/spaghetti-monster/anduril/cfg-noctigon-kr4-219.h b/spaghetti-monster/anduril/cfg-noctigon-kr4-219.h index 083995f..28fc595 100644 --- a/spaghetti-monster/anduril/cfg-noctigon-kr4-219.h +++ b/spaghetti-monster/anduril/cfg-noctigon-kr4-219.h @@ -1,4 +1,4 @@ -// Noctigon KR4 (75% FET) config options for Anduril +// Noctigon KR4 (reduced FET) config options for Anduril #include "cfg-noctigon-kr4.h" #undef MODEL_NUMBER #define MODEL_NUMBER "0213" @@ -6,8 +6,8 @@ // don't turn off first channel at turbo level #undef PWM1_LEVELS -#define PWM1_LEVELS 0,0,1,1,2,2,3,3,4,4,5,6,7,8,9,10,11,13,14,15,17,19,20,22,24,26,28,30,33,35,38,40,43,46,49,52,55,59,62,66,70,74,78,82,86,91,96,100,105,111,116,121,127,133,139,145,151,158,165,172,179,186,193,201,209,217,225,234,243,251,261,270,280,289,299,310,320,331,342,353,364,376,388,400,412,425,438,451,464,478,492,506,521,536,551,566,582,597,614,630,647,664,681,699,717,735,754,772,792,811,831,851,871,892,913,935,956,978,1001,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023 -// 75% FET power +#define PWM1_LEVELS 0,1,1,2,2,3,4,5,6,7,8,9,11,12,14,16,17,19,22,24,26,29,31,34,37,40,43,46,49,53,56,60,63,67,71,74,78,82,86,89,93,96,99,103,105,108,110,112,114,115,116,116,115,114,112,109,106,101,95,89,81,71,60,48,34,19,20,21,22,23,24,26,27,28,30,31,32,34,36,37,39,41,43,45,47,49,51,53,56,58,61,63,66,69,72,75,78,81,84,88,91,95,99,103,107,111,115,119,124,129,133,138,143,149,154,159,165,171,177,183,189,196,203,210,217,224,231,239,247,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 60% FET power #undef PWM2_LEVELS -#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,17,39,60,82,104,126,149,172,195,219,243,268,293,318,343,369,396,422,449,476,504,531,560,588,617,646,676,706,737,768 +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,6,12,18,25,32,38,45,53,60,68,75,83,91,99,108,117,125,135,144,153 diff --git a/spaghetti-monster/anduril/cfg-noctigon-kr4-219b.h b/spaghetti-monster/anduril/cfg-noctigon-kr4-219b.h new file mode 100644 index 0000000..39ac57c --- /dev/null +++ b/spaghetti-monster/anduril/cfg-noctigon-kr4-219b.h @@ -0,0 +1,13 @@ +// Noctigon KR4 (reduced FET) config options for Anduril +#include "cfg-noctigon-kr4.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0214" +// ATTINY: 1634 + +// don't turn off first channel at turbo level +#undef PWM1_LEVELS +#define PWM1_LEVELS 0,1,1,2,2,3,4,5,6,7,8,9,11,12,14,16,17,19,22,24,26,29,31,34,37,40,43,46,49,53,56,60,63,67,71,74,78,82,86,89,93,96,99,103,105,108,110,112,114,115,116,116,115,114,112,109,106,101,95,89,81,71,60,48,34,19,20,21,22,23,24,26,27,28,30,31,32,34,36,37,39,41,43,45,47,49,51,53,56,58,61,63,66,69,72,75,78,81,84,88,91,95,99,103,107,111,115,119,124,129,133,138,143,149,154,159,165,171,177,183,189,196,203,210,217,224,231,239,247,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 50% FET power +#undef PWM2_LEVELS +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,5,10,15,21,26,32,38,44,50,56,63,69,76,83,90,97,104,112,120,128 + diff --git a/spaghetti-monster/anduril/cfg-noctigon-kr4-nofet.h b/spaghetti-monster/anduril/cfg-noctigon-kr4-nofet.h index 3043035..871a405 100644 --- a/spaghetti-monster/anduril/cfg-noctigon-kr4-nofet.h +++ b/spaghetti-monster/anduril/cfg-noctigon-kr4-nofet.h @@ -10,13 +10,16 @@ // 0/1023: 0.35 lm // 1/1023: 2.56 lm // max regulated: 1740 lm -// level_calc.py 3.0 1 150 7135 0 5 1740 #undef PWM_CHANNELS #define PWM_CHANNELS 1 #define RAMP_LENGTH 150 +// prioritize low lows, at risk of visible ripple +// level_calc.py 5.01 1 149 7135 1 0.3 1740 --pwm dyn:78:16384:255 #undef PWM1_LEVELS -#define PWM1_LEVELS 0,0,1,1,2,2,3,3,4,4,5,5,6,7,8,9,10,11,12,13,15,16,17,18,20,21,23,24,26,27,29,31,33,35,37,39,41,43,45,48,50,53,55,58,61,63,66,69,72,75,79,82,85,89,92,96,100,104,108,112,116,120,125,129,134,138,143,148,153,158,163,169,174,180,185,191,197,203,209,215,222,228,235,242,248,255,263,270,277,285,292,300,308,316,324,333,341,350,359,368,377,386,395,405,414,424,434,444,454,465,475,486,497,508,519,531,542,554,566,578,590,603,615,628,641,654,667,680,694,708,722,736,750,765,779,794,809,825,840,856,872,888,904,920,937,954,971,988,1005,1023 +#define PWM1_LEVELS 0,1,1,1,2,3,3,4,5,6,7,8,9,10,11,13,14,16,17,19,21,23,25,27,29,31,34,36,39,42,44,47,50,53,57,60,63,67,70,74,77,81,85,88,92,96,99,103,107,110,113,117,120,123,126,128,130,133,134,136,137,137,137,137,136,135,133,130,126,122,117,111,104,96,87,76,65,52,38,22,23,25,26,27,28,29,30,32,33,34,36,37,39,40,42,43,45,47,49,51,53,55,57,59,61,63,66,68,70,73,76,78,81,84,87,90,93,96,99,103,106,110,113,117,121,125,129,133,137,142,146,151,155,160,165,170,175,181,186,192,197,203,209,215,222,228,234,241,248,255 #undef PWM2_LEVELS +#undef PWM_TOPS +#define PWM_TOPS 16383,16383,12404,8140,11462,14700,11041,12947,13795,14111,14124,13946,13641,13248,12791,13418,12808,13057,12385,12428,12358,12209,12000,11746,11459,11147,11158,10793,10708,10576,10173,9998,9800,9585,9527,9278,9023,8901,8634,8486,8216,8053,7881,7615,7440,7261,7009,6832,6656,6422,6196,6031,5819,5615,5419,5190,4973,4803,4571,4386,4179,3955,3745,3549,3340,3145,2940,2729,2513,2312,2109,1903,1697,1491,1286,1070,871,662,459,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 #undef DEFAULT_LEVEL #define DEFAULT_LEVEL 50 #undef MAX_1x7135 @@ -28,14 +31,14 @@ #undef RAMP_DISCRETE_CEIL #undef RAMP_DISCRETE_STEPS -#define RAMP_SMOOTH_FLOOR 3 // level 1 is unreliable +#define RAMP_SMOOTH_FLOOR 1 // level 1 may be unreliable #define RAMP_SMOOTH_CEIL 130 // 10, 30, [50], 70, 90, 110, 130 (plus [150] on turbo) #define RAMP_DISCRETE_FLOOR 10 #define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL #define RAMP_DISCRETE_STEPS 7 -// safe limit ~67% power / ~1200 lm (can sustain 900 lm) +// safe limit ~1000 lm (can sustain 900 lm) #undef SIMPLE_UI_FLOOR #undef SIMPLE_UI_CEIL #define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR @@ -49,9 +52,13 @@ // (only needed on no-FET build) #define PARTY_STROBE_ONTIME 2 -// stop panicking at ~90% power or ~1600 lm +// jump start a bit higher than base driver +#undef JUMP_START_MOON +#define JUMP_START_MOON 25 + +// stop panicking at ~1300 lm #undef THERM_FASTER_LEVEL -#define THERM_FASTER_LEVEL 143 +#define THERM_FASTER_LEVEL 140 #undef MIN_THERM_STEPDOWN -#define MIN_THERM_STEPDOWN DEFAULT_LEVEL +#define MIN_THERM_STEPDOWN 80 // must be > end of dynamic PWM range diff --git a/spaghetti-monster/anduril/cfg-noctigon-kr4.h b/spaghetti-monster/anduril/cfg-noctigon-kr4.h index 82b8df5..f5625c7 100644 --- a/spaghetti-monster/anduril/cfg-noctigon-kr4.h +++ b/spaghetti-monster/anduril/cfg-noctigon-kr4.h @@ -24,31 +24,40 @@ // 1/1023: 2.56 lm // max regulated: 1740 lm // FET: ~3700 lm -// maxreg at 130: level_calc.py cube 2 150 7135 0 2.5 1740 FET 1 10 2565 -// maxreg at 120: level_calc.py cube 2 150 7135 0 2.5 1740 FET 1 10 3190 #define RAMP_LENGTH 150 -#define PWM1_LEVELS 0,0,1,1,2,2,3,3,4,4,5,6,7,8,9,10,11,13,14,15,17,19,20,22,24,26,28,30,33,35,38,40,43,46,49,52,55,59,62,66,70,74,78,82,86,91,96,100,105,111,116,121,127,133,139,145,151,158,165,172,179,186,193,201,209,217,225,234,243,251,261,270,280,289,299,310,320,331,342,353,364,376,388,400,412,425,438,451,464,478,492,506,521,536,551,566,582,597,614,630,647,664,681,699,717,735,754,772,792,811,831,851,871,892,913,935,956,978,1001,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,0 -#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,22,51,79,109,138,168,198,229,260,292,324,357,390,423,457,492,527,562,598,634,671,708,746,784,822,861,901,941,982,1023 -#define DEFAULT_LEVEL 46 -#define MAX_1x7135 120 -#define HALFSPEED_LEVEL 10 -#define QUARTERSPEED_LEVEL 2 - -#define RAMP_SMOOTH_FLOOR 3 // level 1 is unreliable -#define RAMP_SMOOTH_CEIL 120 -// 10, 28, [46], 65, 83, 101, [120] +#define USE_DYN_PWM +// nice low lows, but might have visible ripple on some lights: +// maxreg at 130, dynamic PWM: level_calc.py 5.01 2 149 7135 1 0.3 1740 FET 1 10 3190 --pwm dyn:64:16384:255 +// (plus one extra level at the beginning for moon) +#define PWM1_LEVELS 0,1,1,2,2,3,4,5,6,7,8,9,11,12,14,16,17,19,22,24,26,29,31,34,37,40,43,46,49,53,56,60,63,67,71,74,78,82,86,89,93,96,99,103,105,108,110,112,114,115,116,116,115,114,112,109,106,101,95,89,81,71,60,48,34,19,20,21,22,23,24,26,27,28,30,31,32,34,36,37,39,41,43,45,47,49,51,53,56,58,61,63,66,69,72,75,78,81,84,88,91,95,99,103,107,111,115,119,124,129,133,138,143,149,154,159,165,171,177,183,189,196,203,210,217,224,231,239,247,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,0 +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,9,20,30,41,52,63,75,87,99,112,125,138,151,165,179,194,208,224,239,255 +#define PWM_TOPS 16383,16383,11750,14690,9183,12439,13615,13955,13877,13560,13093,12529,13291,12513,12756,12769,11893,11747,12085,11725,11329,11316,10851,10713,10518,10282,10016,9729,9428,9298,8971,8794,8459,8257,8043,7715,7497,7275,7052,6753,6538,6260,5994,5798,5501,5271,5006,4758,4525,4268,4030,3775,3508,3263,3010,2752,2517,2256,1998,1763,1512,1249,994,749,497,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// less ripple, but lows are a bit higher than ideal: +// maxreg at 130, dynamic PWM: level_calc.py 5.01 2 149 7135 1 0.3 1740 FET 1 10 3190 --pwm dyn:64:4096:255 +// (plus one extra level at the beginning for moon) +//#define PWM1_LEVELS 0,1,1,1,1,1,1,2,2,2,2,3,3,3,4,4,5,5,6,6,7,8,8,9,10,11,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,32,33,33,34,34,34,34,34,34,33,32,31,30,28,26,24,21,19,20,21,22,23,24,26,27,28,30,31,32,34,36,37,39,41,43,45,47,49,51,53,56,58,61,63,66,69,72,75,78,81,84,88,91,95,99,103,107,111,115,119,124,129,133,138,143,149,154,159,165,171,177,183,189,196,203,210,217,224,231,239,247,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,0 +//#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,9,20,30,41,52,63,75,87,99,112,125,138,151,165,179,194,208,224,239,255 +//#define PWM_TOPS 4095,4095,3760,3403,3020,2611,2176,3582,3062,2515,1940,3221,2761,2283,2998,2584,3004,2631,2899,2555,2735,2836,2538,2606,2636,2638,2387,2382,2361,2328,2286,2238,2185,2129,2070,2010,1949,1887,1826,1766,1706,1648,1591,1536,1482,1429,1379,1329,1242,1199,1122,1084,1016,953,895,842,791,723,659,602,549,482,422,367,302,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +#define MAX_1x7135 130 +#define DEFAULT_LEVEL 50 +#define HALFSPEED_LEVEL 12 +#define QUARTERSPEED_LEVEL 4 + +#define RAMP_SMOOTH_FLOOR 3 // level 1 may be unreliable +#define RAMP_SMOOTH_CEIL 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 ~30% power / ~1400 lm (can sustain 900 lm) +// safe limit ~30% power / ~1300 lm (can sustain 900 lm) #define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR -#define SIMPLE_UI_CEIL 110 +#define SIMPLE_UI_CEIL 120 #define SIMPLE_UI_STEPS 5 -// stop panicking at ~25% power or ~1000 lm -#define THERM_FASTER_LEVEL 100 -#define MIN_THERM_STEPDOWN DEFAULT_LEVEL +// stop panicking at ~1300 lm +#define THERM_FASTER_LEVEL 120 +#define MIN_THERM_STEPDOWN 66 // must be > end of dynamic PWM range #define THERM_NEXT_WARNING_THRESHOLD 16 // accumulate less error before adjusting #define THERM_RESPONSE_MAGNITUDE 128 // bigger adjustments @@ -58,5 +67,10 @@ #define THERM_CAL_OFFSET 5 +// the power regulator is a bit slow, so push it harder for a quick response from off +#define JUMP_START_MOON 25 +#define BLINK_BRIGHTNESS DEFAULT_LEVEL +#define BLINK_ONCE_TIME 12 + // can't reset the normal way because power is connected before the button #define USE_SOFT_FACTORY_RESET diff --git a/spaghetti-monster/anduril/misc.c b/spaghetti-monster/anduril/misc.c index 523bbf0..9c7f0dd 100644 --- a/spaghetti-monster/anduril/misc.c +++ b/spaghetti-monster/anduril/misc.c @@ -25,7 +25,7 @@ /* no longer used void blink_confirm(uint8_t num) { uint8_t brightness = actual_level; - uint8_t bump = actual_level + (MAX_LEVEL/6); + uint8_t bump = actual_level + BLINK_BRIGHTNESS; if (bump > MAX_LEVEL) bump = 0; for (; num>0; num--) { set_level(bump); @@ -41,9 +41,12 @@ void blink_confirm(uint8_t num) { #ifndef BLINK_ONCE_TIME #define BLINK_ONCE_TIME 10 #endif +#ifndef BLINK_BRIGHTNESS +#define BLINK_BRIGHTNESS (MAX_LEVEL/6) +#endif void blink_once() { uint8_t brightness = actual_level; - uint8_t bump = brightness + (MAX_LEVEL/6); + uint8_t bump = brightness + BLINK_BRIGHTNESS; if (bump > MAX_LEVEL) bump = 0; set_level(bump); diff --git a/spaghetti-monster/anduril/off-mode.c b/spaghetti-monster/anduril/off-mode.c index 094cca8..b1faf47 100644 --- a/spaghetti-monster/anduril/off-mode.c +++ b/spaghetti-monster/anduril/off-mode.c @@ -27,11 +27,6 @@ #endif uint8_t off_state(Event event, uint16_t arg) { - #ifdef USE_MANUAL_MEMORY_TIMER - // keep track of how long the light was off, - // so we can do different things on waking, depending on how long asleep - static uint16_t off_time = 0; - #endif // turn emitter off when entering state if (event == EV_enter_state) { @@ -65,7 +60,14 @@ uint8_t off_state(Event event, uint16_t arg) { // blink the indicator LED, maybe else if (event == EV_sleep_tick) { #ifdef USE_MANUAL_MEMORY_TIMER - off_time = arg; + // reset to manual memory level when timer expires + if (manual_memory && + (arg >= (manual_memory_timer * SLEEP_TICKS_PER_MINUTE))) { + memorized_level = manual_memory; + #ifdef USE_TINT_RAMPING + tint = manual_memory_tint; + #endif + } #endif #ifdef USE_INDICATOR_LED if ((indicator_led_mode & 0b00000011) == 0b00000011) { @@ -94,6 +96,12 @@ uint8_t off_state(Event event, uint16_t arg) { #if (B_TIMING_ON == B_PRESS_T) // hold (initially): go to lowest level (floor), but allow abort for regular click else if (event == EV_click1_press) { + #ifdef JUMP_START_MOON + if (!arg) { + set_level(JUMP_START_MOON); + delay_4ms(3); + } + #endif set_level(nearest_level(1)); return MISCHIEF_MANAGED; } @@ -108,6 +116,13 @@ uint8_t off_state(Event event, uint16_t arg) { } else #endif #else // B_RELEASE_T or B_TIMEOUT_T + #ifdef JUMP_START_MOON + // pulse the output for a moment to wake up the power regulator + if (!arg) { + set_level(JUMP_START_MOON); + delay_4ms(3); + } + #endif set_level(nearest_level(1)); #endif // don't start ramping immediately; @@ -126,18 +141,15 @@ uint8_t off_state(Event event, uint16_t arg) { #if (B_TIMING_ON != B_TIMEOUT_T) // 1 click (before timeout): go to memorized level, but allow abort for double click else if (event == EV_click1_release) { - #ifdef USE_MANUAL_MEMORY - // for full manual memory, set manual_memory_timer to 0 - if (manual_memory - #ifdef USE_MANUAL_MEMORY_TIMER - && (off_time >= (manual_memory_timer * SLEEP_TICKS_PER_MINUTE)) - #endif - ) { + #if defined(USE_MANUAL_MEMORY) && !defined(USE_MANUAL_MEMORY_TIMER) + // this clause probably isn't used by any configs any more + // but is included just in case someone configures it this way + if (manual_memory) { + memorized_level = manual_memory; #ifdef USE_TINT_RAMPING tint = manual_memory_tint; #endif - set_level(nearest_level(manual_memory)); - } else + } #endif set_level(nearest_level(memorized_level)); return MISCHIEF_MANAGED; diff --git a/spaghetti-monster/anduril/ramp-mode.c b/spaghetti-monster/anduril/ramp-mode.c index 968b304..263a7aa 100644 --- a/spaghetti-monster/anduril/ramp-mode.c +++ b/spaghetti-monster/anduril/ramp-mode.c @@ -470,6 +470,9 @@ void manual_memory_timer_config_save(uint8_t step, uint8_t value) { // item 1: disable manual memory, go back to automatic if (step == 1) { manual_memory = 0; } // item 2: set manual memory timer duration + // FIXME: should be limited to (65535 / SLEEP_TICKS_PER_MINUTE) + // to avoid overflows or impossibly long timeouts + // (by default, the effective limit is 145, but it allows up to 255) else { manual_memory_timer = value; } } diff --git a/spaghetti-monster/fsm-ramping.c b/spaghetti-monster/fsm-ramping.c index d6a14ef..503f90f 100644 --- a/spaghetti-monster/fsm-ramping.c +++ b/spaghetti-monster/fsm-ramping.c @@ -151,6 +151,32 @@ void set_level(uint8_t level) { #endif #endif // ifdef USE_TINT_RAMPING + + #ifdef USE_DYN_PWM + // pulse frequency modulation, a.k.a. dynamic PWM + PWM1_TOP = PWM_GET(pwm_tops, level); + #ifdef PMW2_TOP + PWM2_TOP = PWM_GET(pwm_tops, level); + #endif + #ifdef PMW3_TOP + PWM3_TOP = PWM_GET(pwm_tops, level); + #endif + + // reset the phase, to avoid random long pulses + // see attiny1634 reference manual page 103 for a warning about + // the timing of changing the TOP value (section 12.8.4) + // (we don't care about being phase-correct, so the brute-force + // approach can be used to reset it here) + #ifdef PWM1_CNT + PWM1_CNT = 0; + #endif + #ifdef PWM2_CNT + PWM2_CNT = 0; + #endif + #ifdef PWM3_CNT + PWM3_CNT = 0; + #endif + #endif } #endif // ifdef OVERRIDE_SET_LEVEL #ifdef USE_DYNAMIC_UNDERCLOCKING diff --git a/spaghetti-monster/fsm-ramping.h b/spaghetti-monster/fsm-ramping.h index 8fd89c7..d1ef6bc 100644 --- a/spaghetti-monster/fsm-ramping.h +++ b/spaghetti-monster/fsm-ramping.h @@ -53,7 +53,9 @@ void gradual_tick(); #define PWM_GET(x,y) pgm_read_byte(x+y) #else #define PWM_DATATYPE uint16_t +#ifndef PWM_TOP #define PWM_TOP 1023 // 10 bits by default +#endif // pointer plus 2*y bytes //#define PWM_GET(x,y) pgm_read_word(x+(2*y)) // nope, the compiler was already doing the math correctly @@ -74,6 +76,12 @@ PROGMEM const PWM_DATATYPE pwm3_levels[] = { PWM3_LEVELS }; PROGMEM const PWM_DATATYPE pwm4_levels[] = { PWM4_LEVELS }; #endif +// pulse frequency modulation, a.k.a. dynamic PWM +// (different ceiling / frequency at each ramp level) +#ifdef USE_DYN_PWM +PROGMEM const PWM_DATATYPE pwm_tops[] = { PWM_TOPS }; +#endif + // default / example ramps #ifndef PWM1_LEVELS #if PWM_CHANNELS == 1 |
