diff --git a/NeoPixelBus.cpp b/NeoPixelBus.cpp index e4f098d..e4a66a4 100644 --- a/NeoPixelBus.cpp +++ b/NeoPixelBus.cpp @@ -37,9 +37,7 @@ NeoPixelBus::NeoPixelBus(uint16_t n, uint8_t p, uint8_t t) : _pin(p), _animationLastTick(0), _activeAnimations(0) -#if defined(NEO_RGB) || defined(NEO_KHZ400) ,_flagsPixels(t) -#endif { setPin(p); @@ -128,7 +126,7 @@ void NeoPixelBus::Show(void) // 8 MHz(ish) AVR --------------------------------------------------------- #if (F_CPU >= 7400000UL) && (F_CPU <= 9500000UL) -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT if ((_flagsPixels & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream @@ -335,7 +333,7 @@ void NeoPixelBus::Show(void) } // endif PORTB #endif -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT } else { @@ -394,7 +392,7 @@ void NeoPixelBus::Show(void) // 12 MHz(ish) AVR -------------------------------------------------------- #elif (F_CPU >= 11100000UL) && (F_CPU <= 14300000UL) -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT if ((_flagsPixels & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream @@ -526,7 +524,7 @@ void NeoPixelBus::Show(void) } #endif -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT } else { @@ -582,7 +580,7 @@ void NeoPixelBus::Show(void) // 16 MHz(ish) AVR -------------------------------------------------------- #elif (F_CPU >= 15400000UL) && (F_CPU <= 19000000L) -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT if ((_flagsPixels & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream @@ -633,7 +631,7 @@ void NeoPixelBus::Show(void) [hi] "r" (hi), [lo] "r" (lo)); -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT } else { @@ -719,7 +717,7 @@ void NeoPixelBus::Show(void) ARM_DEMCR |= ARM_DEMCR_TRCENA; ARM_DWT_CTRL |= ARM_DWT_CTRL_CYCCNTENA; -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT if ((_flagsPixels & NEO_SPDMASK) == NEO_KHZ800) { #endif @@ -745,7 +743,7 @@ void NeoPixelBus::Show(void) } } while (ARM_DWT_CYCCNT - cyc < CYCLES_800); -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT } else { @@ -807,7 +805,7 @@ void NeoPixelBus::Show(void) pix = *p++; mask = 0x80; -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT if ((_flagsPixels & NEO_SPDMASK) == NEO_KHZ800) { #endif @@ -815,7 +813,7 @@ void NeoPixelBus::Show(void) time0 = TIME_800_0; time1 = TIME_800_1; period = PERIOD_800; -#ifdef NEO_KHZ400 +#ifdef INCLUDE_NEO_KHZ400_SUPPORT } else { @@ -895,20 +893,17 @@ void NeoPixelBus::UpdatePixelColor( uint8_t b) { uint8_t *p = &_pixels[n * 3]; -#ifdef NEO_RGB if ((_flagsPixels & NEO_COLMASK) == NEO_GRB) { -#endif *p++ = g; *p++ = r; -#ifdef NEO_RGB } else { *p++ = r; *p++ = g; } -#endif + *p = b; } @@ -920,20 +915,17 @@ RgbColor NeoPixelBus::GetPixelColor(uint16_t n) const RgbColor c; uint8_t *p = &_pixels[n * 3]; -#ifdef NEO_RGB if ((_flagsPixels & NEO_COLMASK) == NEO_GRB) { -#endif c.G = *p++; c.R = *p++; -#ifdef NEO_RGB } else { c.R = *p++; c.G = *p++; } -#endif + c.B = *p; return c; } diff --git a/NeoPixelBus.h b/NeoPixelBus.h index 959e87a..00b024c 100644 --- a/NeoPixelBus.h +++ b/NeoPixelBus.h @@ -29,24 +29,22 @@ License along with NeoPixel. If not, see #include "RgbColor.h" // '_flagsPixels' flags for LED _pixels (third parameter to constructor): +#define NEO_RGB 0x00 // Wired for RGB data order #define NEO_GRB 0x01 // Wired for GRB data order #define NEO_COLMASK 0x01 +#define NEO_KHZ400 0x00 // 400 KHz datastream #define NEO_KHZ800 0x02 // 800 KHz datastream #define NEO_SPDMASK 0x02 -// Trinket flash space is tight, v1 NeoPixels aren't handled by default. -// Remove the ifndef/endif to add support -- but code will be bigger. -// Conversely, can comment out the #defines to save space on other MCUs. -#ifndef __AVR_ATtiny85__ -#define NEO_RGB 0x00 // Wired for RGB data order -#define NEO_KHZ400 0x00 // 400 KHz datastream -#endif +// v1 NeoPixels aren't handled by default, include the following define before the +// NeoPixelBus library include to support the slower bus speeds +// #define INCLUDE_NEO_KHZ400_SUPPORT class NeoPixelBus { public: // Constructor: number of LEDs, pin number, LED type - NeoPixelBus(uint16_t n, uint8_t p = 6, uint8_t t = NEO_GRB + NEO_KHZ800); + NeoPixelBus(uint16_t n, uint8_t p = 6, uint8_t t = NEO_GRB | NEO_KHZ800); ~NeoPixelBus(); void Begin(void); @@ -88,10 +86,8 @@ private: const uint16_t _countPixels; // Number of RGB LEDs in strip const uint16_t _sizePixels; // Size of '_pixels' buffer below - -#if defined(NEO_RGB) || defined(NEO_KHZ400) const uint8_t _flagsPixels; // Pixel flags (400 vs 800 KHz, RGB vs GRB color) -#endif + uint8_t _pin; // Output pin number uint8_t* _pixels; // Holds LED color values (3 bytes each) uint32_t _endTime; // Latch timing reference diff --git a/ReadMe.md b/ReadMe.md new file mode 100644 index 0000000..0e942a3 --- /dev/null +++ b/ReadMe.md @@ -0,0 +1,95 @@ +NeoPixelBus +==== +Arduino NeoPixel library + +Clone this into your Arduino\Library folder + +This library is a modification of the Adafruit NeoPixel library. +The Api is similiar, but it removes the overal brightness feature and adds animation support. + +Installing This Library +------------------------ +Create a directory in your Arduino\Library folder named "NeoPixelBus" +Clone (Git) this project into that folder. +It should now show up in the import list. + +Samples +------- +NeoPixelTest - this is simple example that sets four neopixels to red, green, blue, and then white in order; and then flashes them. If the first pixel is not green instead of read, you need to pass the NEO_RGB flag into the NeoPixelBus constructor. +NeoPixelFun - this is a more complex example, that includes code for three effects, and demonstrates animations. + +API Documentation +----------------- + +RgbColor object: +This represents a color and exposes useful methods to manipulate colors. +
+RgbColor(uint8_t r, uint8_t g, uint8_t b)
+
+ instantiates a RgbColor object with the given r, g, b values.
+
+RgbColor(uint8_t brightness)
+
+ instantiates a RgbColor object with the given brightness. 0 is black, 128 is grey, 255 is white.
+
+uint8_t CalculateBrightness()
+
+ returns the general brightness of the pixe, averaging color.
+
+void Darken(uint8_t delta)
+
+ this will darken the color by the given amount
+
+void Lighten(uint8_t delta)
+
+ this will lighten the color by the given amount
+
+static RgbColor LinearBlend(RgbColor left, RgbColor right, uint8_t progress)
+
+ this will return a color that is a blend between the given colors. The amount to blend is given by the value of progress, 0 will return the left value, 255 will return the right value, 128 will return the value between them.
+ NOTE: This is not an accurate "visible light" color blend but is fast and in most cases good enough.
+
+NeoPixelBus object:
+This represents a single NeoPixel Bus that is connected by a single pin. Please see Adafruit's documentation for details, but the differences are documented below.
+
+
+NeoPixelBus(uint16_t n, uint8_t p = 6, uint8_t t = NEO_GRB | NEO_KHZ800);
+
+instantiates a NewoPixelBus object, with n number of pixels on the bus, over the p pin, using the defined NeoPixel type.
+There are some NeoPixels that address the color values differently, so if you set the green color but it displays as red, use the NEO_RGB type flag.
+
+NeoPixelBus strip = NeoPixelBus(4, 8, NEO_GRB | NEO_KHZ800);
+
+It is rare, but some older NeoPixels require a slower communications speed, to include this support you must include the following define before the NeoPixelBus library include and then include the NEO_KHZ400 type flag to enable this slower speed.
+
+#define INCLUDE_NEO_KHZ400_SUPPORT
+#include <NeoPixelBus.h>
+
+NeoPixelBus strip = NeoPixelBus(4, 8, NEO_GRB | NEO_KHZ400);
+
+
+
+void SetPixelColor(uint16_t n, RgbColor c)
+
+ This allows setting a pixel on the bus to a color as defined by a color object. If an animation is actively running on a pixel, it will be stopped.
+
+RgbColor GetPixelColor(uint16_t n) const
+
+ this allows retrieving the current pixel color
+
+void LinearFadePixelColor(uint16_t time, uint16_t n, RgbColor color)
+
+ this will setup an animation for a pixel to linear fade between the current color and the given color over the time given. The time is in milliseconds.
+
+void StartAnimating()
+
+ this method will initialize the animation state. This should be called only if there are no active animations and new animations are started.
+
+void UpdateAnimations()
+
+ this method will allow the animations to processed and update the pixel color state.
+ NOTE: Show must still be called to push the color state to the physical NeoPixels.
+
+bool IsAnimating() const
+
+ this method will return the current animation state. It will return false if there are no active animations.
\ No newline at end of file
diff --git a/ReadMe.txt b/ReadMe.txt
deleted file mode 100644
index 0c851b1..0000000
--- a/ReadMe.txt
+++ /dev/null
@@ -1,66 +0,0 @@
-NeoPixelBus:
-
-This library is a modification of the Adafruit NeoPixel library.
-The Api is similiar, but it removes the overal brightness feature and adds animation support.
-
-Installing This Library:
-Create a directory in your Library folder named "NeoPixelBus"
-Clone (Git) this project into that folder.
-It should now show up in the import list.
-
-Sample:
- There is a sample project under the Sample sub-directory. Just copy and change the extention to ino.
-
-Documentation:
-
-RgbColor object:
-This represents a color and exposes useful methods to manipulate colors.
-
-RgbColor(uint8_t r, uint8_t g, uint8_t b)
- instantiates a RgbColor object with the given r, g, b values.
-
-RgbColor(uint8_t brightness)
- instantiates a RgbColor object with the given brightness. 0 is black, 128 is grey, 255 is white.
-
-uint8_t CalculateBrightness()
- returns the general brightness of the pixe, averaging color.
-
-void Darken(uint8_t delta)
- this will darken the color by the given amount
-
-void Lighten(uint8_t delta)
- this will lighten the color by the given amount
-
-static RgbColor LinearBlend(RgbColor left, RgbColor right, uint8_t progress)
- this will return a color that is a blend between the given colors. The amount to blend is given
- by the value of progress, 0 will return the left value, 255 will return the right value,
- 128 will return the value between them.
- NOTE: This is note an accurate "light" color blend but is fast and in most cases good enough.
-
-
-NeoPixelBus object:
-This represents a single NeoPixel Bus that is connected by a single pin. Please see Adafruit's
-documentation for details, but the differences are documented below.
-
-void SetPixelColor(uint16_t n, RgbColor c)
- This allows setting a pixel on the bus to a color as defined by a color object.
- If an animation is actively running on a pixel, it will be stopped.
-
-RgbColor GetPixelColor(uint16_t n) const
- this allows retrieving the current pixel color
-
-void LinearFadePixelColor(uint16_t time, uint16_t n, RgbColor color)
- this will setup an animation for a pixel to linear fade between the current color and the
- given color over the time given. The time is in milliseconds.
-
-void StartAnimating()
- this method will initialize the animation state. This should be called only if there
- are no active animations and new animations are started.
-
-void UpdateAnimations()
- this method will allow the animations to processed and update the pixel color state.
- NOTE: Show must still be called to push the color state to the physical NeoPixels.
-
-bool IsAnimating() const
- this method will return the current animation state. It will return false if there are
- no active animations.
\ No newline at end of file
diff --git a/examples/NeeoPixel16Ring/NeoPixel16RingFun.pde b/examples/NeeoPixel16Ring/NeoPixel16RingFun.pde
deleted file mode 100644
index 8990529..0000000
--- a/examples/NeeoPixel16Ring/NeoPixel16RingFun.pde
+++ /dev/null
@@ -1,123 +0,0 @@
-#include
-
-NeoPixelBus strip = NeoPixelBus(16, 8);
-uint16_t p = 0;
-
-
-
-void setup()
-{
- strip.Begin();
- strip.Show();
- randomSeed(analogRead(0));
- Serial.begin(9600);
-
-}
-
-
-void loop()
-{
- Serial.println("next");
-
-
-
- // LoopAround(192, 200);
- PickRandom(128);
- // FadeInFadeOutRinseRepeat(192);
-
- // start animating
- strip.StartAnimating();
-
- // wait until no more animations are running
- while (strip.IsAnimating())
- {
- strip.UpdateAnimations();
- strip.Show();
- delay(31); // ~30hz change cycle
- }
-
-}
-
-void FadeInFadeOutRinseRepeat(uint8_t peak)
-{
- if (p == 0)
- {
- for (uint8_t pixel = 0; pixel < 16; pixel++)
- {
- uint16_t time = random(800,1000);
- strip.LinearFadePixelColor(time, pixel, RgbColor(random(peak), random(peak), random(peak)));
- }
- }
- else if (p == 1)
- {
- for (uint8_t pixel = 0; pixel < 16; pixel++)
- {
- uint16_t time = random(600,700);
- strip.LinearFadePixelColor(time, pixel, RgbColor(0, 0, 0));
- }
- }
- p = (p + 1) % 2; // next procedure and keep within the number of procedures
-
-}
-
-void PickRandom(uint8_t peak)
-{
-
- // pick random set of pixels to animate
- uint8_t count = random(16);
- while (count > 0)
- {
- uint8_t pixel = random(16);
-
- // configure the animations
- RgbColor color; // = strip.getPixelColor(pixel);
-
- color = RgbColor(random(peak), random(peak), random(peak));
-
-
- uint16_t time = random(100,400);
- strip.LinearFadePixelColor( time, pixel, color);
-
- count--;
- }
-}
-
-void LoopAround(uint8_t peak, uint16_t speed)
-{
- // Looping around the ring sample
- uint16_t prev;
- RgbColor prevColor;
-
- // fade previous one dark
- prev = (p + 11) % 16;
- strip.LinearFadePixelColor(speed, prev, RgbColor(0, 0, 0));
-
- // fade previous one dark
- prev = (p + 12) % 16;
- prevColor = strip.GetPixelColor( prev );
- prevColor.Darken(prevColor.CalculateBrightness() / 2);
- strip.LinearFadePixelColor(speed, prev, prevColor);
-
- // fade previous one dark
- prev = (p + 13) % 16;
- prevColor = strip.GetPixelColor( prev );
- prevColor.Darken(prevColor.CalculateBrightness() / 2);
- strip.LinearFadePixelColor(speed, prev, prevColor);
-
- // fade previous one dark
- prev = (p + 14) % 16;
- prevColor = strip.GetPixelColor( prev );
- prevColor.Darken(prevColor.CalculateBrightness() / 2);
- strip.LinearFadePixelColor(speed, prev, prevColor);
-
- // fade previous one dark
- prev = (p + 15) % 16;
- prevColor = strip.GetPixelColor( prev );
- prevColor.Darken(prevColor.CalculateBrightness() / 2);
- strip.LinearFadePixelColor(speed, prev, prevColor);
-
- // fade current one light
- strip.LinearFadePixelColor(speed, p, RgbColor(random(peak), random(peak), random(peak)));
- p = (p+1) % 16;
-}
-
diff --git a/examples/NeoPixelFun/NeoPixelFun.pde b/examples/NeoPixelFun/NeoPixelFun.pde
new file mode 100644
index 0000000..b97ec40
--- /dev/null
+++ b/examples/NeoPixelFun/NeoPixelFun.pde
@@ -0,0 +1,139 @@
+#include
+
+#define pixelCount 4
+
+NeoPixelBus strip = NeoPixelBus(pixelCount, 8);
+uint16_t effectState = 0;
+
+
+void setup()
+{
+ strip.Begin();
+ strip.Show();
+ SetRandomSeed();
+}
+
+
+void loop()
+{
+ // There are three fun functions that implement different effects
+ // uncomment one at a time and upload to see the effect
+
+ // LoopAround(192, 200); // very interesting on rings of NeoPixels
+ PickRandom(128);
+ // FadeInFadeOutRinseRepeat(192);
+
+ // start animating
+ strip.StartAnimating();
+
+ // wait until no more animations are running
+ while (strip.IsAnimating())
+ {
+ strip.UpdateAnimations();
+ strip.Show();
+ delay(31); // ~30hz change cycle
+ }
+
+}
+
+void FadeInFadeOutRinseRepeat(uint8_t peak)
+{
+ if (effectState == 0)
+ {
+ for (uint8_t pixel = 0; pixel < pixelCount; pixel++)
+ {
+ uint16_t time = random(800,1000);
+ strip.LinearFadePixelColor(time, pixel, RgbColor(random(peak), random(peak), random(peak)));
+ }
+ }
+ else if (effectState == 1)
+ {
+ for (uint8_t pixel = 0; pixel < pixelCount; pixel++)
+ {
+ uint16_t time = random(600,700);
+ strip.LinearFadePixelColor(time, pixel, RgbColor(0, 0, 0));
+ }
+ }
+ effectState = (effectState + 1) % 2; // next effectState and keep within the number of effectStates
+
+}
+
+void PickRandom(uint8_t peak)
+{
+
+ // pick random set of pixels to animate
+ uint8_t count = random(pixelCount);
+ while (count > 0)
+ {
+ uint8_t pixel = random(pixelCount);
+
+ // configure the animations
+ RgbColor color; // = strip.getPixelColor(pixel);
+
+ color = RgbColor(random(peak), random(peak), random(peak));
+
+
+ uint16_t time = random(100,400);
+ strip.LinearFadePixelColor( time, pixel, color);
+
+ count--;
+ }
+}
+
+void LoopAround(uint8_t peak, uint16_t speed)
+{
+ // Looping around the ring sample
+ uint16_t prevPixel;
+ RgbColor prevColor;
+
+ // fade previous one dark
+ prevPixel = (effectState + (pixelCount - 5)) % pixelCount;
+ strip.LinearFadePixelColor(speed, prevPixel, RgbColor(0, 0, 0));
+
+ // fade previous one dark
+ prevPixel = (effectState + (pixelCount - 4)) % pixelCount;
+ prevColor = strip.GetPixelColor( prevPixel );
+ prevColor.Darken(prevColor.CalculateBrightness() / 2);
+ strip.LinearFadePixelColor(speed, prevPixel, prevColor);
+
+ // fade previous one dark
+ prevPixel = (effectState + (pixelCount - 3)) % pixelCount;
+ prevColor = strip.GetPixelColor( prevPixel );
+ prevColor.Darken(prevColor.CalculateBrightness() / 2);
+ strip.LinearFadePixelColor(speed, prevPixel, prevColor);
+
+ // fade previous one dark
+ prevPixel = (effectState + (pixelCount - 2)) % pixelCount;
+ prevColor = strip.GetPixelColor( prevPixel );
+ prevColor.Darken(prevColor.CalculateBrightness() / 2);
+ strip.LinearFadePixelColor(speed, prevPixel, prevColor);
+
+ // fade previous one dark
+ prevPixel = (effectState + (pixelCount - 1)) % pixelCount;
+ prevColor = strip.GetPixelColor( prevPixel );
+ prevColor.Darken(prevColor.CalculateBrightness() / 2);
+ strip.LinearFadePixelColor(speed, prevPixel, prevColor);
+
+ // fade current one light
+ strip.LinearFadePixelColor(speed, effectState, RgbColor(random(peak), random(peak), random(peak)));
+ effectState = (effectState + 1) % pixelCount;
+}
+
+void SetRandomSeed()
+{
+ uint32_t seed;
+
+ // random works best with a seed that can use 31 bits
+ // analogRead on a unconnected pin tends toward less than four bits
+ seed = analogRead(0);
+ delay(1);
+
+ for (int shifts = 3; shifts < 31; shifts += 3)
+ {
+ seed ^= analogRead(0) << shifts;
+ delay(1);
+ }
+
+ // Serial.println(seed);
+ randomSeed(seed);
+}
diff --git a/examples/NeoPixelTest/NeoPixelTest.pde b/examples/NeoPixelTest/NeoPixelTest.pde
new file mode 100644
index 0000000..8ef226d
--- /dev/null
+++ b/examples/NeoPixelTest/NeoPixelTest.pde
@@ -0,0 +1,44 @@
+#include
+
+#define pixelCount 4
+#define colorSaturation 128
+
+NeoPixelBus strip = NeoPixelBus(pixelCount, 8);
+
+RgbColor red = RgbColor(colorSaturation, 0, 0);
+RgbColor green = RgbColor(0, colorSaturation, 0);
+RgbColor blue = RgbColor(0, 0, colorSaturation);
+RgbColor white = RgbColor(colorSaturation);
+RgbColor black = RgbColor(0);
+
+void setup()
+{
+ // this resets all the neopixels to an off state
+ strip.Begin();
+ strip.Show();
+}
+
+
+void loop()
+{
+ delay(1000);
+
+ // set the colors,
+ // if they don't match in order, you may need to use NEO_GRB flag
+ strip.SetPixelColor(0, red);
+ strip.SetPixelColor(1, green);
+ strip.SetPixelColor(2, blue);
+ strip.SetPixelColor(3, white);
+ strip.Show();
+
+ delay(3000);
+
+ // turn off the pixels
+ strip.SetPixelColor(0, black);
+ strip.SetPixelColor(1, black);
+ strip.SetPixelColor(2, black);
+ strip.SetPixelColor(3, black);
+ strip.Show();
+}
+
+