Прерывание по кнопке ATmega328 pro mini

magals1
Offline
Зарегистрирован: 23.10.2014

К плате подлючил RGB светодиод и кнопку для смены режима. проблема в том, что прерывание по кнопке не срабатывает

//контакты светодиодов 
const int PinRed = 9;
const int PinGreen = 10;
const int PinBlue = 11;

//контакт кнопки
const int PinMode = 2;
//Режим управления
int Mode = 0;
//значение для PWT
int value;

void setup()
{
pinMode(PinMode,  INPUT);
attachInterrupt(0, ChangeMode, RISING);  
  
pinMode(PinRed,   OUTPUT);
pinMode(PinGreen, OUTPUT);
pinMode(PinBlue,  OUTPUT);
}

void loop()
{

  while(true)
  {
   switch(Mode)
   {

     case 0: SelectPWTon(PinRed,  0); SelectPWToff(PinRed,  0); break;//Плавно зажигаем/гасим Красный
     case 1: SelectPWTon(PinGreen,1); SelectPWToff(PinGreen,1); break;//Плавно зажигаем/гасим Зеленный
     case 2: SelectPWTon(PinBlue, 2); SelectPWToff(PinBlue, 2); break;//Плавно зажигаем/гасим Синий

     default: void SelectOff(); break;//гасим все
    }
  }

}

void ChangeMode()
{
  Mode++; 
  if(Mode>=3)
  {
    Mode=0;
  }
}
//Плавное включение
void SelectPWTon(int Pin, int mode)
{
 value=0;
 do{
   analogWrite(Pin, value);           
   delay(100); 
   value+=5; 
 }while(value<255 && Mode==mode); 
}
//Плавное гашение 
void SelectPWToff(int Pin, int mode)
{
 value=255;
 do{ 
   analogWrite(Pin, value);           
   delay(100); 
   value-=5; 
 }while(value>0 && Mode==mode); 
}

//Выключаем все
void SelectOff()
{
digitalWrite(PinRed,   LOW);
digitalWrite(PinGreen, LOW); 
digitalWrite(PinBlue,  LOW); 
}

 

Araris
Offline
Зарегистрирован: 09.11.2012

Подсказка: 

"Переменная должна быть объявлена volatile, когда её значение может быть изменено чем-либо за пределами того участка программы, где она объявлена, например, параллельно выполняющимся процессом. В Arduino единственным местом, где это может проявиться, является участок программы, ассоциированным с прерываниями, вызванный программой обработки прерываний. См. AttachInterrupt()"

Тут: http://arduino.ru/Reference/Volatile

magals1
Offline
Зарегистрирован: 23.10.2014
//контакты светодиодов 
const int PinRed = 9;
const int PinGreen = 10;
const int PinBlue = 11;

//контакт кнопки
const int PinMode = 2;
//Режим управления
volatile int Mode = 0;
//значение для PWT
int value;

void setup()
{
pinMode(PinMode,  INPUT);
attachInterrupt(0, ChangeMode, RISING);  
  
pinMode(PinRed,   OUTPUT);
pinMode(PinGreen, OUTPUT);
pinMode(PinBlue,  OUTPUT);
}

void loop()
{

  while(true)
  {

   switch(Mode)
   {

     case 0: SelectPWTon(PinRed,  0); SelectPWToff(PinRed,  0); break;//Плавно зажигаем/гасим Красный
     case 1: SelectPWTon(PinGreen,1); SelectPWToff(PinGreen,1); break;//Плавно зажигаем/гасим Зеленный
     case 2: SelectPWTon(PinBlue, 2); SelectPWToff(PinBlue, 2); break;//Плавно зажигаем/гасим Синий

     default: void SelectOff(); break;//гасим все
    }
  }

}

void ChangeMode()
{
  void SelectOff();  
  Mode++; 
  if(Mode>=3)
  {
    Mode=0;
  }
}
//Плавное включение
void SelectPWTon(int Pin, int mode)
{
 value=0;
 do{
   analogWrite(Pin, value);           
   delay(100); 
   value+=5; 
 }while(value<255 && Mode==mode); 
}
//Плавное гашение 
void SelectPWToff(int Pin, int mode)
{
 value=255;
 do{ 
   analogWrite(Pin, value);           
   delay(100); 
   value-=5; 
 }while(value>0 && Mode==mode); 
}

//Выключаем все
void SelectOff()
{
digitalWrite(PinRed,   LOW);
digitalWrite(PinGreen, LOW); 
digitalWrite(PinBlue,  LOW); 
}

немного изменил код, кнопка работает. Вот теперь проблема другая. почему при срабатывании прерывания. не гаснится предыдущий цвет, а вместе с ним зажигается новый? то есть идет смешивание. можно ли сделать, чтоб при прерывании программа(функция loop) начала работать сначала? это не ресет необходимо чтоб значение mode сохранялся  

Radjah
Offline
Зарегистрирован: 06.08.2014

Ты же его не гасишь, вот он и не гаснет.

magals1
Offline
Зарегистрирован: 23.10.2014

у меня в прерывании гасится все. хотя я подозреваю что, когда выполнение функции прерывания заканчивается, то возращаюсь к тому моменту когда ещё раз светодиод зажигается. вот и необхидимо, как то сбрасывать основную программу в преывании 

Radjah
Offline
Зарегистрирован: 06.08.2014

В упор не вижу. Какое-то объявление функции вижу, а вызов её не вижу.

magals1
Offline
Зарегистрирован: 23.10.2014

Radjah пишет:

В упор не вижу. Какое-то объявление функции вижу, а вызов её не вижу.

ой ваша правда. лишний раз void поставил перед вызовом функции вот и не срабатывало. терь вроде нормально