Sky_Jones

Noise + Palette + Blend

Dec 28th, 2014
529
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 11.86 KB | None | 0 0
  1. #include <FastLED.h>
  2.  
  3. #define LED_PIN 6
  4. #define BRIGHTNESS  255
  5. #define LED_TYPE    WS2811
  6. #define COLOR_ORDER RGB
  7.  
  8. const uint8_t kMatrixWidth  = 10;
  9. const uint8_t kMatrixHeight = 4;
  10. const bool    kMatrixSerpentineLayout = true;
  11.  
  12. #define UPDATES_PER_SECOND 100
  13.  
  14.  
  15. #define NUM_LEDS (kMatrixWidth * kMatrixHeight)
  16. #define MAX_DIMENSION ((kMatrixWidth>kMatrixHeight) ? kMatrixWidth : kMatrixHeight)
  17.  
  18. // The leds
  19. CRGB leds[kMatrixWidth * kMatrixHeight];
  20.  
  21. // The 16 bit version of our coordinates
  22. static uint16_t x;
  23. static uint16_t y;
  24. static uint16_t z;
  25.  
  26. // We're using the x/y dimensions to map to the x/y pixels on the matrix.  We'll
  27. // use the z-axis for "time".  speed determines how fast time moves forward.  Try
  28. // 1 for a very slow moving effect, or 60 for something that ends up looking like
  29. // water.
  30. uint16_t speed = 1; // speed is set dynamically once we've started up
  31.  
  32. // Scale determines how far apart the pixels in our noise matrix are.  Try
  33. // changing these values around to see how it affects the motion of the display.  The
  34. // higher the value of scale, the more "zoomed out" the noise iwll be.  A value
  35. // of 1 will be so zoomed in, you'll mostly see solid colors.
  36. uint16_t scale = 30; // scale is set dynamically once we've started up
  37.  
  38. // This is the array that we keep our computed noise values in
  39. uint8_t noise[MAX_DIMENSION][MAX_DIMENSION];
  40.  
  41. CRGBPalette16 currentPalette( CRGB::Black );
  42.  
  43. CRGBPalette16 targetPalette( CRGB::Black );
  44.  
  45. uint8_t       colorLoop = 1;
  46.  
  47. void setup() {
  48.   delay(3000);
  49.   LEDS.addLeds<LED_TYPE,LED_PIN,COLOR_ORDER>(leds,NUM_LEDS);
  50.   LEDS.setBrightness(BRIGHTNESS);
  51.  
  52.   // Initialize our coordinates to some random values
  53.   x = random16();
  54.   y = random16();
  55.   z = random16();
  56. }
  57.  
  58.  
  59.  
  60. // Fill the x/y array of 8-bit noise values using the inoise8 function.
  61. void fillnoise8() {
  62.   // If we're runing at a low "speed", some 8-bit artifacts become visible
  63.   // from frame-to-frame.  In order to reduce this, we can do some fast data-smoothing.
  64.   // The amount of data smoothing we're doing depends on "speed".
  65.   uint8_t dataSmoothing = 0;
  66.   if( speed < 50) {
  67.     dataSmoothing = 200 - (speed * 4);
  68.   }
  69.  
  70.   for(int i = 0; i < MAX_DIMENSION; i++) {
  71.     int ioffset = scale * i;
  72.     for(int j = 0; j < MAX_DIMENSION; j++) {
  73.       int joffset = scale * j;
  74.      
  75.       uint8_t data = inoise8(x + ioffset,y + joffset,z);
  76.  
  77.       // The range of the inoise8 function is roughly 16-238.
  78.       // These two operations expand those values out to roughly 0..255
  79.       // You can comment them out if you want the raw noise data.
  80.       data = qsub8(data,16);
  81.       data = qadd8(data,scale8(data,39));
  82.  
  83.       if( dataSmoothing ) {
  84.         uint8_t olddata = noise[i][j];
  85.         uint8_t newdata = scale8( olddata, dataSmoothing) + scale8( data, 256 - dataSmoothing);
  86.         data = newdata;
  87.       }
  88.      
  89.       noise[i][j] = data;
  90.     }
  91.   }
  92.  
  93.   z += speed;
  94.  
  95.   // apply slow drift to X and Y, just for visual variation.
  96.   x += speed / 8;
  97.   y -= speed / 16;
  98. }
  99.  
  100. void mapNoiseToLEDsUsingPalette()
  101. {
  102.   static uint8_t ihue=0;
  103.  
  104.   for(int i = 0; i < kMatrixWidth; i++) {
  105.     for(int j = 0; j < kMatrixHeight; j++) {
  106.       // We use the value at the (i,j) coordinate in the noise
  107.       // array for our brightness, and the flipped value from (j,i)
  108.       // for our pixel's index into the color palette.
  109.  
  110.       uint8_t index = noise[j][i];
  111.       uint8_t bri =   noise[i][j];
  112.  
  113.       // if this palette is a 'loop', add a slowly-changing base value
  114.       if( colorLoop) {
  115.         index += ihue;
  116.       }
  117.  
  118.       // brighten up, as the color palette itself often contains the
  119.       // light/dark dynamic range desired
  120.       if( bri > 127 ) {
  121.         bri = 255;
  122.       } else {
  123.         bri = dim8_raw( bri * 2);
  124.       }
  125.  
  126.       CRGB color = ColorFromPalette( currentPalette, index, bri);
  127.       leds[XY(i,j)] = color;
  128.     }
  129.   }
  130.  
  131.   ihue+=1;
  132. }
  133.  
  134. void loop() {
  135.  ChangePalettePeriodically();
  136.  
  137. // Crossfade current palette slowly toward the target palette
  138. //
  139. // Each time that nblendPaletteTowardPalette is called, small changes
  140. // are made to currentPalette to bring it closer to matching targetPalette.
  141. // You can control how many changes are made in each call:
  142. // - the default of 24 is a good balance
  143. // - meaningful values are 1-48. 1=veeeeeeeery slow, 48=quickest
  144. // - "0" means do not change the currentPalette at all; freeze
  145. uint8_t maxChanges = 2;
  146. nblendPaletteTowardPalette( currentPalette, targetPalette, maxChanges);
  147.  
  148.   // generate noise data
  149.   fillnoise8();
  150.  
  151.   // convert the noise data to colors in the LED array
  152.   // using the current palette
  153.   mapNoiseToLEDsUsingPalette();
  154.  
  155.   LEDS.show();
  156.   // delay(10);
  157. }
  158.  
  159.  
  160.  
  161. // There are several different palettes of colors demonstrated here.
  162. //
  163. // FastLED provides several 'preset' palettes: RainbowColors_p, RainbowStripeColors_p,
  164. // OceanColors_p, CloudColors_p, LavaColors_p, ForestColors_p, and PartyColors_p.
  165. //
  166. // Additionally, you can manually define your own color palettes, or you can write
  167. // code that creates color palettes on the fly.
  168.  
  169. // 1 = 5 sec per palette
  170. // 2 = 10 sec per palette
  171. // etc
  172. #define HOLD_PALETTES_X_TIMES_AS_LONG 60
  173.  
  174. void ChangePalettePeriodically()
  175. {
  176.   uint8_t secondHand = ((millis() / 1000) / HOLD_PALETTES_X_TIMES_AS_LONG) % 60;
  177.   static uint8_t lastSecond = 99;
  178.  
  179.   if( lastSecond != secondHand) {
  180.     lastSecond = secondHand;
  181.     if( secondHand ==  0)  { targetPalette = CRGBPalette16( //Red
  182.                                              CHSV( 0, 255, 255), CHSV( 0, 255, 0), CHSV( 0, 255, 255) );          
  183.                                              speed = 1; scale = 100; colorLoop = 1; }
  184.     if( secondHand ==  3)  { targetPalette = CRGBPalette16( //Orange
  185.                                              CHSV( 16, 255, 255), CHSV( 16, 255, 0),  CHSV( 16, 255, 255) );        
  186.                                              speed = 1; scale = 100; colorLoop = 1; }
  187.     if( secondHand ==  6)  { targetPalette = CRGBPalette16( //Yellow
  188.                                              CHSV( 64, 255, 255),  CHSV( 64, 255, 0),  CHSV( 64, 255, 255) );
  189.                                              speed = 1; scale = 100; colorLoop = 1; }
  190.     if( secondHand == 9)  { targetPalette = CRGBPalette16( //Green
  191.                                              CHSV( 96, 255, 255),  CHSV( 96, 255, 0),  CHSV( 96, 255, 255) );
  192.                                              speed = 1; scale = 100; colorLoop = 1; }
  193.     if( secondHand == 12)  { targetPalette = CRGBPalette16( //Aqua
  194.                                              CHSV( 128, 255, 255),  CHSV( 128, 255, 0),  CHSV( 128, 255, 255) );
  195.                                              speed = 1; scale = 100; colorLoop = 1; }
  196.     if( secondHand == 15)  { targetPalette = CRGBPalette16( //Blue
  197.                                              CHSV( 160, 255, 255),  CHSV( 160, 255, 0),  CHSV( 160, 255, 255) );
  198.                                              speed = 1; scale = 100; colorLoop = 1; }
  199.     if( secondHand == 18)  { targetPalette = CRGBPalette16( //Purple
  200.                                              CHSV( 192, 255, 255),  CHSV( 192, 255, 0),  CHSV( 192, 255, 255) );
  201.                                              speed = 1; scale = 100; colorLoop = 1; }
  202.     if( secondHand == 21)  { targetPalette = CRGBPalette16( //Pink
  203.                                              CHSV( 224, 255, 255),  CHSV( 224, 255, 0),  CHSV( 224, 255, 255) );
  204.                                              speed = 1; scale = 100; colorLoop = 1; }
  205.     if( secondHand == 24)  { targetPalette = CRGBPalette16( //Red-Orange-Yellow
  206.                                              CHSV( 0, 255, 255),  CHSV( 64, 255, 255),  CHSV( 0, 255, 255) );
  207.                                              speed = 1; scale = 100; colorLoop = 1; }
  208.     if( secondHand == 27)  { targetPalette = CRGBPalette16( //Orange-Yellow-Green
  209.                                              CHSV( 32, 255, 255),  CHSV( 96, 255, 255),  CHSV( 32, 255, 255) );
  210.                                              speed = 1; scale = 100; colorLoop = 1; }
  211.     if( secondHand == 30)  { targetPalette = CRGBPalette16( //Yellow-Green-Aqua
  212.                                              CHSV( 64, 255, 255),  CHSV( 128, 255, 255),  CHSV( 64, 255, 255) );
  213.                                              speed = 1; scale = 100; colorLoop = 1; }
  214.     if( secondHand == 33)  { targetPalette = CRGBPalette16( //Green-Aqua-Blue
  215.                                              CHSV( 96, 255, 255),  CHSV( 160, 255, 255),  CHSV( 96, 255, 255) );
  216.                                              speed = 1; scale = 100; colorLoop = 1; }
  217.     if( secondHand == 36)  { targetPalette = CRGBPalette16( //Aqua-Blue-Purple
  218.                                              CHSV( 128, 255, 255),  CHSV( 192, 255, 255),  CHSV( 128, 255, 255) );
  219.                                              speed = 1; scale = 100; colorLoop = 1; }
  220.     if( secondHand == 39)  { targetPalette = CRGBPalette16( //Blue-Purple-Pink
  221.                                              CHSV( 160, 255, 255),  CHSV( 224, 255, 255),  CHSV( 160, 255, 255) );
  222.                                              speed = 1; scale = 100; colorLoop = 1; }
  223.     if( secondHand == 42)  { targetPalette = CRGBPalette16( //Purple-Pink-Red
  224.                                              CHSV( 192, 255, 255),  CHSV( 255, 255, 255),  CHSV( 192, 255, 255) );
  225.                                              speed = 1; scale = 100; colorLoop = 1; }
  226.     if( secondHand == 45)  { targetPalette = CRGBPalette16( //Pink-Red-Orange
  227.                                              CHSV( 224, 255, 255),  CHSV( 232, 255, 255),  CHSV( 240, 255, 255),  CHSV( 248, 255, 255),
  228.                                              CHSV( 0, 255, 255),  CHSV( 8, 255, 255),  CHSV( 16, 255, 255),  CHSV( 24, 255, 255),
  229.                                              CHSV( 32, 255, 255),  CHSV( 24, 255, 255),  CHSV( 16, 255, 255),  CHSV( 8, 255, 255),
  230.                                              CHSV( 0, 255, 255),  CHSV( 248, 255, 255),  CHSV( 240, 255, 255),  CHSV( 232, 255, 255) );
  231.                                              speed = 1; scale = 100; colorLoop = 1; }
  232.     if( secondHand == 48)  { targetPalette = CRGBPalette16( //Rainbow Noise
  233.                                              CHSV( 0, 255, 255),  CHSV( 64, 255, 255),  CHSV( 128, 255, 255),  CHSV( 192, 255, 255) );
  234.                                              speed = 1; scale = 100; colorLoop = 1; }
  235.     if( secondHand == 54)  { targetPalette = CRGBPalette16( //Ocean
  236.                                              CHSV( 128, 64, 255),  CHSV( 128, 128, 255),  CHSV( 128, 192, 255),  CHSV( 128, 255, 255),
  237.                                              CHSV( 132, 255, 255),  CHSV( 136, 255, 255),  CHSV( 140, 255, 255),  CHSV( 144, 192, 255),
  238.                                              CHSV( 144, 128, 255),  CHSV( 148, 192, 255),  CHSV( 152, 255, 255),  CHSV( 156, 255, 255),
  239.                                              CHSV( 160, 255, 255),  CHSV( 160, 192, 255),  CHSV( 160, 128, 255),  CHSV( 160, 64, 255) );
  240.                                              speed = 1; scale = 100; colorLoop = 1; }
  241.     if( secondHand == 57)  { targetPalette = CRGBPalette16( //White
  242.                                              CHSV( 0, 0, 255), CHSV( 0, 0, 0), CHSV( 0, 0, 255) );          
  243.                                              speed = 1; scale = 100; colorLoop = 1; }
  244.  
  245. }
  246.  
  247. }
  248. //
  249. // Mark's xy coordinate mapping code.  See the XYMatrix for more information on it.
  250. //
  251. uint16_t XY( uint8_t x, uint8_t y)
  252. {
  253.   uint16_t i;
  254.   if( kMatrixSerpentineLayout == false) {
  255.     i = (y * kMatrixWidth) + x;
  256.   }
  257.   if( kMatrixSerpentineLayout == true) {
  258.     if( y & 0x01) {
  259.       // Odd rows run backwards
  260.       uint8_t reverseX = (kMatrixWidth - 1) - x;
  261.       i = (y * kMatrixWidth) + reverseX;
  262.     } else {
  263.       // Even rows run forwards
  264.       i = (y * kMatrixWidth) + x;
  265.     }
  266.   }
  267.   return i;
  268. }
Advertisement
Add Comment
Please, Sign In to add comment