Simon Says

Projecten die niet passen in bovenstaande onderwerpen
Berichten: 2
Geregistreerd: 28 Jul 2017, 19:39

Simon Says

Berichtdoor Wynants » 28 Jul 2017, 19:56

Hoi beste forum gangers, ik ben nieuw op dit forum, maar al wel enige ervaring met Arduino programmeren(dacht ik).

Nu zit het zo dat ik het simon says spel wil namaken(1), dit lukt aardig. Wanneer er een fout is gemaakt knipperen alle lampen 2* en begint hij weer van tevoren. (hij loopt nu een loop tot een knop wordt ingedrukt wacht een X aantal seconden en begint het spel). Dit werkt allemaal goed. Nu waar het fout gaat is, wanneer ik bij de 2e ronde kom en weer op de 1e knop druk(eenmaal) deze aangeeft dat deze 2 maal is gedrukt. Dus in de meeste gevallen betekend dit dat ik af ben. ik snap niet hoe dit komt en hoe ik dit aangepast kan krijgen. Ik heb een deel van mijn code van het internet gekopieerd van voorbeelden die vlekkeloos liepen.

Code: Alles selecteren
int buttons[] = {3, 5, 7, 9};
int interval = 5;

int leds[] = {2, 4, 6, 8};

int sequence[100];
int index = 0;

int gamestate;

const int START = 0;
const int PLAY = 1;
const int GAMEOVER = 2;
const int FINISH = 3;

long currentmillis = 0;
long readingmillis = 0;

unsigned long current = 0;
unsigned long reading = 0;

void setup()
{
  for (int pin = 0; pin < 4; pin++)
  {
    pinMode(leds[pin], OUTPUT);
    pinMode(buttons[pin], INPUT);
  }
  Serial.begin(9600);
  randomSeed(analogRead(40));
}

void loop()
{
  if (gamestate == START)
  {
    startloop();
  }

  else if (gamestate == PLAY)
  {
    readloop();
    showloop();
  }

  else if (gamestate == GAMEOVER)
  {
    allblink(2);
    gamestate = START;
  }

  else if (gamestate == FINISH)
  {
    flashall(10);
    gamestate = START;
  }

}

void showloop()
{
  sequence[index] = random(0, 4);
  index++;

  for (int dex = 0; dex < index; dex++)
  {
    delay(300);
    digitalWrite(leds[sequence[dex]], HIGH);
    delay(700);
    digitalWrite(leds[sequence[dex]], LOW);
  }

  if (index == 10)
  {
    gamestate = FINISH;
  }
}

void readloop()
{
  int positionpressed;
  boolean mademistake = false;

  for (int dex = 0; dex < index & mademistake == false; dex++)
  {

    positionpressed = waitforbutton(2000);
    delay(5);
    if (positionpressed == -1 | positionpressed != sequence[dex])
    {
      mademistake = true;
      gamestate = GAMEOVER;
    }
  }
}

int waitforbutton(int delay)
{
  int buttonpressed = -1;
  int input;
  boolean buttonbackup = false;

  currentmillis = millis();
  readingmillis = currentmillis;


  while (currentmillis - readingmillis < delay & buttonbackup == false)
  {
    for (int pin = 0; pin < 4 & buttonbackup == false; pin++)
    {
      if (digitalRead(buttons[pin]) == HIGH)
      {
        buttonpressed = pin;

        while (currentmillis - readingmillis < delay & buttonbackup == false)
        {
          input = digitalRead(buttons[pin]);
          if (input == LOW)
          {
            buttonbackup = true;
          }
          currentmillis = millis();
        }

        if (currentmillis - readingmillis > delay)
        {
          buttonpressed = -1;
        }

        Serial.print("pin nummer");
        Serial.println(buttonpressed);
      }
    }
    currentmillis = millis();
  }
  return buttonpressed;
}

void startloop()
{
  int buttonpressed = -1;
  allOff();

  for (int pin = 0; pin < 4; pin++)
  {
    if (buttonpressed == -1)
    {
      digitalWrite(leds[pin], HIGH);
      buttonpressed = waitforbutton(800);
      digitalWrite(leds[pin], LOW);
    }
  }
  if (buttonpressed != -1)
  {
    delay(1000);
    index = 0;
    gamestate = PLAY;
  }
}

