NeoPixels: Sketch funktioniert leider nicht

Hallo zusammen,

leider klappt es mit dem unten angegebenen Scatch nicht wie gewünscht.

Konkret bedeutet es, dass er im ersten if noch auf Bewegung colorWipeUP durchläuft, danach tut sich leider nichts mehr. :frowning:

Hab schon erdenklich Varianten durchgespielt, aber keine Lösung gefunden.

Bin für jede Art von Hilfe dankbar!

Viele Grüße!

#include <Adafruit_NeoPixel.h>

Adafruit_NeoPixel strip = Adafruit_NeoPixel(150, 13, NEO_GRB + NEO_KHZ800);

int motionPin = 8;
int senseMotion = 0;

void setup() {
  pinMode(motionPin, INPUT);
  strip.begin();
  strip.show();
}
  
void loop() {
  
  senseMotion = digitalRead (motionPin);

  if (senseMotion == HIGH) {
    colorWipeUP(strip.Color(255, 0, 0), 50);
    strip.show();
    rainbowCycle(20);
  }
  else {
     digitalWrite (motionPin, LOW); 
     colorWipe(strip.Color(0, 0, 0), 20);    
     strip.show();
   }   
}
   
void rainbowCycle(uint8_t wait) {
  uint16_t i, j;

  for(j=0; j<256*2; 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(20);
  }
}   

void colorWipe(uint32_t c, uint8_t wait) {
  for(uint16_t i=0; i<strip.numPixels(); i++) {
    strip.setPixelColor(i, c);
    strip.show();
    delay(20);
  }
}

void colorWipeUP(uint32_t c, uint8_t wait) {
  for(uint16_t i=strip.numPixels()-1; i >= 0; i--) {
    strip.setPixelColor(i, c);
    strip.show();
    delay(20);
  }
}

uint32_t Wheel(byte WheelPos) {
  WheelPos = 255 - WheelPos;
  if(WheelPos < 85) {
    return strip.Color(255 - WheelPos * 3, 0, WheelPos * 3);
  }
  if(WheelPos < 170) {
    WheelPos -= 85;
    return strip.Color(0, WheelPos * 3, 255 - WheelPos * 3);
  }
  WheelPos -= 170;
  return strip.Color(WheelPos * 3, 255 - WheelPos * 3, 0);
}

Fehlt senseMotion nicht im Setup-teil als OUT-oder INPUT??

challenger:
Fehlt senseMotion nicht im Setup-teil als OUT-oder INPUT??

Nein, das ist eine Variable, die wurde zuvor als int definiert.

Zabsi:

void setup() {

pinMode(motionPin, INPUT);
}
 
void loop() {
    digitalWrite(motionPin, LOW);

}

Man kann auf einen Eingang schreiben? verwirrt bin

Moko:
Man kann auf einen Eingang schreiben? verwirrt bin

Ok, dass könnte in der Tat problematisch sein!

Das Problem ist ja aber, dass die if-Funktion soweit funktioniert. Auf Bewegung wird WipeUP durchlaufen, nur geht er danach nicht in den Regenbogen...

Erstmal aber vielen Dank für eure Antworten!

Zabsi:
Ok, dass könnte in der Tat problematisch sein!

Das Problem ist ja aber, dass die if-Funktion soweit funktioniert. Auf Bewegung wird WipeUP durchlaufen, nur geht er danach nicht in den Regenbogen...

Funktioniert der Regenbogen denn einzeln, also ohne vorherige WipeUp ?

HotSystems:
Funktioniert der Regenbogen denn einzeln, also ohne vorherige WipeUp ?

Ja, leider schon...

VG!

Ich habe leider zu wenig Erfahrung mit Neopixel, vermute aber, dass die Bewegung am Sensor schon wieder weg ist, wenn er eigentlich in den Regenbogen springen soll.

HotSystems:
Ich habe leider zu wenig Erfahrung mit Neopixel, vermute aber, dass die Bewegung am Sensor schon wieder weg ist, wenn er eigentlich in den Regenbogen springen soll.

Das ist spannend!

Habe die Dauer, in der der PIR sein Signal ausgibt, auf minimal eingestellt. Da werde ich nachher mal versuchen, dass er ein wenig länger läuft, also INPUT ein wenig länger liegt. Klingt erstmal sehr einleuchtend...

