How many leds can a arduino uno control?

Trying to program led for stairs using two IR motion sensors, ws2812b(10m) and Arduino Uno. I got 10m WS2812B strip = 600 leds in total, I can't go beyond '548 leds' => Adafruit_NeoPixel strip = Adafruit_NeoPixel(548, PIN, NEO_GRB + NEO_KHZ800); . I need to control 600 leds please help.

Try a device with more RAM?

1 Like

For that kind of smart LED you def need memory that is proportional to the number of LEDs.

And for any kind of serially addressed LEDs you will need time that is proportional to the number of LEDs.

Obvsly you can run out of memory. Time may not be important, but if you looking to do any whizzy animated effects, the frame rate you can attain may be the limit you run into.

Adafruit and elsewhere can help you calculate the time needed to “show” a new strip buffer to the physical strip.

For APA smart LEDs, which run off data and clock lines, you can work with no buffer at all. Time to publish a new strip of colors may still be an issue.

a7

1 Like

Try the FAB_LED library.

3 Likes

@flashko Nice!

If you can figure out the data fast enough, the same benefit of the APA LEDs.

Would only get better with a faster processor.

APA data and clock can go as slow as you need, of course nothing dynamical is gonna look very good but you are able to control unlimited LEDs.

It will be interesting to look further at this and raise challenges for what can be accomplish with the time available.

a7

1 Like

There a good chance @billava07 will always have all the LEDs on a single stair step as the same colour/brightness. If so, there are probably only 10~20 groups of LEDs, and, using that FAB_LED library, only a fraction of the ram memory will be required compared to FastLED/NeoPixel.

1 Like

I suspect that your problem is RAM.
I have a Christmas decoration with 600 WS2812 LEDS using a Wemos D1 Mini.

1 Like

And a level converter such as a 74HCT14 I should hope! :face_with_raised_eyebrow:

Can you please help me with two sensor and lighting code? When I pass ground sensor the leds must start from ground and end at top, also they need to fade from ground to top after say 3 seconds. If no motion is detected then play breathing effect.

Currently I'm using below code

  #include <Adafruit_NeoPixel.h>

#define PIN 6
Adafruit_NeoPixel strip = Adafruit_NeoPixel(548, PIN, NEO_GRB + NEO_KHZ800);

 unsigned long timeOut=60000; // timestamp to remember when the PIR was triggered.
 int downUp = 0;              // variable to rememer the direction of travel up or down the stairs
 int alarmPinTop = 10;        // PIR at the top of the stairs
 int alarmPinBottom =11;      // PIR at the bottom of the stairs
 int alarmValueTop = HIGH;    // Variable to hold the PIR status
 int alarmValueBottom = HIGH; // Variable to hold the PIR status
 int ledPin = 13;           // LED on the arduino board flashes when PIR activated
 int change = 1;            // used in 'breathing' the LED's
 int breathe = 0;           // used in 'breathing' the LED's
 int colourArray[350];  
 

void setup() {
   strip.begin();
   strip.show(); // Initialize all pixels to 'off'
   Serial.begin (9600);  // only requred for debugging
   pinMode(ledPin, OUTPUT);  // initilise the onboard pin 13 LED as an indicator
   pinMode(alarmPinTop, INPUT_PULLUP);     // for PIR at top of stairs initialise the input pin and use the internal restistor
   pinMode(alarmPinBottom, INPUT_PULLUP);  // for PIR at bottom of stairs initialise the input pin and use the internal restistor
   delay (2000); // it takes the sensor 2 seconds to scan the area around it before it can 
   //detect infrared presence.
   for (int i=0 ;i < 350; i++)  { // initilise the colourArray to zero
   colourArray[i]=0; 
   } 
}

