Включение и выключение двух наборов светодиодов с помощью двух кнопок

У меня есть два комплекта из 4 светодиодов.

Установите A (Led1, Led2, Led3, Led4) Комплект B (Led5, Led6, Led7, Led8)

Оба набора имеют свою собственную тактильную кнопку:

Тактильный А, Тактильный В,

Тактильный A, включение светодиодов набора A и тактильный B, включение светодиодов набора B.

Поэтому каждый раз, когда я нажимаю тактильную клавишу A, загорается светодиод1 из набора A. Следующее нажатие приведет к включению Led2 и выключению LED1, затем включению Led3, выключению Led2 и включению Led4 и выключению led3.

То же самое для тактильного B и набора B.

Тактильный элемент A не изменит набор be и тот же тактильный элемент B.

Итак, я придумал приведенный ниже код. Это прекрасно работает для тактильного А, для набора А. Но я не могу включить набор B с помощью тактильного B. Тактильный B продолжает переключаться один за другим, тактильный B не функционирует. Каждый набор должен работать со своей собственной тактильной кнопкой.

//Пуск - код включения/выключения питания

#include <Bounce2.h> 

#define POWER_PIN 13
#define power 12


//End - Код включения/выключения питания

// Пуск - Переключение светодиодов
// Светодиоды устанавливают
#define button 2
#define led1 8
#define led2 7
#define led3 6
#define led4 5
//Комплект светодиодов B
#define tactile 3
#define led5 11
#define led6 4
#define led7 9
#define led8 10
int state = 0;      //целое число для хранения текущего состояния Установите A
int old = 0;        //целое число для хранения последнего состояния Установите A
int tactitleState = 0;      //целое число для хранения текущего состояния Установите B
int oldState = 0;        // целое число для хранения последнее состояние Set B
int buttonPoll = 0; // целое число для удержания состояния кнопки для set A
int tactilePoll = 0; // целое число для удержания состояния кнопки для set B
// End - Переключение питания

//Start - код включения/выключения питания

int powerState = LOW;
Bounce b = Bounce(); // Создание экземпляра объекта Bounce

//End - Код включения/выключения питания

void setup() {
  //Start - код включения/выключения питания

  b.attach(POWER_PIN, INPUT_PULLUP); // Присоедините деблокирователь к контакту в режиме INPUT_PULLUP
  b.interval(25); // Используйте интервал деблокирования 25 миллисекунд
  pinMode(power, OUTPUT); // Настройка светодиода
  digitalWrite(power, powerState); // Выключить светодиод

  //End - Код включения/выключения питания

  // Пуск - Переключение мощности

  pinMode(button, INPUT); //кнопка устанавливается в качестве входного
  pinMode(led1, OUTPUT); //Выходной набор Led1
  pinMode(led2, OUTPUT); //Выходной набор Led2
  pinMode(led3, OUTPUT); //Выходной набор Led3
  pinMode(led4, OUTPUT); //Выходной набор Led4

  digitalWrite (led1, HIGH); //установить состояние Led1
  digitalWrite (led2, HIGH); //установить состояние Led2
  digitalWrite (led3, HIGH); //установить состояние Led3
  digitalWrite (led4, HIGH); //установить состояние Led4

  digitalWrite (power, HIGH); // состояние входной мощности 

  //
  pinMode(tactile, INPUT); // кнопка, установленная в качестве
  pinMode(led5, OUTPUT); //Выходной набор Led5
  pinMode(led6, OUTPUT); //Выходной набор Led6
  pinMode(led7, OUTPUT); //Выходной набор Led7
  pinMode(led8, OUTPUT); //Выходной набор Led8

  digitalWrite (led5, HIGH); //установить состояние Led5
  digitalWrite (led6, HIGH); //установить состояние Led6
  digitalWrite (led7, HIGH); //установить состояние Led7
  digitalWrite (led8, HIGH); //установить состояние Led8

  // Конец - Коммутационная мощность

}

