Gemma Neopixel Sound reactive patterns

Hello all! im looking for advice on coding a Gemma with a 16 neopixel ring and microphone. I end goal is to have a pair of googles that are able to perform neopixel library patterns as well as have the brightness reactive to sound. I want the patterns to cycle through and loop like this code;

#include <Adafruit_NeoPixel.h>

#define PIN 0

Adafruit_NeoPixel strip = Adafruit_NeoPixel(16, PIN, NEO_GRB + NEO_KHZ800);


void setup() {
  pinMode(1, INPUT);
  digitalWrite(1, HIGH); // connect internal pull-up
  strip.begin();
  strip.show(); // Initialize all pixels to 'off'
}

int counter = 1;


void loop() {
  if (digitalRead(1) == LOW && counter < 6)
  {
    counter++;
    if (counter == 6) {
      counter = 1;
    }

  }

  // Some example procedures showing how to display to the pixels:
  colorWipe(strip.Color(255, 0, 0), 50); // Red
  colorWipe(strip.Color(0, 255, 0), 50); // Green
  colorWipe(strip.Color(0, 0, 255), 50); // Blue
  // Send a theater pixel chase in...
  theaterChase(strip.Color(127, 127, 127), 50); // White
  theaterChase(strip.Color(200,   0,   0), 50); // Red
  theaterChase(strip.Color(200,   0,   200), 50);
  theaterChase(strip.Color(  0,   0, 200), 50); // Blue

  rainbow(20);
  rainbowCycle(20);
  theaterChaseRainbow(30);

}


// Fill the dots one after the other with a color
void colorWipe(uint32_t c, uint8_t wait) {
  if (counter == 1) {
    for (uint16_t i = 0; i < strip.numPixels(); i++) {
      strip.setPixelColor(i, c);
      strip.show();
      delay(wait);
    }
  }
}

void rainbow(uint8_t wait) {
  if (counter == 2) {
    uint16_t i, j;

    for (j = 0; j < 256; j++) {
      for (i = 0; i < strip.numPixels(); i++) {
        strip.setPixelColor(i, Wheel((i + j) & 255));
      }
      strip.show();
      delay(wait);
    }
  }
}

// Slightly different, this makes the rainbow equally distributed throughout
void rainbowCycle(uint8_t wait) {
  if (counter == 3) {
    uint16_t i, j;

    for (j = 0; j < 256 * 5; j++) { // 5 cycles of all colors on wheel
      for (i = 0; i < strip.numPixels(); i++) {
        strip.setPixelColor(i, Wheel(((i * 256 / strip.numPixels()) + j) & 255));
      }
      strip.show();
      //delay(wait);
    }
  }
}

//Theatre-style crawling lights.
void theaterChase(uint32_t c, uint8_t wait) {
  if (counter == 4) {
    for (int j = 0; j < 10; j++) { //do 10 cycles of chasing
      for (int q = 0; q < 2; q++) {
        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, c);  //turn every second pixel on
        }
        strip.show();

        delay(wait);

        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, 0);      //turn every second pixel off
        }
      }
    }
  }
}

//Theatre-style crawling lights with rainbow effect
void theaterChaseRainbow(uint8_t wait) {
  if (counter == 5) {
    for (int j = 0; j < 256; j++) {   // cycle all 256 colors in the wheel
      for (int q = 0; q < 2; q++) {
        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, Wheel( (i + j) % 255)); //turn every second pixel on
        }
        strip.show();

        delay(wait);
        delay(wait);
        delay(wait);
        delay(wait);

        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, 0);      //turn every second pixel off
        }
      }
    }
  }
}

// Input a value 0 to 255 to get a color value.
// The colours are a transition r - g - b - back to r.
uint32_t Wheel(byte WheelPos) {
  if (WheelPos < 85) {
    return strip.Color(WheelPos * 3, 255 - WheelPos * 3, 0);
  }
  else if (WheelPos < 170) {
    WheelPos -= 85;
    return strip.Color(255 - WheelPos * 3, 0, WheelPos * 3);
  }
  else {
    WheelPos -= 170;
    return strip.Color(0, WheelPos * 3, 255 - WheelPos * 3);
  }
}

but have the brightness fade to from 255-0 from output of the microphone

I bet the original code was not in italics. This would not happen if the code was properly posted in code tags.

To post code and/or error messages:

  1. Use CTRL-T in the Arduino IDE to autoformat your complete code.
  2. Paste the complete autoformatted code between code tags (the </> button)
    so that we can easily see and deal with your code.
  3. Paste the complete error message between code tags (the </> button)
    so that we can easily see and deal with your messages.
  4. If you already posted without code tags, you may add the code tags by
    editing your post. Do not change your existing posts in any other way.
    You may make additional posts as needed.

