# HG changeset patch # User Dennis Fink # Date 2017-12-11 16:39:55 # Node ID 63573dd833fb834aaf24dd32935d1faaffb49a11 First commit diff --git a/Goggles.ino b/Goggles.ino new file mode 100644 --- /dev/null +++ b/Goggles.ino @@ -0,0 +1,322 @@ +#include +#ifdef __AVR_ATtiny85__ // Trinket, Gemma, etc. +#include +#endif + +#define PIN 0 + +enum pattern { + RAINBOW_CYCLE, + COLOR_WIPE, + DOUBLE_COLOR_WIPE, + SCANNER, + DOUBLE_SCANNER, + RANDOM, + DOUBLE_RANDOM, + BLINK, + DOT +}; + +class NeoPatterns : public Adafruit_NeoPixel { + public: + pattern ActivePattern; + + uint16_t Interval; + unsigned long lastUpdate; + uint32_t Color1; + uint16_t TotalSteps; + uint16_t Index; + + void (*OnComplete)(); + + NeoPatterns(uint16_t pixels, uint8_t pin, uint8_t type, void (*callback)()) : Adafruit_NeoPixel(pixels, pin, type) { + OnComplete = callback; + } + + void Update() { + if ((millis() - lastUpdate) > Interval) { + lastUpdate = millis(); + switch (ActivePattern) { + case RAINBOW_CYCLE: + RainbowCycleUpdate(); + break; + case COLOR_WIPE: + ColorWipeUpdate(); + break; + case DOUBLE_COLOR_WIPE: + DoubleColorWipeUpdate(); + break; + case SCANNER: + ScannerUpdate(); + break; + case DOUBLE_SCANNER: + DoubleScannerUpdate(); + break; + case RANDOM: + RandomUpdate(); + break; + case DOUBLE_RANDOM: + DoubleRandomUpdate(); + break; + case BLINK: + BlinkUpdate(); + break; + case DOT: + DotUpdate(); + break; + default: + break; + } + } + } + + void Increment() { + show(); + Index++; + if (Index >= TotalSteps) { + Index = 0; + OnComplete(); + } + } + + void RainbowCycle(uint16_t interval) { + ActivePattern = RAINBOW_CYCLE; + Interval = interval; + TotalSteps = 255; + Index = 0; + } + + void RainbowCycleUpdate() { + for (int i = 0; i < numPixels(); i++) { + setPixelColor(i, Wheel(((i * 256 / numPixels()) + Index) & 255)); + } + Increment(); + } + + void ColorWipe(uint32_t color, uint16_t interval) { + ActivePattern = COLOR_WIPE; + Interval = interval; + TotalSteps = numPixels(); + Color1 = color; + Index = 0; + } + + void ColorWipeUpdate() { + setPixelColor(Index, Color1); + Increment(); + } + + void DoubleColorWipe(uint32_t color, uint16_t interval) { + ActivePattern = DOUBLE_COLOR_WIPE; + Interval = interval; + TotalSteps = numPixels() / 2; + Color1 = color; + Index = 0; + } + + void DoubleColorWipeUpdate() { + setPixelColor(Index, Color1); + setPixelColor(numPixels() - 1 - Index, Color1); + Increment(); + } + + void Scanner(uint32_t color1, uint16_t interval) { + ActivePattern = SCANNER; + Interval = interval; + TotalSteps = (numPixels() - 1) * 2; + Color1 = color1; + Index = 0; + } + + void ScannerUpdate() { + for (int i = 0; i < numPixels(); i++) { + if (i == Index) { + setPixelColor(i, Color1); + } + else if (i == TotalSteps - Index) { + setPixelColor(i, Color1); + } + else { + setPixelColor(i, DimColor(getPixelColor(i))); + } + } + Increment(); + } + + void DoubleScanner(uint32_t color1, uint16_t interval) { + ActivePattern = DOUBLE_SCANNER; + Interval = interval; + TotalSteps = (numPixels() / 2); + Color1 = color1; + Index = 0; + } + + void DoubleScannerUpdate() { + for (int i = 0; i < numPixels() / 2; i++) { + if (i == Index) { + setPixelColor(i, Color1); // First Eye + setPixelColor(numPixels() - 1 - i, Color1); // Second Eye + } + else { + setPixelColor(i, DimColor(getPixelColor(i))); + setPixelColor(numPixels() - 1 - i, DimColor(getPixelColor(i))); + + } + } + Increment(); + } + + void Random(uint32_t color1, uint16_t steps, uint16_t interval) { + ActivePattern = RANDOM; + Interval = interval; + TotalSteps = steps; + Color1 = color1; + Index = 0; + } + + void RandomUpdate() { + setPixelColor(random(numPixels()), Color1); + Increment(); + } + + void DoubleRandom(uint32_t color1, uint16_t steps, uint16_t interval) { + ActivePattern = DOUBLE_RANDOM; + Interval = interval; + TotalSteps = steps; + Color1 = color1; + Index = 0; + } + + void DoubleRandomUpdate() { + int i = random(numPixels() / 2); + setPixelColor(i, Color1); + setPixelColor(numPixels() - 1 - i, Color1); + Increment(); + } + + void Blink(uint32_t color1, uint16_t steps, uint16_t interval) { + ActivePattern = BLINK; + Interval = interval; + if (steps % 2 != 0) { + steps++; + } + TotalSteps = steps; + Color1 = color1; + Index = 0; + } + + void BlinkUpdate() { + uint32_t c; + if (Index % 2 == 0) { + c = Color1; + } else { + c = Color(0, 0, 0); + } + ColorSet(c); + Increment(); + } + + void Dot(uint32_t color1, uint16_t steps, uint16_t interval) { + ActivePattern = DOT; + Interval = interval; + TotalSteps = steps; + Color1 = color1; + Index = 0; + } + + void DotUpdate() { + ColorSet(Color(0, 0, 0)); + show(); + setPixelColor(random(numPixels()), Color1); + Increment(); + } + + uint32_t DimColor(uint32_t color) { + return Color(((color >> 16) & 0xFF) >> 1, ((color >> 8) & 0xFF) >> 1, (color & 0xFF) >> 1); + } + + uint32_t Wheel(byte WheelPos) { + WheelPos = 255 - WheelPos; + if (WheelPos < 85) { + return Color(255 - WheelPos * 3, 0, WheelPos * 3); + } + else if (WheelPos < 170) { + WheelPos -= 85; + return Color(0, WheelPos * 3, 255 - WheelPos * 3); + } + else { + WheelPos -= 170; + return Color(WheelPos * 3, 255 - WheelPos * 3, 0); + } + } + + void ColorSet(uint32_t color) { + for (int i = 0; i < numPixels(); i++) { + setPixelColor(i, color); + } + } +}; + +void RingsComplete(); + +NeoPatterns Rings(32, PIN, NEO_GRB + NEO_KHZ800, &RingsComplete); +uint8_t mode = 0; +uint32_t prev_time; + +void setup() { +#ifdef __AVR_ATtiny85__ // Trinket, Gemma, etc. + if (F_CPU == 16000000) clock_prescale_set(clock_div_1); +#endif + Rings.begin(); + Rings.setBrightness(64); + Rings.RainbowCycle(random(1, 11)); + prev_time = millis(); +} + +void loop() { + Rings.Update(); + uint32_t t = millis(); + if ((t - prev_time) >= 10000) { + mode = random(0, 9); + prev_time = t; + } +} + +void RingsComplete() +{ + uint16_t slow_interval = random(25, 56); + //uint16_t fast_interval = random(1, 11); + uint32_t color = Rings.Wheel(random(1, 256)); + uint16_t steps = random(5, 11); + switch (mode) { + case 0: + Rings.RainbowCycle(random(1, 11)); + break; + case 1: + Rings.ColorWipe(color, slow_interval); + break; + case 2: + Rings.DoubleColorWipe(color, slow_interval); + break; + case 3: + Rings.Scanner(color, slow_interval); + break; + case 4: + Rings.DoubleScanner(color, slow_interval); + break; + case 5: + Rings.Random(color, steps, slow_interval); + break; + case 6: + Rings.DoubleRandom(color, steps, slow_interval); + break; + case 7: + Rings.Blink(color, steps, random(250, 501)); + break; + case 8: + Rings.Dot(color, steps, slow_interval); + break; + default: + break; + } +}