Arduino sketch werkt niet

Hallo,

Ik ben voor mijn profielwerkstuk bezig met het programmeren van verkeerslichten. Ik ben dit aan het doen met ledjes op een breadboard (Arduino). Ik ben nu met twee stoplichten bezig.

Ik wil nu graag dat als ik op button 1 druk het ene stoplicht op groen gaat en de ander op rood,
Dat als ik op button 2 druk het net andersom gebeurt,
Als ik op geen van beide druk gaat hij gewoon het normale rijtje af (Changelights) .

Dit heb ik tot nu toe, maar het wil maar niet lukken. Er gebeurt niks als ik op de buttons druk, hij gaat alleen het normale rijtje af (Changelights). zou iemand kunnen vertellen wat ik verkeerd doe?

code:


const int red= 10;
const int yellow = 9;
const int green = 8;

const int red2= 7;
const int yellow2 = 6;
const int green2 = 5;

const int buttonPin = 12;
const int button2Pin = 11;

int buttonState = LOW;
int button2State = LOW;


void setup() {
  // put your setup code here, to run once:
pinMode(red, OUTPUT);
pinMode(yellow, OUTPUT);
pinMode(green, OUTPUT);

  pinMode(red2, OUTPUT);
  pinMode(yellow2, OUTPUT);
  pinMode(green2, OUTPUT);

pinMode(buttonPin, INPUT);
pinMode(button2Pin, INPUT);
}


