Кнопки, прерывания, LCD.

Hayabusa
Offline
Зарегистрирован: 29.03.2012

 Доброй ночи. К ардуино подключено 6 кнопок (через 10к резисторы), LCD дисплей 20x4. Сводобных ног не так уж и много остается. 

Пытаюсь сообразить подобие меню и организовать обработчик события по нажатию кнопки.

То есть ели нажата кнопка Up - вызов функции ну... блинкЗеленый. И моргает до тех пор пока не нажму кнопку Esc.

Down - вызов функции блинкКрасный, и соответственно моргаем пока не нажму Esc.

Озадачился, как же мне зациклить функцию, Loop один а фнкций будет тьма. Придумал засунутьее в 

do...while, но, не вышло.

Пробовал писать код:


void fuckingBlink () {

do
{
  EscState =digitalRead(buttonPinEsc); // EscState =0 - это  у меня статус кнопки Esc. Кнопка поключена к 8 ноге.




digitalWrite(0, HIGH); // set the LED on
delay(1000); // wait for a second
digitalWrite(0, LOW); // set the LED off
delay(1000); 

} 
  while (EscState ==HIGH); // 
ну как бы моргаем пока на 8 ноге не будет HIGH
}
Диод моргает, но на кнопку не реагирует. Давай копаться, нашел про прерывания, замечательная вещь. Но вроде
как их всего пару штук и они на ногах которые у меня заняты уже LCD. Как быть, куды бечь?



maksim
Offline
Зарегистрирован: 12.02.2012

Ну для начала лучше было бы если при нажитии кнопки digitalRead(button) выдавал 0, а не 1, но дело ваше.

Вам нужно обьявить глобальную переменную, которую будет менять нажатие кнопки и которая будет определять ход программы.

maksim
Offline
Зарегистрирован: 12.02.2012

В вашем случае примерно вот так:

#define BUTTON1 2
#define BUTTON2 3
#define BUTTON3 4
//#define BUTTON.. ..
//#define .....

int rezgim = 0;

void setup() {
  pinMode(10, OUTPUT); //зеленый
  pinMode(11, OUTPUT); // красный
}

void loop() {
  if(digitalRead(BUTTON1)){
    rezgim = 1;
  }
  if(digitalRead(BUTTON2)){
    rezgim = 2;
  }
  if(digitalRead(BUTTON3)){
    rezgim = 3;
  }
  /*if(digitalRead(BUTTON..)){
   rezgim = ..;
   }                             */
  switch (rezgim) {
  case 1:
    digitalWrite(10, HIGH); // set the LED on
    delay(1000); // wait for a second
    digitalWrite(10, LOW); // set the LED off
    delay(1000); 
    break;
  case 2:
    digitalWrite(11, HIGH); // set the LED on
    delay(1000); // wait for a second
    digitalWrite(11, LOW); // set the LED off
    delay(1000); 
    break;
  case 3:
    // код для выполнения
    break;
  case 4:
    // код для выполнения
    break;
  default:
    ;// код для выполнения
  }

}

 

step962
Offline
Зарегистрирован: 23.05.2011

 Если реализовать приведенный вариант, то ждать реакции на нажатие кнопки придется по несколько секунд. Что в корне изничтожает удобство пользования.

Кнопки должны реагировать как и положено кнопкам - с задержкой, незаметной для пользователя. Поэтому:

определяем две переменные

oTime - момент последнего переключения "активного" светодиода

oState - последнее состояние "активного" светодиода

В setup() присваивааем этим переменным значения - текущего времени и любое (например, LOW) соответственно.

В loop():

if(millis()-oTime)>1000 { // прошла секунда?
  if(oState==LOW) oState=HIGH;
  else oState==LOW;
// изменили состояние светодиода, теперь определяем, каким светодиодом рулим в настоящий момент -> nLED
switch(regim) {
    ...
  }
  digitalWrite(nLED,oState);
// готовимся к отсчету очередной секунды:
  oState=millis();
}
// дальше - остальные операторы функции loop()

 Приведенное условие будет срабатывать каждую секунду и производить мигание светодиодом без существенной задержки (пара микросекунд не в счет) в работе программы.

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

maksim
Offline
Зарегистрирован: 12.02.2012

Да задержки лучше не использовать

Hayabusa
Offline
Зарегистрирован: 29.03.2012

Спасибо, какие же вы хорошие, отзывчивые люди!  

vworld
vworld аватар
Offline
Зарегистрирован: 26.09.2011

тоже начинаю озадачиваться созданием меню...

пока нарыл инфу

http://arduino.ru/forum/programmirovanie/menyu-dlya-tekstovogo-lcd-pomog...

http://rln.nnov.ru/index.php?ind=reviews&op=entry_view&iden=211