looped void problem

Hey,

I have a mobile robot platform with a servo on top and on that servo is a ping-sensor so the ping-sensor can look forward, left and right, it also has a receiver.

Now, i have a small problem:
I want it so i can wirelessly transmit a number to the arduino (this works) and when the arduino receives it it calls a function to make the car drive automatically and when the number is not transmitted anymore it stops.

Now i want the automatic car-driving to look kinda-like this:

Servo looks left, right and forward and compares what the biggest distance is, it turns to the side with the biggest distance and drives forward with the ping-sensor only looking forward and when an obstacle gets close the car stops and looks around etc.

Now i have one problem:
Everytime after it turns, i think i will have to call another function from the autosteer void that gets called with the receiver, but if i do that, it will loop the autosteering forever and if the number is not received anymore it wil still automatically drive, does someone know how to get all of it in one function?

huh? do you mean the load of typing and trying to explain?

I love the work you have done here.

I smell spam.

lyron:
i think i will have to call another void from the autosteer void that gets called with the receiver, but if i do that, it will loop the autosteering forever and if the number is not received anymore it wil still automatically drive, does someone know how to get all of it in one void?

Right. I think we have a terminology problem here. You don't call voids. Here is an example:

void blink ()
{
digitalWrite (13, HIGH);
delay (500);
digitalWrite (13, LOW);
delay (500);
}

Now I know it starts with "void", but the correct term is "function". This is a function definition. The function does something, but does not return a value. Hence it has "void" at the start. The word "void" means "no return value".

AWOL:

I love the work you have done here.

I smell spam.

I love like your replies.

Ok, edited, now can someone help me with this problem?

I think you need to post code.

i solved the problem myself, but have another problem now, i have this code:

//robot car v3.6 by Niek Blankers
//Motorshield uses digital pins 11 and 3
//Receiver uses digital pin 0 (RX)
//PING))) sensor uses digital pin 7
//ping servo right = 0 degrees middle = 85 degrees left = 171 degrees
#include <AFMotor.h>
#include <Servo.h> 

Servo pingservo;  // create servo object to control a servo 
AF_DCMotor M_right(1, MOTOR12_64KHZ); // driver-side motor
AF_DCMotor M_left(2, MOTOR12_64KHZ); // passenger-side motor
const int pingPin = 2;
int message = 0; // This will hold one byte of the serial message
#define velocityright (66) /* how fast the wheels spin */
#define velocityleft  (80)
#define turntime (975)
unsigned long ping1 = microsecondsToCentimeters(ping());
unsigned long dright = 0;
unsigned long dfront = 0;
unsigned long dleft = 0;

void setup()
{
  pingservo.attach(5);
  pingservo.write(0);
  delay(400);
  pingservo.write(85);
  delay(400);
  pingservo.write(171);
  delay(400);
  pingservo.write(85);
  M_left.setSpeed(velocityleft);
  M_right.setSpeed(velocityright);
  Serial.begin(1200);  // Hardware supports up to 2400, but 1200 gives longer range
  delay(500);
}

void loop()
{
// here's gonna be like: if receivednumber = 534 so on..
autosteer();
}

void goforward()
{
   pingservo.write(85);
  M_left.run(FORWARD);
  M_right.run(FORWARD); 
 // delay(1000);
}

void turnleft()
{
   pingservo.write(85);
 M_left.run(BACKWARD);
 M_right.run(FORWARD);   
delay(turntime);
}

void turnright()
{
   M_left.run(FORWARD);
 M_right.run(BACKWARD); 
 pingservo.write(85); 
 delay(turntime);
}

void full_stop()
{
  M_left.run(RELEASE);
  M_right.run(RELEASE);
}

