Несколько циклов для управления включением и выключением светодиодов

Я здесь новенький. Я попытался написать простой код, чтобы включить светодиоды и зажечь их по определенному шаблону, а также иметь возможность выключать его во время цикла. До сих пор мне удавалось либо заставить их постоянно мигать по шаблону и не реагировать на кнопку, либо когда я писал в отдельных циклах пустоты каждую функцию IDE Arduino, выдавало мне ошибку «ожидается» пока перед «loop1», и я полностью застрял и не понял, в чем проблема с кодом. Кто-нибудь может помочь?

Вот код:

const int ledPin =  2;
const int ledPin1 = 3;
const int ledPin2 = 4;
const int buttonPin = 5;

int programState = 0;

int buttonState;
long buttonMillis = 0;
const long intervalButton = 300;   

long ledMillis = 300;
const long intervalLed = 500;   

void setup() {
  pinMode(ledPin, OUTPUT); 
  pinMode(ledPin1, OUTPUT);
  pinMode(ledPin2, OUTPUT);    
  pinMode(buttonPin, INPUT);     
  digitalWrite(buttonPin, HIGH);
}

void loop()
{
  unsigned long currentMillis = millis();
  buttonState = digitalRead(buttonPin);

 if (buttonState == LOW && programState == 0)
  do{
   programState = 1;
    }
void loop1(){
if {programState = 1 && buttonState == HIGH}
 do  {
   programState = 2;
    ledMillis = currentMillis;
    digitalWrite(ledPin, HIGH);
    delay(200);
    digitalWrite(ledPin1,HIGH);
    delay(200);
    digitalWrite(ledPin2,HIGH);
    delay(200);
    digitalWrite(ledPin2,LOW);
    delay(200);
    digitalWrite(ledPin1,LOW);
    delay(200);
    digitalWrite(ledPin,LOW);
    delay(200);
    digitalWrite(ledPin,HIGH);
    delay(200);
    digitalWrite(ledPin1,HIGH);
    delay(200);
    digitalWrite(ledPin2,HIGH);
    delay(200);
    digitalWrite(ledPin2,LOW);
    delay(200);
    digitalWrite(ledPin1,LOW);
    delay(200);
    digitalWrite(ledPin,LOW);
    delay(1500);}
 }
 void loop2(){
 if (programState = 2 && buttonState == LOW)

 do {
  programState = 2;
    digitalWrite(ledPin, HIGH);
    delay(200);
    digitalWrite(ledPin1,HIGH);
    delay(200);
    digitalWrite(ledPin2,HIGH);
    delay(200);
    digitalWrite(ledPin2,LOW);
    delay(200);
    digitalWrite(ledPin1,LOW);
    delay(200);
    digitalWrite(ledPin,LOW);
    delay(200);
    digitalWrite(ledPin,HIGH);
    delay(200);
    digitalWrite(ledPin1,HIGH);
    delay(200);
    digitalWrite(ledPin2,HIGH);
    delay(200);
    digitalWrite(ledPin2,LOW);
    delay(200);
    digitalWrite(ledPin1,LOW);
    delay(200);
    digitalWrite(ledPin,LOW);
    delay(1500);}


 else if  (programState == 2 && buttonState == HIGH) 
 do
   {

    digitalWrite(ledPin, LOW);
    digitalWrite(ledPin1, LOW);
    digitalWrite(ledPin2, LOW);
  }
}
yield();
}

, 👍-1


2 ответа


0

Вы неправильно используете функцию do:

Вот так:

do{
  programState = 1;
}

Это должно быть что-то вроде:

do
{
  programState = 1;
} while (`some condition`);

Где какое-то условие — это условие, которое повторяет части { и } в случае, если некоторое условие верно.

Однако, помимо этого, обычно не имеет смысла назначать переменную в цикле while как единственный оператор, так как она будет равна 1 после первой итерации, и повторное ее повторное присвоение не изменит значение (programState остается равным 1).

Также обратите внимание, что в большинстве случаев используется следующая форма (если только вы не хотите, чтобы тело всегда выполнялось хотя бы один раз):

while (`some condition`)
{
  `statements`
}

Вы уверены, что вам вообще нужен оператор do или while? В противном случае попробуйте удалить операторы do и посмотрите, ближе ли это к тому, что вам нужно (я не могу сопоставить код с вашими требованиями). У меня такое ощущение, что вы хотите использовать циклы, чтобы предотвратить дублирование кода, для этого вам нужно хранить ledPin, ledPin1 и ledPin2 переменные в массиве и перебрать их в цикле.

Другой способ - вместо, например, следующего кода:

digitalWrite(ledPin, HIGH);
delay(200);

для создания отдельной функции:

void setPin(int pin, int value)
{
   digitalWrite(pin, value);
   delay(200);
}

и вызвать функцию следующим образом:

setPin(ledPin, HIGH);

Теперь вы можете изменить все вхождения 'digitalWrite(some pin, some state); delay(200)' на один оператор выше.

Кроме того, я вижу функцию yield, которая не реализована.

,

Спасибо :) Я последую Вашему совету и посмотрю, куда он меня приведет., @jbengsch


0

В дополнение к неправильному использованию конструкции do вы также используете подход, который не будет работать.

Как правило, в Arduino не следует использовать оператор do-while. Это приводит к тому, что ваш код «застревает» в теле оператора do-while, пока условие while истинно, что предотвращает выполнение остальной части вашего кода.

Вы также не должны использовать функцию delay(), если вам нужно управлять синхронизацией разных вещей одновременно. (Чтобы сделать более общее заявление, вы не должны использовать функцию delay() вообще. Забудьте о ее существовании.) В редких случаях (например, при однократной настройке оборудования в вашем методе setup().), где уместно использование функции delay(), или очень короткие интервалы, такие как синхронизация ультразвуковых импульсов, но функция delay() ВСЕГДА приводит к полной остановке вашей программы до тех пор, пока не пройдет интервал задержки.

Вы должны выполнить поиск «Arduino, мигающий без задержки» и изучить пример проекта, который вы найдете. В нем описано, как использовать функцию millis() для отслеживания времени. С таким подходом вы можете синхронизировать несколько вещей одновременно. (У вас будет несколько переменных «время срабатывания», которые будут помнить значение millis(), при котором вы хотите, чтобы произошло изменение, и вы получите это значение millis() ваш код вызовет изменение (например, переключение светодиода), а затем обновит эту переменную "время срабатывания".

,