dillonradio

Untitled

Mar 1st, 2016
103
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 13.69 KB | None | 0 0
  1. /* candle for Adafruit NeoPixel
  2.    1 pixel version
  3.    by Tim Bartlett, December 2013
  4.    Version for FastLED and removed instances of delay()
  5.    Adapted by Rob Hilken, February 2016
  6. */
  7.  
  8. // current settings for 3.5v Teensy 3.1
  9.  
  10. #include <FastLED.h>
  11. #define LED_PIN 2
  12. #define NUM_LEDS 1
  13. #define BRIGHTNESS  100 // set at 25 to run powersaving
  14.  
  15. struct CRGB leds[NUM_LEDS];
  16.  
  17. unsigned long currentMillis;
  18.  
  19. // Candle animation randomiser and status monitor
  20. byte candleAnimStatus[NUM_LEDS];              // 1: On, 2: Burn, 3: Flicker, 4: Flutter
  21. byte randomAnimNumber;                        // to store random animation number from 1-4
  22. unsigned long candleAnimOnTimes[NUM_LEDS];    // millis() at switching on LED
  23. int candleAnimLength;                        // random between 1000 and 10000 milliseconds
  24.  
  25. // Storing the RGB Values of the LED
  26. byte ledRedValue[NUM_LEDS];
  27. byte ledGreenValue[NUM_LEDS];
  28. byte ledBlueValue[NUM_LEDS];
  29.  
  30. // color variables: mix RGB (0-255) for desired yellow
  31. byte redPx = 255;
  32. byte grnHigh = 100; //110-120 for 5v, 135 for 3.3v
  33. byte bluePx = 10; //10 for 5v, 15 for 3.3v
  34.  
  35. // animation time variables, with recommendations
  36. byte burnDepth = 14; //10 for 5v, 14 for 3.3v -- how much green dips below grnHigh for normal burn -
  37. byte flutterDepth = 30; //25 for 5v, 30 for 3.3v -- maximum dip for flutter
  38. byte cycleTime = 120; //120 -- duration of one dip in milliseconds
  39.  
  40. // pay no attention to that man behind the curtain
  41. byte fDelay;
  42.  
  43. // byte flickerDepth;
  44. byte burnDelay;
  45. byte burnLow;
  46. byte flickDelay;
  47. byte flickLow;
  48. byte flutDelay;
  49. byte flutLow;
  50.  
  51. // declare functions because of bug
  52. // https://github.com/FastLED/FastLED/issues/234
  53.  
  54. bool flutter(byte f, byte n);
  55. bool flicker(byte f, byte n);
  56. bool burn(byte f, byte n);
  57. void on(byte n);
  58. bool fire(byte grnLow, byte animLed);
  59. bool doDelay(unsigned long duration);
  60. void candleAnimation(byte animateCandleNumber);
  61.  
  62. void setup() {
  63.   FastLED.addLeds<WS2811, LED_PIN, RGB>(leds, NUM_LEDS);
  64.   FastLED.setBrightness( BRIGHTNESS );
  65.  
  66.   randomSeed(analogRead(0));
  67.  
  68.   byte flickerDepth = (burnDepth + flutterDepth) / 2.4;
  69.   burnLow = grnHigh - burnDepth;
  70.   burnDelay = (cycleTime / 2) / burnDepth;
  71.   flickLow = grnHigh - flickerDepth;
  72.   flickDelay = (cycleTime / 2) / flickerDepth;
  73.   flutLow = grnHigh - flutterDepth;
  74.   flutDelay = ((cycleTime / 2) / flutterDepth);
  75.  
  76.   Serial.begin(9600);
  77.   // while the serial stream is not open, do nothing:
  78.   while (!Serial);
  79.  
  80.   // Print variable values for debugging
  81.   Serial.print("flickerDepth = ");
  82.   Serial.println(flickerDepth);
  83.   Serial.print("burnLow = ");
  84.   Serial.println(burnLow);
  85.   Serial.print("burnDelay = ");
  86.   Serial.println(burnDelay);
  87.   Serial.print("flickLow = ");
  88.   Serial.println(flickLow);
  89.   Serial.print("flickDelay = ");
  90.   Serial.println(flickDelay);
  91.   Serial.print("flutLow = ");
  92.   Serial.println(flutLow);
  93.   Serial.print("flutDelay = ");
  94.   Serial.println(flutDelay);
  95.  
  96. }
  97.  
  98. void loop() {
  99.   currentMillis = millis();
  100.   candleAnimation(0); // pass ledNumber
  101.   FastLED.show();
  102. }
  103.  
  104. void candleAnimation(byte animateCandleNumber)
  105. {
  106.   /*  each state of the animation calls one of the following animation elements:
  107.         1. on() = solid yellow - does not need a flicker so does not pass a variable
  108.         2. burn(onForSeconds) = candle is burning normally, flickering slightly
  109.         3. flicker(onForSeconds) = candle flickers noticably
  110.         4. flutter(onForSeconds) = the candle needs air!
  111.       the onForSeconds variable tells how long to play that animation element for and also
  112.       passes down into the elements that require effects
  113.   */
  114.  
  115.   //   candleAnimLength = random(0, 10);
  116.   //   randomAnimNumber = random(0, 4);
  117.   //   candleAnimStatus[animateCandleNumber] = random(0, 4);
  118.  
  119.  
  120.  
  121.   // initial value 0
  122.   static byte statenumber = 0;
  123.  
  124.   // allows for onForSecondss of each animation to be changed easily
  125.   byte onForSeconds; // in seconds
  126.  
  127.   switch (statenumber)
  128.   {
  129.     // state 0: burn for seconds equal to onForSeconds
  130.     case 0:
  131.       // burn
  132.       onForSeconds = 10;
  133.       Serial.println("Case 0: Burn");
  134.       if (burn(onForSeconds, animateCandleNumber) == true)
  135.       {
  136.         // go to next state
  137.         statenumber = 1;
  138.       }
  139.       break;
  140.  
  141.     // state 1: flicker for seconds equal to onForSeconds
  142.     case 1:
  143.       // flicker
  144.       onForSeconds = 5;
  145.       Serial.println("Case 1: Flicker");
  146.       if (flicker(onForSeconds, animateCandleNumber) == true)
  147.       {
  148.         // go to next state
  149.         statenumber = 2;
  150.       }
  151.       break;
  152.  
  153.     // state 2: burn for seconds equal to onForSeconds
  154.     case 2:
  155.       // burn
  156.       onForSeconds = 8;
  157.       Serial.println("Case 2: Burn");
  158.       if (burn(onForSeconds, animateCandleNumber) == true)
  159.       {
  160.         // go to next state
  161.         statenumber = 3;
  162.       }
  163.       break;
  164.     // state 3: flutter for seconds equal to onForSeconds
  165.     case 3:
  166.       // flutter
  167.       onForSeconds = 5;
  168.       Serial.println("Case 3: Flutter");
  169.       if (flutter(onForSeconds, animateCandleNumber) == true)
  170.       {
  171.         // go to next state
  172.         statenumber = 4;
  173.       }
  174.       break;
  175.     // state 4: burn for seconds equal to onForSeconds
  176.     case 4:
  177.       // burn
  178.       onForSeconds = 3;
  179.       Serial.println("Case 4: Burn");
  180.       if (burn(onForSeconds, animateCandleNumber) == true)
  181.       {
  182.         // go to next state
  183.         statenumber = 5;
  184.       }
  185.       break;
  186.     // state 5: on for seconds equal to onForSeconds
  187.     case 5:
  188.       // on
  189.       onForSeconds = 10;
  190.       Serial.println("Case 5: On");
  191.       on(animateCandleNumber); // does not pass the variable as no effect is required
  192.       // delay
  193.       if (doDelay(onForSeconds * 1000)) // converts to seconds
  194.       {
  195.         // go to next state
  196.         statenumber = 6;
  197.       }
  198.       break;
  199.     // state 6: burn for seconds equal to onForSeconds
  200.     case 6:
  201.       // burn
  202.       onForSeconds = 10;
  203.       Serial.println("Case 6: Burn");
  204.       if (burn(onForSeconds, animateCandleNumber) == true)
  205.       {
  206.         // go to next state
  207.         statenumber = 7;
  208.       }
  209.       break;
  210.     // state 7: flicker for seconds equal to onForSeconds and loop back
  211.     case 7:
  212.       // flicker
  213.       onForSeconds = 10;
  214.       Serial.println("Case 7: Flicker");
  215.       if (flicker(onForSeconds, animateCandleNumber) == true)
  216.       {
  217.         // go to next state
  218.         statenumber = 0;
  219.       }
  220.       break;
  221.   }
  222. }
  223.  
  224.  
  225. /*
  226.   For Main Animation States
  227.   non-blocking delay for duration milliseconds
  228.   returns false if delay in progress, else true
  229. */
  230. bool doDelay(unsigned long duration)
  231. {
  232.   // variable to keep track of previous millis
  233.   static unsigned long previousMillis = 0;
  234.  
  235.   // if delay not started
  236.   if (previousMillis == 0)
  237.   {
  238.     // start delay
  239.     previousMillis = currentMillis;
  240.   }
  241.   // if delay has lapsed
  242.   if (currentMillis - previousMillis >= duration)
  243.   {
  244.     // reset previous millis
  245.     previousMillis = 0;
  246.     // indicate that delay has lapsed
  247.     return true;
  248.   }
  249.   // indicate delay in progress
  250.   return false;
  251. }
  252.  
  253.  
  254. /*
  255.   For Animation Element Effects
  256.   non-blocking delay for duration milliseconds
  257.   returns false if delay in progress, else true
  258. */
  259. // basic fire function - not called in main loop
  260.  
  261. bool fire(byte grnLow, byte animLed) {
  262.   // remember if we're dimming (true) or brightening (false)
  263.   static bool fDimming = true;
  264.   // remember value for grnPx
  265.   static int grnPx = grnHigh;
  266.   // remember start time of delay
  267.   static unsigned long previousMillis = 0;
  268.  
  269.   //Serial.print("Seconds: ");
  270.   //Serial.println(currentMillis / 1000);
  271.   //Serial.print("Green: ");
  272.   //Serial.println(grnPx);
  273.  
  274.   //Serial.print("fDelay: ");
  275.   //Serial.println(fDelay);
  276.  
  277.   // if in dimming mode
  278.   if (fDimming == true)
  279.   {
  280.     Serial.println("Dimming");
  281.     // if timing not started yet
  282.     if (previousMillis == 0)
  283.     {
  284.       leds[animLed] = CRGB(redPx, grnPx, bluePx);
  285.       // set start time
  286.       previousMillis = currentMillis;
  287.     }
  288.  
  289.     // if delay lapsed
  290.     if (currentMillis - previousMillis >= fDelay)
  291.     {
  292.       // decrement grnPx
  293.       grnPx--;
  294.  
  295.       // reset start time
  296.       previousMillis = 0;
  297.     }
  298.     // if lower limit reached
  299.     if (grnPx <= grnLow)
  300.     {
  301.       // switch to next state
  302.       fDimming = false;
  303.     }
  304.   }
  305.   // if in brightening mode
  306.  
  307.   else
  308.   {
  309.     Serial.println("Brightening");
  310.  
  311.     // if timing not started yet
  312.     if (previousMillis == 0)
  313.     {
  314.       leds[animLed] = CRGB(redPx, grnPx, bluePx);
  315.  
  316.       // set start time
  317.       previousMillis = currentMillis;
  318.     }
  319.  
  320.     // if delay lapsed
  321.     if (currentMillis - previousMillis >= fDelay)
  322.     {
  323.       // increment grnPx
  324.       grnPx++;
  325.  
  326.       // reset start time
  327.       previousMillis = 0;
  328.     }
  329.  
  330.     // if upper limit reached
  331.     if (grnPx >= grnHigh)
  332.     {
  333.       // switch to previous state
  334.       fDimming = true;  // This is causing a bug. when commented grnPx continues to rise
  335.  
  336.       // indicate that we have done one cycle dim and brighten
  337.  
  338.       Serial.println("This is the original TRUE return point");  
  339.       return true;       //<-- Returns True once and then only returns false after that
  340.  
  341.     }
  342.   }
  343.  
  344.     // indicate function not completed yet
  345.     Serial.println("Fire = false");
  346.     return false;
  347.  
  348. }
  349.  
  350.  
  351.  
  352. // fire animations
  353. void on(byte n) {
  354.   byte grnPx = grnHigh - 5;
  355.   leds[n] = CRGB(redPx, grnPx, bluePx);
  356. }
  357.  
  358. bool burn(byte f, byte n) {
  359.  
  360.   byte fRep = f * (1000 / cycleTime);
  361.   fDelay = burnDelay;
  362.   // remember var count; initial value zero
  363.   static byte var = 0;
  364.  
  365.   // call fire; if the result is true, a cycle has been completed
  366.   if (fire(burnLow, n) == true)
  367.   {
  368.     // increment var
  369.     var++;
  370.   }
  371.  
  372.    Serial.print("var = ");
  373.    Serial.println(var);
  374.  
  375.   // if not fRep cycles done
  376.   if (var < fRep)
  377.   {
  378.     // indicate burn (still) in progress
  379.     return false;
  380.   }
  381.   else {
  382.     // reset var
  383.     var = 0;
  384.     // indicate burn completed
  385.     Serial.println("Burn Complete");
  386.     return true;
  387.   }
  388. }
  389.  
  390. bool flicker(byte f, byte n) {
  391.  
  392.   byte fRep = f * (1000 / cycleTime);
  393.   static byte statenumber = 0;
  394.   static byte var = 0;
  395.  
  396.   switch (statenumber)
  397.   {
  398.     // state 0: burn once
  399.     case 0:
  400.  
  401.       fDelay = burnDelay;
  402.       if (fire(burnLow, n) == true)
  403.       {
  404.         // go to next state
  405.         statenumber = 1;
  406.       }
  407.       break;
  408.  
  409.     // state 1: flicker fRep times
  410.     case 1:
  411.       fDelay = flickDelay;
  412.  
  413.       // remember var count; initial value zero
  414.       var = 0;
  415.  
  416.       // call fire; if the result is true, a cycle has been completed
  417.       if (fire(flickLow, n) == true)
  418.       {
  419.         // increment var
  420.         var++;
  421.       }
  422.  
  423.       // if not fRep cycles done
  424.       if (var < fRep)
  425.       {
  426.         // indicate burn (still) in progress
  427.         return false;
  428.       }
  429.  
  430.       if (var == fRep)
  431.       {
  432.         // go to next state
  433.         statenumber = 2;
  434.  
  435.         // reset var
  436.         var = 0;
  437.       }
  438.       break;
  439.  
  440.     // state 2: burn three times
  441.     case 2:
  442.       fDelay = burnDelay;
  443.  
  444.       // remember var count; initial value zero
  445.       var = 0;
  446.  
  447.       // call fire; if the result is true, a cycle has been completed
  448.       if (fire(burnLow, n) == true)
  449.       {
  450.         // increment var
  451.         var++;
  452.       }
  453.  
  454.       // if not fRep cycles done
  455.       if (var < 3)
  456.       {
  457.         // indicate burn (still) in progress
  458.         return false;
  459.       }
  460.       break;
  461.  
  462.   }
  463.   // indicate flicker completed
  464.   return true;
  465. }
  466.  
  467. bool flutter(byte f, byte n) {
  468.  
  469.   byte fRep = f * (1000 / cycleTime);
  470.  
  471.   static byte statenumber = 0;
  472.   static byte var = 0;
  473.  
  474.   switch (statenumber)
  475.   {
  476.     // state 0: burn once
  477.     case 0:
  478.       fDelay = burnDelay;
  479.       if (fire(burnLow, n) == true)
  480.       {
  481.         // go to next state
  482.         statenumber = 1;
  483.       }
  484.       break;
  485.  
  486.     // state 1: flicker once
  487.     case 1:
  488.       fDelay = flickDelay;
  489.       if (fire(flickLow, n) == true)
  490.       {
  491.         // go to next state
  492.         statenumber = 2;
  493.       }
  494.       break;
  495.  
  496.     // state 2 flutter fRep times
  497.     case 2:
  498.       fDelay = flutDelay;
  499.  
  500.       // remember var count; initial value zero
  501.       var = 0;
  502.  
  503.       // call fire; if the result is true, a cycle has been completed
  504.       if (fire(flutLow, n) == true)
  505.       {
  506.         // increment var
  507.         var++;
  508.       }
  509.  
  510.       // if not fRep cycles done
  511.       if (var < fRep)
  512.       {
  513.         // indicate burn (still) in progress
  514.         return false;
  515.       }
  516.  
  517.       if (var == fRep)
  518.       {
  519.         // go to next state
  520.         statenumber = 3;
  521.  
  522.         // reset var
  523.         var = 0;
  524.       }
  525.       break;
  526.  
  527.     // state 3: flicker two times
  528.     case 3:
  529.       fDelay = flickDelay;
  530.  
  531.       // remember var count; initial value zero
  532.       var = 0;
  533.  
  534.       // call fire; if the result is true, a cycle has been completed
  535.       if (fire(flickLow, n) == true)
  536.       {
  537.         // increment var
  538.         var++;
  539.       }
  540.  
  541.       // if not fRep cycles done
  542.       if (var < 2)
  543.       {
  544.         // indicate burn (still) in progress
  545.         return false;
  546.       }
  547.  
  548.       if (var == 2)
  549.       {
  550.         // go to next state
  551.         statenumber = 4;
  552.  
  553.         // reset var
  554.         var = 0;
  555.       }
  556.       break;
  557.  
  558.     // state 4: burn two times
  559.     case 4:
  560.       fDelay = burnDelay;
  561.  
  562.       // remember var count; initial value zero
  563.       var = 0;
  564.  
  565.       // call fire; if the result is true, a cycle has been completed
  566.       if (fire(burnLow, n) == true)
  567.       {
  568.         // increment var
  569.         var++;
  570.       }
  571.  
  572.       // if not fRep cycles done
  573.       if (var < 2)
  574.       {
  575.         // indicate burn (still) in progress
  576.         return false;
  577.       }
  578.       break;
  579.  
  580.   }
  581.   // indicate flutter completed
  582.   return true;
  583. }
Advertisement
Add Comment
Please, Sign In to add comment