Receiving bytes (Arduino + AI2)

Hallo,

Ik ben niet bepaald een pro als het aan komt op programmeren. Nu heb ik voor een schoolproject een app gemaakt op mit app inventor 2, waar ik met een switch kan wisselen tussen auto modus en manual modus (het project is een zelf rijdende robot, maar ingrijpen moet een optie zijn voor het geval hij vasthangt) en een button om de runstatus te sturen. Dit heb ik geprogrammeerd in ai2 dat als de run button in geklikt wordt de bool naar true gaat en dus run actief is, dan zal hij een 1 sturen en stuurt voor de manual modus 1 als de switch niet actief is en 0 als deze wel actief is.

Kortom ik stuur 2 bytes.

Nu heb ik een klein test programmatje gemaakt die de connectiviteit moet testen (dus nog niks met de robot zelf)

dit is de code ervoor:

#include <AltSoftSerial.h>
AltSoftSerial Bluetooth;


int data[4];
byte i = 0;

unsigned long HuidigMillis, StartMillis, VerlopenMillis, minuten, seconden, milliseconden;      // Tijds variabelen

float snelheid;

float topspeed = 0;
float Verbruikt = 0;

byte Run = 0;
byte manual = 0;
byte x_as = 0;
byte y_as = 0;



void stopwatch(void) {
  HuidigMillis = millis();
  VerlopenMillis = (HuidigMillis - StartMillis);

  milliseconden = (VerlopenMillis % 1000);
  seconden = ((VerlopenMillis / 1000) % 60);
  minuten = ((VerlopenMillis / 60000) % 60);
}



void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  Bluetooth.begin(9600);
  Serial.println("Welkom bij de AGV, dit is een kleine demo van de wireless communicatie");
  Serial.println("Ik wacht op het inklikken van de run button...");
  while (Bluetooth.available() < 2) {
    data[i] = Bluetooth.read();
    i++;
  }
  Run = data[0];
  manual = data[1];
  i = 0;
  Serial.println("Mijn status is als volgt:");
  Serial.print("Run: ");
  Serial.print(Run);
  Serial.print("      manual: ");
  Serial.print(manual);
  Serial.println();
  Serial.println();
  
  
  StartMillis = millis();
}

void loop() {
  switch (Run) {
    case 0:                                                   // Robot wordt gestopt
      StartMillis = millis();
      
      while (Bluetooth.available() >= 2) {
        data[i] = Bluetooth.read();
        i++;
      }
      Run = data[0];
      manual = data[1];
      i = 0;
      
      break;

    case 1:                                                   // Robot is gestart
      stopwatch();
      Verbruikt = Verbruikt + random(10,30);

      while (Bluetooth.available() >= 2) {
        data[i] = Bluetooth.read();
        i++;
      }
      Run = data[0];
      manual = data[1];
      i = 0;

      switch (manual) {
        case 0:                                               // Robot staat in auto modus            
          snelheid = random(1.0,15.0);
          if (snelheid > topspeed) {
            topspeed = snelheid;
          }
          Bluetooth.print(topspeed);
          Bluetooth.print(" m/s");
          Bluetooth.print("|");
          Bluetooth.print(minuten);
          Bluetooth.print(":");
          Bluetooth.print(seconden);
          Bluetooth.print(".");
          Bluetooth.print(milliseconden);
          Bluetooth.print("|");
          Bluetooth.print(Verbruikt);
          Bluetooth.print(" W");
          Bluetooth.println();
          break;

        case 1:                                               // Robot staat in manual modus
          if (Bluetooth.available() > 0) {
            data[i] = Bluetooth.read();
            i++;
          }
          Run = data[0];
          manual = data[1];
          x_as = data[2];
          y_as = data[3];

          if (i == 4) {
            i = 0;
          }
          
          if (manual == 1 && Run == 1) {
            Serial.print(Run);
            Serial.print(",   ");
            Serial.print(manual);
            Serial.print(",   ");
            Serial.print(x_as);
            Serial.print(",   ");
            Serial.print(y_as);
            Serial.println();
          }
          
          break;
      }
      break;
  }      
}

Er staat wat extra in zoals de snelheid etc. dit wil ik sturen en bepalen als de robot in automodus staat. Ook heb ik wat getest met switch cases, nog nooit gebruikt dus proberen kan geen kwaad denk ik.

Terug naar mijn punt, in de setup wacht ik op het indrukken van die run button en dan zendt hij 2 bytes. Nu heb ik geen flauw benul hoe ik dit ga uitlezen en aan mijn juiste variabel koppel, ik heb wel het een en ander rond gekeken maar daar snapte ik buiten dit concept niet fantastisch veel van.

Mijn vraag is dus hoe moet ik die bytes goed aflezen zodat ik überhaupt in mijn loop kom, want op het moment kom ik niet uit mijn setup.

Aan de hand van deze hulp kan ik dan ook alles in de loop voor het aflezen van de statussen goed maken want het is nogal wat. Misschien heeft iemand daar sowieso een betere suggestie voor, maar dat komt dan nog wel. Voor nu zou ik graag antwoord willen op mijn bovenste vraag en weten wat ik sowieso al fout doe.

groetjes,
Brum

// wacht op twee bytes
while (Bluetooth.available() < 2)
{
  // niks doen
}