void loop() {
  
  if (timeOut+12000 < millis()) {        // idle state - 'breathe' the top and bottom LED to show program is looping
    
     breathe = breathe + change;
     for(int i = 0; i<=600; i++){
      strip.setPixelColor(i,0,0,breathe);
      }
     strip.show();
     if (breathe == 100 || breathe == 0) change = -change;      // breathe the LED from 0 = off to 100 = fairly bright
     if (breathe == 100 || breathe == 0) delay (250);           // Pause at beginning and end of each breath
     delay(25); 
  }
  
    alarmValueTop = digitalRead(alarmPinTop);        // Constantly poll the PIR at the top of the stairs
    alarmValueBottom = digitalRead(alarmPinBottom);  // Constantly poll the PIR at the bottom of the stairs
    
     if (alarmValueTop == HIGH && downUp != 2)  {      // the 2nd term allows timeOut to be contantly reset if one lingers at the top of the stairs before decending but will not allow the bottom PIR to reset timeOut as you decend past it.
      timeOut=millis();  // Timestamp when the PIR is triggered.  The LED cycle wil then start.
      downUp = 1;
      topdown();         // lights up the strip from top down
    }
 
    if (alarmValueBottom == HIGH && downUp != 1)  {    // the 2nd term allows timeOut to be contantly reset if one lingers at the bottom of the stairs before decending but will not allow the top PIR to reset timeOut as you decend past it.
      timeOut=millis();    // Timestamp when the PIR is triggered.  The LED cycle wil then start.
      downUp = 2;
      bottomup();         // lights up the strip from bottom up
    }
    if (timeOut+10000 < millis() && timeOut+11999 < millis()) {    //switch off LED's in the direction of travel.
       if (downUp == 1) {
          colourWipeDown(strip.Color(0, 0, 0), 40); // Off
       }
       if (downUp == 2)  {
        colourWipeUp(strip.Color(0, 0, 0), 40);   // Off
       }
      downUp = 0;
      //   for (int i=0 ;i < 350; i++)  {          // Depending on your preference you may want to include this loop to clear out the colourArray
      //    colourArray[i]=0; 
      // }
    }
   
}

 void topdown() {
    Serial.println ("detected top");                // Helpful debug message
    colourWipeDown(strip.Color(130, 100, 30), 40);    // Warm White
    for(int i=0; i<3; i++) {                        // Helpful debug indication flashes led on Arduino board twice
      digitalWrite(ledPin,HIGH);
      delay(200);
      digitalWrite(ledPin,LOW);
      delay(200);
    }
 }

 void bottomup() {
    Serial.println ("detected bottom");          // Helpful debug message
    colourWipeUp(strip.Color(130, 100, 30), 40);   // Warm White
    for(int i=0; i<3; i++) {                     // Helpful debug indication flashes led on Arduino board twice
      digitalWrite(ledPin,HIGH);
      delay(200);
      digitalWrite(ledPin,LOW);
      delay(200);
    }
  }

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

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

What is this array for? It is consuming an extra 700 bytes of precious ram memory, but I can't see it being used anywhere.

 int colourArray[350];      // An array to hold RGB values

That was for waterfall effect, I removed it while posting it over here.

I use a 74LS244. I know, not the best level converter chip, but I have several tubes of them in my kit. And they work.

What's the use of level converter?

Converting logic levels from the low voltage Wemos ESP to the 5V logic required by the LEDs

It may work just as well without them. Have you ever looked at the levels they actually generate?

What I've found in my experiments.. Yes, the ESP will drive the WS2812 LED without a level driver. But, the wire length to the first LED has to be pretty short. Once you get the first LED to function, it conditions the data line for the next LED in the string. What I did in one project was to sacrifice one LED (I was using strings, so cutting one off was easy). The sacrifice LED was on the perfboard next to the ESP, and the the rest of the LEDs in the string worked just fine.

All 600 leds work in simple programs and not in my current program.

Did those simple programs include 600 LEDs and the waterfall effect that needs that array of 350 int?

If you didn't have this loop, the compiler would probably optimise the array away (and anyway, the loop is unnecessary - assuming you have enough RAM, the array was already zeroed)

1 Like

Simple. You are running out of RAM. Don't use the Uno. Use something with more RAM. I am surprised that you don't get a warning of low ram from the compiler. In settings (in the IDE) set compiler warnings to "all". (Personally, I think that should be the default).