void loop() {
  // put your main code here, to run repeatedly:
  buttonState = digitalRead(buttonPin);
  button2State = digitalRead(button2Pin);
  
  if (buttonState == HIGH && button2State == LOW){
   digitalWrite(green, HIGH);
    digitalWrite(yellow, LOW);
    digitalWrite(red, LOW);
        digitalWrite(green2, LOW);
        digitalWrite(yellow2, LOW);
        digitalWrite(red2, HIGH);
    delay(6000);
  }
  
  else{
  Changelights();
  delay(1000);  
  Changelights();
} 


if (buttonState == LOW && button2State == HIGH){
   digitalWrite(green, LOW);
    digitalWrite(yellow, LOW);
    digitalWrite(red, HIGH);
        digitalWrite(green2, HIGH);
        digitalWrite(yellow2, LOW);
        digitalWrite(red2, LOW);
    delay(6000);
  }
  
  else{
  Changelights();
  delay(1000);  
  Changelights(); 


}


void Changelights() {
  digitalWrite(red, LOW);
  digitalWrite(yellow, LOW);
  digitalWrite(green, HIGH);
  
  digitalWrite(red2, HIGH);
  digitalWrite(yellow2, LOW);
  digitalWrite(green2, LOW);
  delay(6000);
  // stoplicht 1 staat op groen, stoplicht 2 staat op rood (6 seconden)

  
  digitalWrite(red, LOW);
  digitalWrite(yellow, HIGH);
  digitalWrite(green, LOW);
  
  digitalWrite(red2, HIGH);
  digitalWrite(yellow2, LOW);
  digitalWrite(green2, LOW);
  delay(3000); 
  // stoplicht 1 staat op geel, stoplicht 2 staat op rood (3 seconden)


  digitalWrite(red, HIGH);
  digitalWrite(yellow, LOW);
  digitalWrite(green, LOW);
  
  digitalWrite(red2, LOW);
  digitalWrite(yellow2, LOW);
  digitalWrite(green2, HIGH);
  delay(6000);
  // stoplicht 1 staat op rood, stoplicht 2 staat op groen (6 seconden)


  digitalWrite(red, HIGH);
  digitalWrite(yellow, LOW);
  digitalWrite(green, LOW);
  
  digitalWrite(red2, LOW);
  digitalWrite(yellow2, HIGH);
  digitalWrite(green2, LOW);
  delay(3000);
}

c code:

if (buttonState == HIGH /*&& button2State == LOW*/){

Blijkbaar heb je al wat geprobeerd.
Hoe heb je de drukknoppen aangesloten? En weet je zeker dat ze ook op de goede ingangen zitten.

Op 9 oktober 2019 17:03:59 schreef benleentje:

c code:

if (buttonState == HIGH /*&& button2State == LOW*/){

Blijkbaar heb je al wat geprobeerd.
Hoe heb je de drukknoppen aangesloten? En weet je zeker dat ze ook op de goede ingangen zitten.

Ja ik heb al wat zitten proberen.

Ik ben er vrij zeker van dat de draden goed zijn aangesloten. In de bijlage zie je hoe ik de buttons heb aangesloten. Ik heb ze beide zo aangesloten met een weerstand van 10K ohm (natuurlijk wel op pin 12 en 11 )

Binnen Changelights() heb je :

code:


   ...
   delay(6000);
   ...
   delay(3000);
   ...
   delay(6000);
   ...
   delay(3000);

Dus dan duurt het 18 seconden voordat die funktie klaar is en al die tijd kijkt het systeem niet naar de knopjes. Pas als de hele cyclus is afgelopen krijgen de knopjes even een kans, en daarna is het systeem weer 18 seconden bezig met de volgende Changelights().

Dus dat moet je oplossen met een statemachientje. En dan kun je millis() gebruiken om te zien hoeveel tijd er verstreken is.

zou ik ook tussen elke stap in changelights weer dit kunnen zetten zodat hij na elke stap controleert of de button is ingedrukt?:

c code:

if (buttonState == HIGH && button2State == LOW){
   digitalWrite(green, HIGH);
   digitalWrite(yellow, LOW);
   digitalWrite(red, LOW);
        digitalWrite(green2, LOW);
        digitalWrite(yellow2, LOW);
        digitalWrite(red2, HIGH);
   delay(6000);
  }
   else if (buttonState == LOW && button2State == HIGH){
   digitalWrite(green, LOW);
   digitalWrite(yellow, LOW);
   digitalWrite(red, HIGH);
        digitalWrite(green2, HIGH);
        digitalWrite(yellow2, LOW);
        digitalWrite(red2, LOW);
  delay(6000);
  }

[Bericht gewijzigd door Henry S. op 9 oktober 2019 20:39:49 (32%)]

Dat maakt helemaal niets uit. Als de microcontroller in een delay zit doet de cpu niets anders dan wachten totdat de delay klaar is.
Je kan dan met interrupt gaan werken die kijken naar een verandering van de ingangen. In een microcontroller zitten veel aparte blokken die onafhankelijk van elkaar hoen werk doen. Zoals bv de cpu, timmers, uart en ook de interruptcontroller. Dus ook al zit de cpu in een helel lange wacht lus van 6 seconden de interruptcontroller ziet wel dat een ingang verandert en geeft dan een seintje aan de cpu. JE moet dat wel eerst insoftware geregeld hebben want anders staat dat standaard uit.

Een andere manier is de delays veel korter maken maar dan vaker uitvoeren. Dat gaat een delay van bv 100mS en die dan 60 keer uitvoeren. Je maakt dan een aparte functie daarvoor.

Als je niet zeker bent over de werking van de drukknoppen kan je dat ook beter even apart testen met een programma met geen delays of gewoon een apart programma. Dit is eigenlijk altijd een goed advies een bepaalde dingen uit te sluiten. Want bij mij werken die drukknoppen nooit in mijn breadbord ze schieten er altijd uit en de korte pootje maken amper contact. Maar dat kan ook mijn (on)kunde liggen of ik heb gewoon de verkeerde drukkoppen.

[Bericht gewijzigd door benleentje op 9 oktober 2019 19:20:19 (23%)]

Interrupts zijn heel niet nodig hier, Dat maakt het alleen maar ingewikkeld.

Een state-machine klinkt misschien ingewikkeld maar dat valt wel mee. Hierbij een aanzetje:

code:




void Stoplicht1(int Kleur)
{
   if(Kleur == 1) // Groen
   {  digitalWrite(red,    HIGH);
      digitalWrite(yellow, LOW);
      digitalWrite(green,  LOW);
   }
   if(Kleur == 2) // Rood
   {  digitalWrite(red,    LOW);
      digitalWrite(yellow, LOW);
      digitalWrite(green,  HIGH);
   }
}

void Stoplicht2(int Kleur)
{
   if(Kleur == 1) // Groen
   {  digitalWrite(red2,    LOW);
      digitalWrite(yellow2, LOW);
      digitalWrite(green2,  HIGH);
   }
   if(Kleur == 2) // Rood
   {  digitalWrite(red2,    HIGH);
      digitalWrite(yellow2, LOW);
      digitalWrite(green2,  LOW);
   }
}

int State = 0;
unsigned long Start = millis();

void loop()
{
   if(digitalRead (buttonpin))
   {  State = 2;
      Start = millis();
   }

   if(digitalRead (buttonpin2))
   {  State = 0;
      Start = millis();
   }

   switch(State)
   {  case 0:
      {  Stoplicht1(1);
         Stoplicht2(2);
         if((millis() - Start) > 6000)
         {  State += 1;
            Start = millis();   
         }
         break;
      }
      case 1:
      {  Stoplicht1(2);
         Stoplicht2(2);
         if((millis() - Start) > 1000)
         {  State += 1;
            Start = millis();   
         }
         break;
      }
      case 2:
      {  Stoplicht1(2);
         Stoplicht2(1);
         if((millis() - Start) > 6000)
         {  State += 1;
            Start = millis();   
         }
         break;
      }
      case 3:
      {  Stoplicht1(2);
         Stoplicht2(2);
         if((millis() - Start) > 1000)
         {  State += 1;
            Start = millis();   
         }
         break;
      }
      default:
      {  State = 0;
         Start = millis();
      }
   }
}

Als je niet goed weet hoe je programma doorlopen wordt, moet je dat inzichtelijk maken. Dat kan bv door serial.print() commandos in je code te zetten op allerlei plaatsen. Je print dan steeds waar je zit. Op je terminal kun je dan zien wat er gebeurt als je een knop drukt. Het kan hier bv best zijn dat je knoppen niet gezien worden en daar heb je nu geen idee van.

"We cannot solve our problems with the same thinking we used when we created them" - Albert Einstein