Goto Loop gets ignored sometimes

I am having some issues with a goto loop. In my code I have a startup portion and then waits for a high signal. Once the High signal is applied it hold until it is removed. This is where my problem is. About half the time the goto goes back to the middle of the code and holds unit the next high signal. The other half of the time it goes back to the beginning of the code and starts at the very beginning again. No matter how much debounce I add it doesn't seem to matter. I've also tried moving the goto command but that doesn't seem to help either. My code is below. Any help would be gladly appreciated.

#include <FastLED.h>

#define NUM_LEDS 112
#define DATA_PIN 13
const int buttonPin = 2;
int buttonState = 0;      // Current state of the button
bool lastButtonState = false;  // Previous state of the button
bool loopStarted = false;      // Whether the loop has started

CRGB leds[NUM_LEDS];

void setup() {
  FastLED.addLeds<WS2812, DATA_PIN, RGB>(leds, NUM_LEDS);
  pinMode(buttonPin, INPUT);  // Set the button pin as input with internal pull-up
}

void fadeall() {
  for (int i = 0; i < NUM_LEDS; i++) { leds[i].nscale8(200); }  // nscale is comet length (Small number - shorter tail)
}


void loop() {

  // Turn all LEDs off
  FastLED.clear();
  FastLED.show();


    // First loop: LED pattern fills outward from end
    int halfWay = NUM_LEDS / 2;  // cuts strip in half
     for (int i = halfWay - 1; i >= 0; i--) {


      leds[halfWay + i] = CRGB(70, 254, 0);
      leds[halfWay - i] = CRGB(70, 254, 0);

      FastLED.setBrightness(120);
      FastLED.show();
      fadeall();  //remove for fill sweep.  Also change speed of fill to 30
      delay(20);  // Speed of fill (50)
    }

     
    // Second loop: LED comet spreads out
    for (int i = 0; i <= halfWay; i++) {


      leds[halfWay + i] = CRGB(90, 254, 0);
      leds[halfWay - i] = CRGB(90, 254, 0);

      FastLED.setBrightness(120);
      FastLED.show();
      fadeall();
      delay(20);   // Speed of fill (50)
    }

    // Third loop: LED comet returns to the center
    for (int i = halfWay - 1; i >= 0; i--) {

      leds[halfWay + i] = CRGB(70, 254, 0);
      leds[halfWay - i] = CRGB(70, 254, 0);

      FastLED.show();
      fadeall();
      delay(20);   // Speed of fill (50)
    }
    // Turn off all LEDs
    for (int i = 0; i < NUM_LEDS; i++) {
      leds[i] = CRGB(0, 0, 0);
    }
    FastLED.show();
    delay(100);

checkAgain: 

    while (digitalRead(buttonPin) == LOW) {
      delay(500);  // Debounce delay to avoid multiple triggers
  
  // Do nothing
   }

  // Read the current state of the button -------------------------------------
  buttonState = digitalRead(buttonPin);  // Button pressed when HIGH

    // Check if the button was just pressed (edge detection)
  if (buttonState && !lastButtonState) {
    loopStarted = !loopStarted;  // Toggle the state of the loop
        delay(100);  // Debounce delay to avoid multiple triggers
  }
  // Store the current button state for the next loop iteration
  lastButtonState = buttonState;

  // If the loop is started, do something   
  if (loopStarted) {

     // Clear all LEDs 
    FastLED.clear();
    FastLED.show();
    delay(100);

    // Set LED 16 through 21, 52 through 58, 92 through 97 at brightness 255 (4 LEDS ON)
    for (int i = 14; i <= 19; i++) {
      leds[i] = CRGB(70, 254, 0);
    }
    for (int i = 52; i <= 58; i++) {
      leds[i] = CRGB(70, 254, 0);
    }
    for (int i = 92; i <= 97; i++) {
      leds[i] = CRGB(70, 254, 0);
    }
    FastLED.setBrightness(255);
    FastLED.show();
    delay(500);



// Hold until power removed
    while (digitalRead(buttonPin) == HIGH) {
      // do nothing

// Read the current state of the button -------------------------------------
  buttonState = digitalRead(buttonPin);  // Button pressed when HIGH

      if (digitalRead(buttonPin) == LOW) {
        FastLED.clear();       // Clear the LEDs
        FastLED.show();        // Update the LED state
        delay(1000);           // Debounce delay
      
goto checkAgain;
      }
    } 
  }    
}

Forum members call that approach "spaghetti code", because it is so difficult to follow and understand.

There is almost never a good reason to use goto statements, so if you can think of a way to remove it and use instead clear, simple logical constructions, your program will probably work as you expect.

Keep in mind that the loop function loops, so there is rarely a need to use while() as well.

1 Like

@rbreak7
Your code is the mess. It is very difficult to read and understand it.

Leaving aside the using the goto, your code has another drawback.
React to the button is almost impossible if the code has as much delays as your code. The code has to be rewritten completely. See the example "blink without delay" in the IDE.

Thank you for the advice. I will look into the blink without delay.