void loop() {
  //Start -- код включения / выключения питания
  b.update(); // Обновить экземпляр отказов
  if ( b.fell() ) {  // Код вызова, если кнопка переходит с ВЫСОКОГО уровня на НИЗКИЙ
    powerState = !powerState; // Переключить состояние светодиода
    digitalWrite(power, powerState); // Применить новое состояние светодиода
  }
  //End - Код включения/выключения питания

  //Пуск - Переключение набора мощности A. 

  buttonPoll = digitalRead(button); //Определить состояние кнопки
  if (buttonPoll == 1) {              //Проверить, нажата ли кнопка
    delay (50);                       //Задержка 50 мс
    buttonPoll = digitalRead (button); //Снова кнопка опроса
    if (buttonPoll == 0) {           //если значение равно 0, считается одно нажатие
      state = old + 1;               // увеличивает состояние на 1
    }
  }
  else {
    delay (100);                    //Задержка 100 мс
  }
  switch (state) {     //реагирует на нажатие кнопки tot и состояние
    case 1:
      digitalWrite (led1, LOW); // led1 включен
      digitalWrite (led2, HIGH); // led2 выключен
      digitalWrite (led3, HIGH); // led3 выключен
      digitalWrite (led4, HIGH); // led4 выключен
      old = state;
      break;
    case 2:
      digitalWrite (led1, HIGH); // led1 выключен
      digitalWrite (led2, LOW); // led2 включен
      digitalWrite (led3, HIGH); // led3 выключен
      digitalWrite (led4, HIGH); // led4 выключен
      old = state;
      break;
    case 3:
      digitalWrite (led1, HIGH); // led1 выключен
      digitalWrite (led2, HIGH); // led2 выключен
      digitalWrite (led3, LOW); // led3 включен
      digitalWrite (led4, HIGH); // led4 выключен
      old = state;
      break;
    case 4:
      digitalWrite (led1, HIGH); // led1 имеет значение
      digitalWrite (led2, HIGH); // led2 выключен
      digitalWrite (led3, HIGH); // led3 выключен
      digitalWrite (led4, LOW); // led4 находится в
      old = state;
      break;
    default:                   // если состояние отсутствует, то все светодиоды выключены
      digitalWrite (led1, HIGH); // led1 имеет значение
      digitalWrite (led2, HIGH); // led2 выключен
      digitalWrite (led3, HIGH); // led3 выключен
      digitalWrite (led4, HIGH); //led4 выключен
      old = 0;   // Все состояния сбрасываются на 0 выключен
      break;
  }
  // Конец - переключение светодиодного набора A
  // Начало - переключение светодиодного набора B

  tactilePoll = digitalRead(tactile); //Определить состояние кнопки
  if (tactilePoll == 1) {              //Проверить, нажата ли кнопка
    delay (50);                       //Задержка 50 мс
    tactilePoll = digitalRead (tactile); //Снова кнопка опроса
    if (tactilePoll == 0) {           //если значение равно 0, считается одно нажатие
      tactitleState = oldState + 1;               //увеличивает состояние на 1
    }
  }
  else {
    delay (100);                    //Задержка 100 мс
  }
  switch (tactitleState) {     // реагирует на нажатие и состояние кнопки tot
      case 1:
      digitalWrite (led5, LOW); // led5 включен
      digitalWrite (led6, HIGH); // led6 выключен
      digitalWrite (led7, HIGH); // led7 выключен
      digitalWrite (led8, HIGH); // led8 выключен
      oldState = tactitleState;
      break;
    case 2:
      digitalWrite (led5, HIGH); // led5 выключен
      digitalWrite (led6, LOW); // led6 включен
      digitalWrite (led7, HIGH); // led7 выключен
      digitalWrite (led8, HIGH); // led8 выключен
      oldState = tactitleState;
      break;
    case 3:
      digitalWrite (led5, HIGH); // led5 выключен
      digitalWrite (led6, HIGH); // led6 выключен
      digitalWrite (led7, LOW); // led7 включен
      digitalWrite (led8, HIGH); // led8 выключен
      oldState = tactitleState;
      break;
    case 4:
      digitalWrite (led5, HIGH); // led5 выключен
      digitalWrite (led6, HIGH); // led6 выключен
      digitalWrite (led7, HIGH); // led7 выключен
      digitalWrite (led8, LOW); // led8 включен
      oldState = tactitleState;
      break;
    default:                   // если состояние отсутствует, то все светодиоды выключены
      digitalWrite (led5, HIGH); // led5 выключен
      digitalWrite (led6, HIGH); // led6 выключен
      digitalWrite (led7, HIGH); // led7 выключен
      digitalWrite (led8, HIGH); //led8 выключен
      oldState = 0;   // Все состояния сбрасываются на 0 выключен
      break;
  }
  //Конец - Переключение светодиодов комплект B
}

, 👍1

Обсуждение

Ссылка, похоже, не работает без учетной записи. Ваш код для проверки того, нажата ли кнопка, очень странный, и меня удивляет, что он даже, кажется, работает для кнопки A set. Как связаны ваши кнопки? Есть ли у них подтягивающий / опускающий резистор? Могу ли я также предложить переименовать ваши переменные во что-то менее случайное? Например, используйте "StateA" и "StateB" вместо "state" и "tactileState". То же самое для "buttonPoll" и "tactilePoll". старый" и "Старое государство., @Gerben


1 ответ


1

Вашему коду довольно трудно следовать.

Ваш код для чтения нажатия кнопки не имеет особого смысла:

  buttonPoll = digitalRead(button); //Определить состояние кнопки
  if (buttonPoll == 1) {              //Проверить, нажата ли кнопка
    delay (50);                       //Задержка 50 мс
    buttonPoll = digitalRead (button); //Снова кнопка опроса
    if (buttonPoll == 0) {           //если значение равно 0, считается одно нажатие
      state = old + 1;               // увеличивает состояние на 1
    }
  }
  else {
    delay (100);                    //Задержка 100 мс
  }

Я думаю, что этот код будетобнаруживать нажатие кнопки только в том случае, если вы нажимаете на кнопку ровно 50 мс. Учитывая, что вы уже используете библиотеку отказов, почему бы вам не создать экземпляры отказов для кнопок вашего светодиодного контроллера и не использовать их для чтения этих кнопок?