void autosteer()
{
  STEER:
  full_stop();
  pingservo.write(0);
  delay(600);
  dright = microsecondsToCentimeters(ping()); 

  pingservo.write(85);
  delay(400);
  dfront = microsecondsToCentimeters(ping()); 

  pingservo.write(171);
  delay(400);
  dleft = microsecondsToCentimeters(ping()); 



if ( dright && dfront && dleft < 10)
{
  //go backward
   M_left.run(BACKWARD);
    M_right.run(BACKWARD); 
     pingservo.write(85);
    delay(1950);
    pingservo.write(85);

    goforward();
    BACK1:
   if (ping1)
   {
     goto STEER;
   }
    goto BACK1;
 
}

if (dright > dfront && dleft)
  {
    //go right
    turnright();
    goforward();
    RIGHT1:
   if (ping1 < 10)
   {
     goto STEER;
   }
    goto RIGHT1;
  }

  if (dleft > dfront && dright)
  {
    //go left
  turnleft();
  goforward();
  LEFT1:
  if (ping1 < 10)
  {
   goto STEER; 
  }
  
  goto LEFT1;
  }
  if (dfront > dright && dleft)
  {
    // go forward
    goforward();
    delay(400);
    FORWARD1:
     if (ping1 < 10)
  {
   goto STEER; 
  }
  goto FORWARD1;
  }

 
  
}



unsigned long ping()
{
  // The PING))) is triggered by a HIGH pulse of 2 or more microseconds.
  // Give a short LOW pulse beforehand to ensure a clean HIGH pulse:
  pinMode(pingPin, OUTPUT);
  digitalWrite(pingPin, LOW);
  delayMicroseconds(2);
  digitalWrite(pingPin, HIGH);
  delayMicroseconds(5);
  digitalWrite(pingPin, LOW);

  // The same pin is used to read the signal from the PING))): a HIGH
  // pulse whose duration is the time (in microseconds) from the sending
  // of the ping to the reception of its echo off of an object.
  pinMode(pingPin, INPUT);
  return pulseIn(pingPin, HIGH); 
}  

unsigned long microsecondsToCentimeters(unsigned long microseconds)
{
  // The speed of sound is 340 m/s or 29 microseconds per centimeter.
  // The ping travels out and back, so to find the distance of the
  // object we take half of the distance travelled.
  return microseconds / 29 / 2;
}

but now my car won't drive at all

Any help?

Get rid of the gotos, then we can talk :wink:

but if i do that, how will i be able to have all of this in one function?

I don't know - it isn't clear to me why it should all be in one function.
The problem with "goto" is that it turns your code into instant spaghetti.

Don't get me wrong, I don't dislike "goto" per se, but I probably haven't written any code with one in for about five years (deep in the bowels of a Linux device driver).

I suspect that this:if ( dright && dfront && dleft < 10) doesn't do what you think it does, even if it does compile.

Use a "while" loop?

I've written tens of thousands of lines of code. None of them use goto (well, not in the last 40 years anyway). Get out of the habit right now. You won't regret it. :slight_smile:

I've got a feeling that this: unsigned long ping1 = microsecondsToCentimeters(ping()); probably doesn't work.

This would be initialised before the timers have been initialised (before "main", so therefore before "init".

If you need a one-off initial range, move the assignment (though not the declaration) into "setup".

i thought that if i used

if ( dright && dfront && dleft < 10)

that it will drive backward if all the distances are less than 10.

What the compiler reads it as:

if ( dright != 0 && dfront != 0 && dleft < 10)
     pingservo.write(85);
     delay(1950);
     pingservo.write(85);

After nearly two seconds, I would hope it was already there.

No. This isn't Cobol.

You are thinking "if all of (dright and dfront and dleft) are less than 10" but the compiler is not thinking like that. As AWOL is hinting, more like this:

if ( dright < 10 && dfront < 10 && dleft < 10)

Solved all of the minor issues, but how do i replace goto with "while" loops?

Well, if you promise not to tell anyone else, a "while" loop has a "goto" in it.
I know, shocking, isn't it?

What you need to do is think what the behaviour of your robot is.

Take a simple case.
Imagine your robot has to drive in a straight line until it reaches 10cm from a wall.
It then has to reverse until it is 20cm from the wall and execute a right turn.
Basic pseudo code:

motorForward ();
while (distanceMeasure () > 10) {
// nothing to do - the distanceMeasure takes care of the sonar
}
motorReverse ();
while (distanceMeasure () < 20) {
}
motorRight ();

"goto" is just a mindset engendered (IMHO) by flowcharts.

while programming i accidentally pressed a weird key combination and now in stead of normal typing cursor i get the "low stripe" thingy and if i for example go to the middle of a sentence and type something it replaces the text after the cursor with the text i am typing.

how to fix this?