Before posting again, you should read the three locked topics at the top of the Programming Questions forum, and any links to which these posts point.

If your project involves wiring, please provide a schematic and/or a wiring diagram and/or a clear photograph of the wiring.

Good Luck!

here is the wiring schematic for my sketch, sorry i had to draw it out

end goal is to have a pair of googles

A pair of googles? Isn't one google enough? Are they going to compete or cooperate?

I do not understand why you define pin 1 as INPUT, turn on the internal pullup resistor, and then read from pin 4.

I do not see where you read anything from the pin that the microphone is connected to. I don't see where you do anything with the value that you don't read, to influence brightness.

I hope you understand that the value that you read from the analog pin that the microphone is connected to will NOT tell you the volume.

Yes you read correctly, a pair of goggles, one pair for myself and one for my partner both utilizing the same pattern. sorry that sketch i posted was the same one i used on my UNO that toggled between patterns using a push button momentary switch.

googles != goggles

PaulS read correctly but addobson90 did not.

I still have not seen the correct code or an explanation of why pin 1 versus pin 4.

I still have not seen any response to the other comments that PaulS made.

Well heres the code so far, thanks for your patience as i am very new to all of this. the issue im having with this is the brightness isn’t updating to the mic output, any thoughts?

#include <Adafruit_NeoPixel.h>

#define N_PIXELS  16  // Number of pixels you are using
#define MIC_PIN   A1  // Microphone is attached to Trinket GPIO #2/Gemma D2 (A1)
#define LED_PIN    0  // NeoPixel LED strand is connected to GPIO #0 / D0
#define DC_OFFSET  0  // DC offset in mic signal - if unusure, leave 0
#define NOISE     100  // Noise/hum/interference in mic signal
#define SAMPLES   60  // Length of buffer for dynamic level adjustment
#define TOP       (N_PIXELS +1) // Allow dot to go slightly off scale

byte
peak      = 0,      // Used for falling dot
dotCount  = 0,      // Frame counter for delaying dot-falling speed
volCount  = 0;      // Frame counter for storing past volume data

int
vol[SAMPLES],       // Collection of prior volume samples
    lvl       = 10,     // Current "dampened" audio level
    minLvlAvg = 0,      // For dynamic adjustment of graph low & high
    maxLvlAvg = 512;

Adafruit_NeoPixel strip = Adafruit_NeoPixel(16, LED_PIN, NEO_GRB + NEO_KHZ800);


void setup() {
  memset(vol, 0, sizeof(int)*SAMPLES);
  strip.begin();
  strip.show(); // Initialize all pixels to 'off'
}

int counter = 1;


void loop() {

  uint8_t  i;
  uint16_t minLvl, maxLvl;
  int      n, height;
  n   = analogRead(MIC_PIN);                 // Raw reading from mic
  n   = abs(n - 512 - DC_OFFSET);            // Center on zero
  n   = (n <= NOISE) ? 0 : (n - NOISE);      // Remove noise/hum
  lvl = ((lvl * 7) + n) >> 3;    // "Dampened" reading (else looks twitchy)

  // Calculate bar height based on dynamic min/max levels (fixed point):
  height = TOP * (lvl - minLvlAvg) / (long)(maxLvlAvg - minLvlAvg);

  if (height < 0L)       height = 0;     // Clip output
  else if (height > TOP) height = TOP;
  if (height > peak)     peak   = height; // Keep 'peak' dot at top

  // if POT_PIN is defined, we have a potentiometer on GPIO #3 on a Trinket
  //    (Gemma doesn't have this pin)
  uint8_t bright = 255;
#ifdef MIC_PIN
  bright = analogRead(MIC_PIN);  // Read pin (0-255) (adjust potentiometer
  //   to give 0 to Vcc volts
#endif
  strip.setBrightness(bright);    // Set LED brightness (if POT_PIN at top
  //  define commented out, will be full)
  // Color pixels based on rainbow gradient
  for (i = 0; i < N_PIXELS; i++) {
    if (i >= height)
      strip.setPixelColor(i,   0,   0, 0);
    else
      strip.setPixelColor(i, (map(i, 0, strip.numPixels() - 1, 30, 150)));
  }

  strip.show(); // Update strip

  vol[volCount] = n;                      // Save sample for dynamic leveling
  if (++volCount >= SAMPLES) volCount = 0; // Advance/rollover sample counter

  // Get volume range of prior frames
  minLvl = maxLvl = vol[0];
  for (i = 1; i < SAMPLES; i++) {
    if (vol[i] < minLvl)      minLvl = vol[i];
    else if (vol[i] > maxLvl) maxLvl = vol[i];
  }
  // minLvl and maxLvl indicate the volume range over prior frames, used
  // for vertically scaling the output graph (so it looks interesting
  // regardless of volume level).  If they're too close together though
  // (e.g. at very low volume levels) the graph becomes super coarse
  // and 'jumpy'...so keep some minimum distance between them (this
  // also lets the graph go to zero when no sound is playing):
  if ((maxLvl - minLvl) < TOP) maxLvl = minLvl + TOP;
  minLvlAvg = (minLvlAvg * 63 + minLvl) >> 6; // Dampen min/max levels
  maxLvlAvg = (maxLvlAvg * 63 + maxLvl) >> 6; // (fake rolling average)


{
  counter++;
  if (counter == 6) {
    counter = 1;
  }

}

// Some example procedures showing how to display to the pixels:
colorWipe(strip.Color(255, 0, 0), 50); // Red
colorWipe(strip.Color(0, 255, 0), 50); // Green
colorWipe(strip.Color(0, 0, 255), 50); // Blue
// Send a theater pixel chase in...
theaterChase(strip.Color(127, 127, 127), 50); // White
theaterChase(strip.Color(200,   0,   0), 50); // Red
theaterChase(strip.Color(200,   0,   200), 50);
theaterChase(strip.Color(  0,   0, 200), 50); // Blue

rainbow(20);
rainbowCycle(20);
theaterChaseRainbow(30);

}