Misschien dat Robin's updated Serial Input Basics je ook wat idees kan geven. Het is echter gebaseerd op het feit dat loop() eindeloos draait dus moet je een andere benadering hebben waar je bijhoudt met een variabele wat je programma moet doen.

Even voor de duidelijkheid:
1: Ik neem aan dat de Arduino in de robot zit?
2: En dat zowel de switch als de button waar je van spreekt alleen in software op je Android smartphone bestaan, en de besturing helemaal via BT plaatsvindt?
3: Welk type Arduino gebruik je?

Ik voorzie een probleem omdat je al in setup() begint met het eigenlijke programma. Dat kun je beter naar loop() verplaatsen, dan kan elke actie tenminste meer dan een keer worden gedaan.
NB.:

  • setup() wordt eenmalig uitgevoerd
  • loop() wordt eindeloos herhaald

In loop() moet je dan eerst alle inputdata verzamelen in variabelen, en daarna pas met een switch/case-constructie de gewenste acties uitvoeren.

Gebruik voor die input liever geen while(); het programma is dan geblokkeerd voor alle andere acties, en doet dus niets.

Verander byte Run = 0; even in byte run = 0;, het is wijs om consequent te zijn met de spelling.

Gaat dat goed met de poorten want altsoftserial moet ook toegewezen worden want serial is poort 0 en 1 standaard.

sterretje:

// wacht op twee bytes

while (Bluetooth.available() < 2)
{
 // niks doen
}





Misschien dat Robin's updated [Serial Input Basics](https://forum.arduino.cc/index.php?topic=396450.0) je ook wat idees kan geven. Het is echter gebaseerd op het feit dat loop() eindeloos draait dus moet je een andere benadering hebben waar je bijhoudt met een variabele wat je programma moet doen.

sowieso kan ik niet teveel van deze while loops doen lijkt me aangezien ik tijdens het wachten op de data van het switchen naar manual, aangezien tijdens de auto status het een en ander wel moet gebeuren. Of bedoel je meer in de zin van dat kan tijdens die while en op het moment dat je daaruit komt ga je toch niet meer verder met die status.
zegmaar als manual 0 is (dus op auto staat)
while (Serial.available() < 2) {
automatisch programma
}
switchen van programma
dit moet zegmaar in de loop sowieso iets komen aangezien de optie om tussen states te switchen er moet zijn. mijn voorbeeld was puur voor het wachten tot de connectie is gemaakt en dat ik aangeef dat hij mag beginnen namelijk.
hoop dat ik het nog een beetje duidelijk verwoord heb, want heb zo'n voorgevoel dat het niet helemaal duidelijk is maar dan hoor ik het graag.

Erik_Baas:
Even voor de duidelijkheid:
1: Ik neem aan dat de Arduino in de robot zit?
2: En dat zowel de switch als de button waar je van spreekt alleen in software op je Android smartphone bestaan, en de besturing helemaal via BT plaatsvindt?
3: Welk type Arduino gebruik je?

Ik voorzie een probleem omdat je al in setup() begint met het eigenlijke programma. Dat kun je beter naar loop() verplaatsen, dan kan elke actie tenminste meer dan een keer worden gedaan.
NB.:

  • setup() wordt eenmalig uitgevoerd
  • loop() wordt eindeloos herhaald

In loop() moet je dan eerst alle inputdata verzamelen in variabelen, en daarna pas met een switch/case-constructie de gewenste acties uitvoeren.

Gebruik voor die input liever geen while(); het programma is dan geblokkeerd voor alle andere acties, en doet dus niets.

Verander byte Run = 0; even in byte run = 0;, het is wijs om consequent te zijn met de spelling.

  1. Zit er inderdaad op.
  2. De run is een button die je in kan klikken en de Auto-Manual is echt een switch, bijvoorbeeld vinkjessysteem zegmaar. (allemaal op de telefoon inderdaad
  3. Uno (voor dit demo'tje althans)

met die setup wil ik bereiken dat de robot wacht op die run command, dan zal deze dus ook 1 worden en dan aan de hand van de stand van die switch wordt de manual modus 0 of 1 (in screenshot 0). vanuit daar gaat hij zijn programma starten. op basis van die gegevens gaat hij pas zijn programma in.
het is namelijk zo dat het een race robot moet zijn en dus pas moet starten als ik dat zeg dus dat kon net zo goed de setup in dacht ik, maakt weinig verschil toch.

voor die Run heb je als je run gebruikt dat hij oranje kleurt dus al een functie is lijkt me, zoveel weet ik er al niet van. dacht dat dat misschien problemen zou opleveren maar dat maakt dus niet uit dan?

shooter:
Gaat dat goed met de poorten want altsoftserial moet ook toegewezen worden want serial is poort 0 en 1 standaard.

Bij altsoftserial hoef je toch juist niet altsoftserial (8,9) aangezien dit een standaard in de library is te doen zoals je bijvoorbeeld bij softwareserial wel moet doen, of bedoel je dit niet.
Ik wilde deze poorten juist gebruiken zodat ik wel serial kan printen om even te zien of ik daad werkelijk de data ook wel krijg.

Check out my tutorial on Multitasking in Arduino, which will help with doing multiple things, like running your robot and still processing inputs

This topic was automatically closed 120 days after the last reply. New replies are no longer allowed.