boolean readanybutton(int delay)
{
  boolean buttondown = false;

  currentmillis = millis();
  readingmillis = currentmillis;

  while (currentmillis - readingmillis < delay & buttondown == false)
  {
    for (int pin = 0; pin < 4; pin++)
    {
      if (digitalRead(buttons[pin]) == HIGH)
      {
        buttondown = false;
      }
    }
    currentmillis = millis();
  }
  return buttondown;
}

void allOff()
{
  for (int pin = 0; pin < 4; pin++)
  {
    digitalWrite(leds[pin], LOW);
  }
}

void allOn()
{
  for (int pin = 0; pin < 4; pin++)
  {
    digitalWrite(leds[pin], HIGH);
  }
}

void allblink(int times)
{
  for (int count = 0; count < times; count++)
  {
    allOn();
    delay(500);
    allOff();
    delay(200);
  }
}

int flashall(int times)
{
  for (int count = 0; count < times; count++)
  {
    for (int pin = 0; pin < 4; pin++)
    {
      digitalWrite(leds[pin], HIGH);
      delay(30);
      digitalWrite(leds[pin], LOW);
    }
  }
}


het zou in mijn code kunnen zitten of de hardware.

Ik hoop dat iemand mij hier mee kan helpen.


(1)Simon Says is een herinneringsspel dat een random licht patroon aangeeft en deze moet je herhalen om na het licht patroon op de knoppen te drukken.

Advertisement

Gebruikers-avatar
Berichten: 2655
Geregistreerd: 06 Aug 2016, 01:03

Re: Simon Says

Berichtdoor Koepel » 28 Jul 2017, 20:51

Oef ! Dat is niet zo maar te doorzien. De structuur van de sketch kan beter en er ontbreekt goed commentaar.

Ik denk dat het mogelijk is dat wanneer een knop dendert, dat het heel snel door de waitforbutton() rolt. Volgens mij is er geen delay die dat tegenhoudt. Iedere knop dendert, daar is een library voor: Bounce2.

Maar om dat te verbeteren... :? dat is lastig. Ergens een delay(50) tussen proppen om het te vertragen zou kunnen werken.

Je doet een analogRead(40), dat begrijp ik niet. Je kunt gewoon analogRead(A0) doen.

Berichten: 4064
Geregistreerd: 16 Okt 2013, 14:31
Woonplaats: s hertogenbosch

Re: Simon Says

Berichtdoor shooter » 29 Jul 2017, 10:18

in readanybutton maak je de twee variabelen gelijk en dus 0 en dus doet hij de while, nergens wordt de buttondown high dus dat klopt niet, die routine gaat zo snel <1 ms dus current is nog steeds gelijk en dus wordt de routine nogmaals gedaan.
paul deelen
shooter@home.nl

Berichten: 2
Geregistreerd: 28 Jul 2017, 19:39

Re: Simon Says

Berichtdoor Wynants » 29 Jul 2017, 13:19

Heel erg bedankt! ik had een delay van 5 ms geplaatst dit was blijkbaar te weinig. ik heb deze verhoogt naar 50 en nu werkt hij zoals de bedoeling is!
Ik kan nu weer verder!

Gebruikers-avatar
Berichten: 2655
Geregistreerd: 06 Aug 2016, 01:03

Re: Simon Says

Berichtdoor Koepel » 29 Jul 2017, 20:34

O nee :o
Wat gebeurt er als je nog iets wilt wijzigen ?

Ik weet eigenlijk maar één goede oplossing, en dat is opnieuw beginnen. Maak eerst een goede beschrijving, beschrijf ook alle timeouts. Maak het iets meer abstract. Dus onderaan een laag voor de knoppen, en daar zou ik Bounce2 voor gebruiken.
Je loop() is nu een state-machine, maar dat wordt meestal anders opgeschreven. En vooral commentaar ontbreekt.

In de taal 'c' wordt het niet lelijk gevonden als je halverwege een functie er uit springt (met return) wanneer er een error situatie ontstaat. Dus als de knop niet goed is, kun je ook een return geven om uit die functie te springen.

Terug naar Overige projecten

Wie is er online?

Gebruikers in dit forum: Google [Bot] en 8 gasten