Danke!

Hauptproblem: Blockierende Programmierung mit for und delay macht den µC blind für den Eingang. (Die Beispiele eignen sich nicht immer zur direkten Integration in Projekte.)

Umgehung: Innerhalb der Schleife mittels digitalRead ein Flag setzen und außerhalb auswerten. Damit wird das Eingangssifnal praktisch "verlängert".

Lösung: Auf nicht blockierende Programmierung mit millis umsteigen. (Der schwierigere aber lohnende Weg.)

Hallo nochmal und vielen Dank für die bisherigen Antworten!

Ich habe das Ganze jetzt auf millis() umgestellt. Soweit funktioniert jetzt auch alles...

ABER: Sobald ich in der loop von colorWipe auf colorWipeUP umstelle, läuft eben nur einmal colorWipeUP und danach passiert nichts mehr.

Mit colorWipeUP soll eigentlich der Streifen nur rückwärts durchlaufen. Ich habe absolut keine Ahnung, welche Teil da problematisch ist.

Somit wieder für jede Hilfe dankbar!

#include <Adafruit_NeoPixel.h>

Adafruit_NeoPixel strip = Adafruit_NeoPixel(150, 8, NEO_GRB + NEO_KHZ800);

int calibrationTime = 10;         

long unsigned int lowIn;         
long unsigned int pause = 5000;  

boolean lockLow = true;
boolean takeLowTime;  

int pirPin = 7;
int ledPin = 8; 

void setup(){
  strip.begin();
  strip.show();
  pinMode(pirPin, INPUT);
  pinMode(ledPin, OUTPUT);
  digitalWrite(pirPin, LOW);
  
  for(int i = 0; i < calibrationTime; i++){
    delay(1000);
  }
}

void loop() {
  if(digitalRead(pirPin) == HIGH){
    digitalWrite(ledPin, HIGH);
    colorWipe(strip.Color(255, 0, 0), 50);
    rainbowCycle(20);
    delay(100);
    
  if(lockLow){
    lockLow = false;
    }
    takeLowTime = true;
  }

  if(digitalRead(pirPin) == LOW){
    digitalWrite(ledPin, LOW);
    
  if(takeLowTime){
    colorWipe(strip.Color(0, 0, 0), 20);
    lowIn = millis();
    takeLowTime = false;
  }
        
       if(!lockLow && millis() - lowIn > pause){
           lockLow = true;                        
           }
       }
  }

void rainbowCycle(uint8_t wait) {
  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);
  }
}   

void colorWipe(uint32_t c, uint8_t wait) {
  for(uint16_t i=0; i<strip.numPixels(); i++) {
    strip.setPixelColor(i, c);
    strip.show();
    delay(wait);
  }
}

void colorWipeUP(uint32_t c, uint8_t wait) {
  for(uint16_t i=strip.numPixels()-1; i >= 0; i--) {
    strip.setPixelColor(i, c);
    strip.show();
    delay(wait);
  }
}

uint32_t Wheel(byte WheelPos) {
  WheelPos = 255 - WheelPos;
  if(WheelPos < 85) {
    return strip.Color(255 - WheelPos * 3, 0, WheelPos * 3);
  }
  if(WheelPos < 170) {
    WheelPos -= 85;
    return strip.Color(0, WheelPos * 3, 255 - WheelPos * 3);
  }
  WheelPos -= 170;
  return strip.Color(WheelPos * 3, 255 - WheelPos * 3, 0);
}

Zabsi:
Ich habe das Ganze jetzt auf millis() umgestellt.

Das sehe ich nicht so:

delay(wait);

Das sind beispielsweise bei colorWipe 3 Sekunden Blockade!

agmue:
Das sind beispielsweise bei colorWipe 3 Sekunden Blockade!

Ok, aber was ich nicht verstehe ist, dass es bei colorWipe damit keine Probleme gibt. Der Sketch läuft vorgesehen durch. Sobald aber colorWipeUP an Stelle von colorWipe gesetzt wird, läuft nur colorWipeUP und dann bleibt er stehen.

Eigentlich ist doch nur die Zählung der LEDs anders. Wie sollte sich da das delay auswirken und bei dem anderne nicht?

Soll keine Argument dafür sein, dass es unsauber ist!!! Da werde ich nochmal nacharbeiten müssen.