loop switching using interrupts

I am using two accelerometers(ADXL335) outputs to execute two led loops namely left and right.I am using compare match interrupt to generate flag for each 10 sensor outputs and led’s are made high sequentially.I have a problem when i use left accelerometer and led’s start blinking for a set time and if i stop the left accelerometer and use the right accelerometer the left led’s should stop in the middle of loop and the right led’s should start. it’s not happening.please help.

#include <avr/io.h>
#include <avr/interrupt.h>
// these constants describe the pins. They won't change:
//const int groundpin = 18;             // analog input pin 4 -- ground
//const int powerpin = 19;              // analog input pin 5 -- voltage
//const int xpin = A3;                  // x-axis of the accelerometer
const int ypin = A2;                  // y-axis
const int ypin1 = A3;
//const int zpin = A1;                  // z-axis (only on 3-axis models)
float a = 0;
float b = 0;
int flag;
int flag1;

void setup() {
  // initialize the serial communications:
  Serial.begin(115200);

  // Provide ground and power by using the analog inputs as normal
  // digital pins.  This makes it possible to directly connect the
  // breakout board to the Arduino.  If you use the normal 5V and
  // GND pins on the Arduino, you can remove these lines.
  //pinMode(groundpin, OUTPUT);
  //pinMode(powerpin, OUTPUT);
  int k;
  for (k = 3; k < 11; k++)
  {
    pinMode(k, OUTPUT);
  }
  // digitalWrite(groundpin, LOW);
  // digitalWrite(powerpin, HIGH);
  // initialize Timer1
  cli();          // disable global interrupts
  TCCR1A = 0;     // set entire TCCR1A register to 0
  TCCR1B = 0;     // same for TCCR1B

  // set compare match register to desired timer count:
  OCR1A = 15624/5;
  // turn on CTC mode:
  TCCR1B |= (1 << WGM12);
  // Set CS10 and CS12 bits for 1024 prescaler:
  TCCR1B |= (1 << CS10);
  TCCR1B |= (1 << CS12);
  // enable timer compare interrupt:
  TIMSK1 |= (1 << OCIE1A);
  sei();          // enable global interrupts


}

void loop()
{

  // int z = analogRead(zpin) - 350;
  // z = (z * 9.8) / 75;
  float y = analogRead(ypin) - 350;
  y = (y * 9.8) / 75;
  float y1 = analogRead(ypin1) - 350;
  y1 = (y1 * 9.8) / 75;
  // print the sensor values:
  // Serial.print(analogRead(xpin));
  // print a tab between values:
  //Serial.print("\t");
  //Serial.print(analogRead(ypin));
  // print a tab between values:
  Serial.print(y);
  Serial.print("\t");
  Serial.print((y1));
  Serial.print("\t");
  Serial.print("\n");
  a = y1;
  b = y;
  

  righton();
  lefton();


  //Serial.println();
  // delay before next reading:
  // delay(30);
}



void gesture()
{
  int i = 0;
  int count = 0;

  for (i = 0; i < 10; i++)
  {
    if (b < -2.5)
      count = count + 1;
    else
      count = count;


  }
  if (count == 10)
  {
    flag = 0;
  }
  else
    flag = 1;
}


void gesture2()
{
  int i = 0;

  int count1 = 0;

  for (i = 0; i < 10; i++)
  {
    if (a < -2.5)
      count1 = count1 + 1;
    else
      count1 = count1;


  }
  if (count1 == 10)
  {
    flag1 = 0;
  }
  else
    flag1 = 1;
}

ISR(TIMER1_COMPA_vect)
{
  gesture();
  gesture2();
  loop();
}





void lefton()
{
  if (flag == 0 && flag1==1)
  {
    int j = 3;
    int i = 0;
    for(i=0;i<10;i++)
    {
    for (j = 3; j < 6; j++)
    {
      digitalWrite(j, HIGH);
      delay(50);
      digitalWrite(j, LOW);
      delay(50);
    }
    }
  }
  else
  {
    return 0;;
  }

}


void righton()
{
  if (flag1 == 0 && flag==1)
  {
    int i=0;
    for(i=0;i<10;i++)
    {
    int j = 8;
    for (j = 8; j < 11; j++)
    {
      digitalWrite(j, HIGH);
      delay(50);
      digitalWrite(j, LOW);
      delay(50);
    }
    }
  }
  else
  {
    return 0;
  }
}

test15.ino (3.8 KB)

What's going on with all the commented out lines?

nick371997:
I am using two accelerometers(ADXL335) outputs to execute two led loops namely left and right.I am using compare match interrupt to generate flag for each 10 sensor outputs and led’s are made high sequentially.I have a problem when i use left accelerometer and led’s start blinking for a set time and if i stop the left accelerometer and use the right accelerometer the left led’s should stop in the middle of loop and the right led’s should start. it’s not happening.please help.

#include <avr/io.h>

#include <avr/interrupt.h>
// these constants describe the pins. They won’t change:
//const int groundpin = 18;             // analog input pin 4 – ground
//const int powerpin = 19;              // analog input pin 5 – voltage
//const int xpin = A3;                  // x-axis of the accelerometer
const int ypin = A2;                  // y-axis
const int ypin1 = A3;
//const int zpin = A1;                  // z-axis (only on 3-axis models)
float a = 0;
float b = 0;
int flag;
int flag1;