Следующая проблема: вы устанавливаете для своих кнопок и тактильных контактов значение INPUT, а не INPUT_PULLUP. У вас есть на них выдвижные резисторы? (когда ваш вход настроен на режим ввода, вам понадобятся выдвижные резисторы, а переключатели необходимо подключить к +5В. Если вы используете режим INPUT_PULLUP, вам не нужны никакие резисторы, но вы подключаете свои переключатели к земле. Затем они считывают значение HIGH до тех пор, пока вы не нажмете переключатель, после чего переключатель подключает контакт к заземлению и опускает его.)

Следующая проблема: вы рассматриваете значение 1 как нажатое, а 0 - как не нажатое. Вместо этого вы должны использовать константы HIGH и LOW . (И обратите внимание, что если вы используете режим INPUT_PULLUP для своих контактов, вы должны подключить свои кнопки к VCC и считать ВЫСОКИЙ уровень не нажатым, а НИЗКИЙ - нажатым.)

Я бы предложил переименовать ваши переменные и использовать массивы контактных номеров светодиодов:

int set1Button 2;
int set1LEDs[] = {8, 7, 6, 5};
int set1State = 0; // Светодиоды не горят

int set2Button 3;
int set2LEDs[] = {11, 4, 9, 10};
int set2State = 0; // Светодиоды не горят

Нажатие setButton1 должно продвинуть set1State, а нажатие set2Button должно продвинуть set2State.

Для значения 0 установите все светодиоды в положение выкл. при любом другом значении включите светодиод с индексом setXState - 1, а все остальные выключите.

Этот код будет работать для первого набора светодиодов:

for (int index = 1; index <= 4; index++) {
     int value = set1State == index ? HIGH : LOW;
     digitalWrite (set1LEDs[index-1], value); 
}
,

Небольшая поправка: при использовании INPUT_PULLUP следует подключить кнопку к заземлению, а не к Vcc. И, конечно, определение массива должно выглядеть так, как указано в редактировании вашего вопроса. Насколько я знаю, приведенное выше определение массива не работает в C / C ++., @chrisl

Крисл, из того, как был сформулирован мой ответ, было неясно, что для вывода, установленного на вход, вам нужен выдвижной резистор и переключатель, подключенный к + 5 В, но для режима INPUT_PULLUP вам необходимо подключить переключатель к земле. Я отредактировал ответ, чтобы сделать его более понятным., @Duncan C

В наши дни я работаю в основном в Swift и не могу вспомнить синтаксис статического массива C / C ++. Спасибо @Mat за то, что исправил это., @Duncan C

@DuncanC, не могли бы вы, пожалуйста, предоставить полный код? Я пытался, но это не работает., @Habib Anwari

Это не сервис для написания кода, и мой частичный код может не соответствовать остальной части вашего скетча. Отредактируйте свой вопрос и предоставьте обновленный код в конце вместе с подробной информацией о том, как он ведет себя., @Duncan C

На вашей новой схеме подключения показано, что кнопки подключены к +5V. Это правильно? Используете ли вы режим ВВОДА или режим INPUT_PULLUP? Рассматриваете ли вы ВЫСОКОЕ значение как нажатую кнопку или НИЗКОЕ значение?, @Duncan C

@DuncanC, кнопка подключена к 5 В, а также к контакту 2, а другая - к контакту 3. Таким образом, при нажатии кнопки вывод 2 или тот же вывод 3 поднимается вверх., @Habib Anwari

А остальные мои вопросы?, @Duncan C

@DuncanC, я использую режим ввода с резистором, как показано на рисунке, если это неправильно, тогда я буду использовать режим INPUT_PULLUP. Когда кнопка нажата, она будет действовать на НИЗКОМ УРОВНЕ., @Habib Anwari

Режим ввода с выдвижными резисторами должен работать. Однако я не вижу никаких понижающих резисторов на изображении вашей схемы., @Duncan C

Но ваша кнопка, удаляющая код из вашего исходного сообщения, - это беспорядок. Почему бы не использовать библиотеку отказов для ваших коммутаторов? Я предполагаю, что именно для этого он и предназначен., @Duncan C

@DuncanC, поскольку я опубликовал этот вопрос, я начал онлайн-курс по кодированию Arduino и C ++. Я почти закончил курс Arduino, и это было не так уж и полезно. Я начну еще один продвинутый курс по Arduino. В будущем, возможно, я смогу разобраться с этим. Но сейчас я слишком новичок. Я просто делаю это для удовольствия и опыта, и это не бизнес. Я погуглил библиотеку отказов и проверил YouTube, я посмотрю, как это возможно. Спасибо за указания., @Habib Anwari

Я нашел несколько примеров в этих ссылках: Как определить короткие, длинные и двойные щелчки с помощью Arduino https://youtu.be/TwM1sp2IXYI Снятие подпрыгивания кнопок https://youtu.be/4NcfEwm9WBI, @Habib Anwari