// Fill the dots one after the other with a color
void colorWipe(uint32_t c, uint8_t wait) {
  if (counter == 1) {
    for (uint16_t i = 0; i < strip.numPixels(); i++) {
      strip.setPixelColor(i, c);
      strip.show();
      delay(wait);
    }
  }
}

void rainbow(uint8_t wait) {
  if (counter == 2) {
    uint16_t i, j;

    for (j = 0; j < 256; j++) {
      for (i = 0; i < strip.numPixels(); i++) {
        strip.setPixelColor(i, Wheel((i + j) & 255));
      }
      strip.show();
      delay(wait);
    }
  }
}

// Slightly different, this makes the rainbow equally distributed throughout
void rainbowCycle(uint8_t wait) {
  if (counter == 3) {
    uint16_t i, j;

    for (j = 0; j < 256 * 5; j++) { // 5 cycles of all colors on wheel
      for (i = 0; i < strip.numPixels(); i++) {
        strip.setPixelColor(i, Wheel(((i * 256 / strip.numPixels()) + j) & 255));
      }
      strip.show();
      //delay(wait);
    }
  }
}

//Theatre-style crawling lights.
void theaterChase(uint32_t c, uint8_t wait) {
  if (counter == 4) {
    for (int j = 0; j < 10; j++) { //do 10 cycles of chasing
      for (int q = 0; q < 2; q++) {
        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, c);  //turn every second pixel on
        }
        strip.show();

        delay(wait);

        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, 0);      //turn every second pixel off
        }
      }
    }
  }
}

//Theatre-style crawling lights with rainbow effect
void theaterChaseRainbow(uint8_t wait) {
  if (counter == 5) {
    for (int j = 0; j < 256; j++) {   // cycle all 256 colors in the wheel
      for (int q = 0; q < 2; q++) {
        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, Wheel( (i + j) % 255)); //turn every second pixel on
        }
        strip.show();

        delay(wait);
        delay(wait);
        delay(wait);
        delay(wait);

        for (int i = 0; i < strip.numPixels(); i = i + 2) {
          strip.setPixelColor(i + q, 0);      //turn every second pixel off
        }
      }
    }
  }
}

// Input a value 0 to 255 to get a color value.
// The colours are a transition r - g - b - back to r.
uint32_t Wheel(byte WheelPos) {
  if (WheelPos < 85) {
    return strip.Color(WheelPos * 3, 255 - WheelPos * 3, 0);
  }
  else if (WheelPos < 170) {
    WheelPos -= 85;
    return strip.Color(255 - WheelPos * 3, 0, WheelPos * 3);
  }
  else {
    WheelPos -= 170;
    return strip.Color(0, WheelPos * 3, 255 - WheelPos * 3);
  }
}

I'm not seeing the part where you do the Serial.begin(9600); then you have outputs to the monitor to see what's going on in there. Have you looked at the raw volume values? Have you looked at what they are after thy've been dragged through all this.. refinement?

Sigh..

Divide an conquer is the name of the game here. Show us and yourself the bits that work.

-jim lee