void setup() {
 // initialize the serial communications:
 Serial.begin(115200);

// Provide ground and power by using the analog inputs as normal
 // digital pins.  This makes it possible to directly connect the
 // breakout board to the Arduino.  If you use the normal 5V and
 // GND pins on the Arduino, you can remove these lines.
 //pinMode(groundpin, OUTPUT);
 //pinMode(powerpin, OUTPUT);
 int k;
 for (k = 3; k < 11; k++)
 {
   pinMode(k, OUTPUT);
 }
 // digitalWrite(groundpin, LOW);
 // digitalWrite(powerpin, HIGH);
 // initialize Timer1
 cli();          // disable global interrupts
 TCCR1A = 0;     // set entire TCCR1A register to 0
 TCCR1B = 0;     // same for TCCR1B

// set compare match register to desired timer count:
 OCR1A = 15624/5;
 // turn on CTC mode:
 TCCR1B |= (1 << WGM12);
 // Set CS10 and CS12 bits for 1024 prescaler:
 TCCR1B |= (1 << CS10);
 TCCR1B |= (1 << CS12);
 // enable timer compare interrupt:
 TIMSK1 |= (1 << OCIE1A);
 sei();          // enable global interrupts

}

void loop()
{

// int z = analogRead(zpin) - 350;
 // z = (z * 9.8) / 75;
 float y = analogRead(ypin) - 350;
 y = (y * 9.8) / 75;
 float y1 = analogRead(ypin1) - 350;
 y1 = (y1 * 9.8) / 75;
 // print the sensor values:
 // Serial.print(analogRead(xpin));
 // print a tab between values:
 //Serial.print("\t");
 //Serial.print(analogRead(ypin));
 // print a tab between values:
 Serial.print(y);
 Serial.print("\t");
 Serial.print((y1));
 Serial.print("\t");
 Serial.print("\n");
 a = y1;
 b = y;

righton();
 lefton();

//Serial.println();
 // delay before next reading:
 // delay(30);
}

void gesture()
{
 int i = 0;
 int count = 0;

for (i = 0; i < 10; i++)
 {
   if (b < -2.5)
     count = count + 1;
   else
     count = count;

}
 if (count == 10)
 {
   flag = 0;
 }
 else
   flag = 1;
}

void gesture2()
{
 int i = 0;

int count1 = 0;

for (i = 0; i < 10; i++)
 {
   if (a < -2.5)
     count1 = count1 + 1;
   else
     count1 = count1;

}
 if (count1 == 10)
 {
   flag1 = 0;
 }
 else
   flag1 = 1;
}

ISR(TIMER1_COMPA_vect)
{
 gesture();
 gesture2();
 loop();
}

void lefton()
{
 if (flag == 0 && flag1==1)
 {
   int j = 3;
   int i = 0;
   for(i=0;i<10;i++)
   {
   for (j = 3; j < 6; j++)
   {
     digitalWrite(j, HIGH);
     delay(50);
     digitalWrite(j, LOW);
     delay(50);
   }
   }
 }
 else
 {
   return 0;;
 }

}

void righton()
{
 if (flag1 == 0 && flag==1)
 {
   int i=0;
   for(i=0;i<10;i++)
   {
   int j = 8;
   for (j = 8; j < 11; j++)
   {
     digitalWrite(j, HIGH);
     delay(50);
     digitalWrite(j, LOW);
     delay(50);
   }
   }
 }
 else
 {
   return 0;
 }
}

try this:
any global variable used inside the interrupt must be made volatile or it will not get the updates made elseware

volatile  float a = 0;
volatile  float b = 0;
volatile  int flag;
volatile  int flag1;

Calling loop() from an ISR? That's novel

      count = count;

Useful ?

for (i = 0; i < 10; i++)
  {
    if (b < -2.5)
      count = count + 1;
    else
      count = count;

If b is (or isn’t) less than -2.5, why do you need to check it ten times?
Just to be absolutely certain?

the accelerometers are sensitive.in case due to a bump or some other vibration a single value becomes less than the threshold you don't want the led's to glow.

I think you misunderstood. - why do you check a single value ten times?

changed that.still working the same.any other suggestions.

void gesture()
{
  if(b<-2.5)
  flag=0;
  else
  flag=1;
}


void gesture2()
{
  if(a<-2.5)
  flag1=0;
  else
  flag1=1;
}

See reply #3

if i call loop() in ISR, the led’s will glow only when the accelerometer is active.so switching becomes easy.If i don’t call loop() in ISR,the led’s will glow for the set amount of time and if i change the activity of accelerometer from left to the right the sequence executes after the left led’s sequence is completed.I need to combine both of them.

void gesture()
{
  if (b < -2.5)
    flag = 0;
  else
    flag = 1;
}


void gesture2()
{
  if (a < -2.5)
    flag1 = 0;
  else
    flag1 = 1;
}

ISR(TIMER1_COMPA_vect)
{
  gesture();
  gesture2();
  loop();
}




void ledon()
{
  for (int i = 0; i < 10; i++)
  {
    if (flag == 0 && flag1 == 1)
    {
      int j = 3;
      for (j = 3; j < 6; j++)
      {
        digitalWrite(j, HIGH);
        delay(50);
        digitalWrite(j, LOW);
        delay(50);
      }
    }
    else if (flag1 == 0 && flag == 1)
    {
      int j = 8;
      for (j = 8; j < 11; j++)
      {
        digitalWrite(j, HIGH);
        delay(50);
        digitalWrite(j, LOW);
        delay(50);
      }
    }
    else
    {
      break;
    }
  }
}

Calling loop() from an ISR is plain nonsense.

What is the interval between interrupts?

...R

330ms

nick371997: 330ms

That is a very long interval - why not just use millis() to manage the timing? The technique is illustrated in Several Things at a Time

...R