Help to read analog output from MB7078 XL-MaxSonar-WRCA

I’m using this IP67 sonar: MB7078 XL-MaxSonar-WRCA with Arduino Mega (i tried to use Arduino UNO, too, but it didn’t solved the problem).

Here you can find the sonar datasheet: http://www.maxbotix.com/uploads/MB7068- … asheet.pdf

I tried to use both the analog sonar output and the PWM one but in both cases i’m not able to read correct values because it always prints random numbers or fixed ones.

For example, if i use the analog output and i try to read the analog value i always have something like sensorValue = 114 and it never changes.

I even tried to directly read values with a voltmeter, but the values seems to be always random.

In the datasheet, there is written:

(AN) This pin outputs analog voltage with a scaling factor of

(Vcc/1024) per cm. A supply of 5V yields ~4.9mV/cm., and 3.3V yields

~3.2mV/cm. Hardware limits the maximum reported range on this output

to ~700 cm at 5V and ~600 cm at 3.3V. The output is buffered and

corresponds to the most recent range data.

int sensorPin = 0;    // select the input pin for the potentiometer
int sensorValue = 0;

void setup() {
  // declare the ledPin as an OUTPUT:
  Serial.begin(9600);
}

void loop() {
  // read the value from the sensor:
  sensorValue = analogRead(sensorPin);    
  Serial.println(sensorValue);
  delay(125);             
}

I tried to simply print the analog values, but they are random.

I do not think the sonar is broken because i’ve bought in total three sonars (same model) and all of them do not output correct values.

I’m sure i’m not doing it in the correct way.

May be i have to connect some other pin?

Can you help me, please? :frowning:

I connect the Vcc and GND to Arduino GND and 5VDC and the analog output to analog pin 0 without using a resistor or a capacitors to avoid noise.

marcusbarnet:
I tried to use both the analog sonar output and the PWM one but in both cases i’m not able to read correct values because it always prints random numbers or fixed ones.

For example, if i use the analog output and i try to read the analog value i always have something like sensorValue = 114 and it never changes.

I even tried to directly read values with a voltmeter, but the values seems to be always random.

The two pins output different things. Pin 2 outputs a time varying signal whose voltage corresponds to detection strenth and distance. Look at the graphs on page 4 of the PDF and read the words on how the sensor “ranges”. It does a sweep every 99 msec. You can think of this sweep from 0 to 99 msec as being a sweep in range from 20 cm out to the max range. A voltage peak at some time in the sweep corresponds to a detection at some range. The later in time the peak occurs, the further away the object is. The bigger the peak, the stronger the return/echo.

Put an object 100 cm away and you’ll see a voltage peak/spike at some time (~5-6 msec) after the start of the sweep. Put it out at 200 cm and the peak occurs later in the sweep (~12 msec).

If you want to “see” a detection with your Arduino using this pin you’ll need to sample the analog voltage repetitively and very quickly. I’ll guess at least 1 sample every msec. If you then want to “print” this value out to the serial monitor, you’ll need to increase the baud rate to the highest number you can … so you can get the data out before the next sample comes in. 56K should work but slower will not. What you’ll see is lots and lots of low random numbers (the noise floor) with a occasional spike or 2 tossed in every 99 or so numbers.

The first spike will be the detected transmit pulse (see the graphs again) and the 2’nd spike would be your target. More targets would give you even more spikes. I’m not sure a sample every 1 msec is guaranteed to catch these peaks every time they occur, they might be too narrow (in time), but I doubt you can sample any faster and “print” the output.

You can control when the sweep starts by controlling pin4 on the sensor. If you wanted to you could turn the sweep off, and then start the sweep via pin 4 and then start an even faster sampling … but storing the samples in RAM … after some time delay after starting the sweep (see the PDF). Collect as many samples as your memory will allow and then turn the sweep and sampling off. Only after this would you “print” the stored samples out to the serial monitor. You can get a finer time/range resolution this way but it’ll happen in bursts occuring only every so often (dependant on how many samples you take and how fast you can send them to the monitor).

The analog output on pin 3 is harder to figure out. What I think is happening is that as each detection occurs, it’s range is computed and then the voltage at pin 3 is output, with that voltage being proportional to the detection range. This happens for each detection in the sweep so multiple detections will result in a ramping/staircase waveform. If there’s only 1 detection the voltage will be constant. I think this volage remains even after the target goes away, for at least for 1 hour. I’ll guess to reset the detection filter you’ll need to reset/power cycle the sensor (or perhaps toggle pin 4).

Your reading of “114” corresponds to a detection at about 114 cm. Does this sounds reasonable for your test condition ? How have you been testing the sensor(s) ?

Thanks a lot for your reply!

Now, it’s more clear! :slight_smile:

I already know that two pins output different things because the first is an analog value proportional to the distance detected and the second one is just a PWM (this second one should be more precise).

That “114” value is not related to the correct distance, unfortunately.

The main problem is that the outputs values are not in according to the real distance which i use to test the sensors.

I’m using Arduino to read sonar values and send them via UDP over the net to a C application which controls some DC motors.

Before to buy these sonars, i used some other indoor sonars (srf08) with I2C bus and they worked very well.

I’m very sad at the moment, because these new sonars seems easier to use than the previous ones, but i’m not able to get them work properly. :frowning:

For the pulse pin, i’m using this simple code:

const int pwPin = 7; 
long pulse, cm;

void setup() {
  //This opens up a serial connection to shoot the results back to the PC console
  Serial.begin(9600);
  //Set up the input pin.
  pinMode(pwPin, INPUT);
}
void loop() {

  pulse = pulseIn(pwPin, HIGH);
  //58uS per cm according with the datasheet
  cm = pulse/58;
  Serial.println(cm);
  delay(10);
}

If needed, i can post the output values.

I tested the sonars by powering them up and checking with a voltmeter the changing values on the analog output.

(when they are powered up, it is possible to ear the ping)

The problem i noticed is that even with the voltmeter, the analog output does not cover all the possible range (it should be 0 - 5V, isn’t it?) and it changes frequently so it is not possible to read correct values.

Values changes even if nothing is in front of the sonar.

(the same happens with the other two sonars i’ve bought; i have three XL-MaxSonar-WRCA sonars)

marcusbarnet:
For the pulse pin, i’m using this simple code:

I don't think the 7078 model you have does a pulse output. That's the 7068 model. Pin 2 for the 7078 is the AE (analog envelope) output. Pin 3 is the AN (analog) output, whose voltage I thought you were trying to measure before ???

marcusbarnet:
I tested the sonars by powering them up and checking with a voltmeter the changing values on the analog output.

(when they are powered up, it is possible to ear the ping)

The problem i noticed is that even with the voltmeter, the analog output does not cover all the possible range (it should be 0 - 5V, isn’t it?) and it changes frequently so it is not possible to read correct values.

Values changes even if nothing is in front of the sonar.

(the same happens with the other two sonars i’ve bought; i have three XL-MaxSonar-WRCA sonars)

How sure are you that nothing is being detected ? Which pin # are you measuring ? If there is no detection then I’d expect some low voltage out of pin 3. If something is detected … at a short range, I’d expect a low voltage out of pin 3. You need to have a detection at long range to make the pin 3 voltage be close to 5 V. Have you tried putting a big piece of plywood in front of the sensor ? Initially at close range and then slowly move it out to long range ? And then bring it back to short range ? (Alternately move the sensor close to/ far away from a wall).

A voltmeter can’t react fast enough to “see” anything on pin 2. The envelope changes too quickly (see the graphs on page 4 of the PDF). To measure pin 2 output you’ll need an oscilloscope or a really fast sampling on the Arduino.

Have you tried looking at the serial data outout on pin 5 ? It seems like that outputs 5 bytes at the end of every 99 msec sweep. All are ASCII encoded; an R, 3 characters of range data and a carriage return. If you’re just looking at a single target this might work for you.

I’m reading values from the pin #3 and i connected it to Arduino A0.

This is the sketch i’m using:

    int sensorPin = 0;    // select the input pin for the potentiometer
    int sensorValue = 0;

    void setup() {
  
      Serial.begin(57600);
    }

    void loop() {
      // read the value from the sensor:
      sensorValue = analogRead(sensorPin);   
      Serial.println(sensorValue);
      delay(20);          
    }

And below, there is the output on the serial monitor if I point the sonar against the ceiling (no object is present between the sonar and the ceiling).

As you can see, the values changes randomly and i do not know why.

http://www.dronyx.com/output.rtf

Sometimes, i try to put my hand in front of the sensor and to move it at close and long range but the values does not seem to change according on the range.

I mean: the values change even the object is fixed or if no object is present.

I did a mistake with the pulse pin, actually i have 7078 so i do not have the pulse output: thanks a lot for having explained that, i didn’t realize it.

I read carefully the datasheet and as you said the pulse pin is just for 7068 models.

I’m a little bit consufed because i’m not able to get these three sonars work well. :frowning:

P.S. serial data is outside rs232 arduino standard, i already tried to read serial data on RX1,TX1 but i receive nothing. :frowning:

marcusbarnet:
And below, there is the output on the serial monitor if I point the sonar against the ceiling (no object is present between the sonar and the ceiling). As you can see, the values changes randomly and i do not know why.

P.S. serial data is outside rs232 arduino standard, i already tried to read serial data on RX1,TX1 but i receive nothing. :frowning:

I looked at the data and I don’t know what to think of it. It’s certainly NOT what I’d expect. How far away was the ceiling ?

As for the serial output … the PDF file says something odd about the TX output. It implies it’s a lower voltage version of RS232. RS232 levels are inverted when compared to a normal logic level serial output, So I think to make the serial output readable by an Arduino you’ll need to complement the bit stream first. That is make 0’s into 1’s and 1’s into 0’s. The hardware UART won’t like the inverted bit stream but perhaps a “soft” UART might be able to read them. I don’t know much about New Soft Serial but you might want to look into using that to try to read the TX output. Or get an inverter chip and try it.

In fact, the analog output is too strange also for me.

I’d expect low values for close range objects and high values for long distances.

Ceiling was at about 3 meters.

However, i did another test: i placed the sonar out of my window and i pointed it outdoor.

No object was present in front of the sonar and i acquired the values.

What i noticed is that values changed even if no object was present and even if the sonar was always in a fixed position.

This is the new output: http://www.dronyx.com/output1.txt

(See how the values change from 500 to 150… it’s very strange for me because no event occurs)

And these are the photos:

http://www.dronyx.com/IMAG0350.jpg

http://www.dronyx.com/IMAG0351.jpg

http://www.dronyx.com/IMAG0352.jpg

(i’ve changed the arduino analog pin, now i’m using pin A8)

I prefer to not use the UART because i’ll need to use a sonar daisy chain with, at least, 6 sonars so i prefer to use analog input because it’s simpler.

Just a little question: may be the problems are related to the max current draw requested by the 5VDC sonar pin? It says it needs 100mA for each transmission.

marcusbarnet:
Just a little question: may be the problems are related to the max current draw requested by the 5VDC sonar pin? It says it needs 100mA for each transmission.

I was thinking the same thing ! You’re running the Arduino and sonar off the USB power, which should be good for 500 mA. I don’t think the Arduino draws all that much, certainly not 400 mA. So at first glance it appears you’d be OK but I don’t know that your particular USB can respond quickly to a sudden demand for current. The high demand period is during the transmit time which is supposed to be 20 cycles of a 42 kHz waveform … only 0.5 msec at worst. The odd periods in the data last much longer than that … at times. So I don’t know.

It can’t hurt to put a really big cap at the sonar power pins or to even run it off a separate supply (? battery ?). I also saw from your pics that you have the sonar +Vcc plugged into your Arduino’s Vin pin. Is this proper ? I know the USB voltage is 5V so it should work … so long as you’re using USB power. Switching to another power input might damage the sonar. That said I don’t know how much current the Arduino 5V regulator can source so I can’t say if that’s a good alternative.

A largish bypass cap (10uF or more) can’t hurt.

However, trying to catch the peaks in the envelope data with an ADC is going to be hard.

I would use the analog comparator on the ATMega. You can set it up to interrupt when the input voltage is above a certain level. Here’s a thread on the subject - http://www.arduino.cc/cgi-bin/yabb2/YaB … 1272923299 It’s complicated because you are forced to use the 1.1V bandgap as a reference (the mega doesn’t connect the AIN0 pin). You may need to use a divider (or pot) to adjust the input voltage from the 7078 to work with the bandgap voltage.

Philba:
However, trying to catch the peaks in the envelope data with an ADC is going to be hard.

I’m not sure he’s trying to do that. Then again I’m not sure what pin 3 is really outputting. Pin 2 is supposed to be the analog envelope but pin 3 is … well my interpretation of the cryptic spec … a voltage proportional to the range of the (? last?) detection. There are words in the spec about “advanced filtering” and holding the voltage even when the detection is missed. An o-scope would reveal a lot but … :frowning:

I am guilty of assuming he’s trying to get ranging information for multiple returns. On the analog output, the peaks indicate a reflection. The height of which indicates the strength of the reflection (a combination of reflectiveness and profile). A scope would, indeed, be helpful. The analog output envelope graphs on page 4 of the ds are fairly clear as to what’s going on and should be what pin 2 is outputting. I think lack of filtering means that it’s basically the raw received echo value. Pin 3 description seems to be the analog equivalent of the serial range data from pin 5.

If the goal is to produce a trace of the analog envelope strength, then a different approach is called for. I wouldn’t write each sample out but rather store them in an array and then dump the array when it’s full. So a simple approach is to wait until a max ADC reading is seen (indicating initial pulse transmission) and then, in a tight loop, read the adc value and store it in the array. Once the array is full, dump it out to the serial port. The ATMega 2560 has 8K bytes of ram so a 2 or 3K int array would work. iirc, the ADC is capable of about 10K samples/sec so a 225 mS measuring period could be saved. (the sensor’s max range is 765 cm or 225 mS.)

Also to get simple ranging info, I’d just use one of the serial channels of the Mega. Use Serial1 RX to read the data. Pretty straightforward: read 4 characters from Serial1 and write them to Serial.

By the way, voltmeter readings would appear random - the sample period has to be pretty long and I’d bet there is a fair amount of noise.

Your post (above) just kicked a neuron into working. The datasheet says the device does 20 cycles of a 42 kHz waveform. But these are probably being done as a pulse, listen, pulse, listen … type of train since I’ll bet that the transducer is both the speaker and the microphone. So the 0.5 msec period I cited above is really going to be much longer. So now I’m thinking that voltage droop may be the leading suspect. My first inclination to debug the OP’s problem would be to run the sonar off a separate battery pack and see if the problem persists. Three new standard alkalines in series would seem to be sufficient and easy enough to cobble together.

Really, thanks a lot for all your answer!

I used a DC converter to power the sonar with 5VDC and a maximum of 3.5A and then i read the values.

It seems to be stable and i did a new test with the sonar in a fixed position (70 cm from a blank wall).

With this setup, it outputs 71 or 72, then if I put an object (a book) in front of the sonar, it is able to detect the new distance.

The problems i noticed are:

  • Sonar is not able to detect object closer than 24 centimeters: if an object is present below this range, then it prints random values, for example, it can print 121 or 181 or 21 (on datasheet, it is specified that it can detect object from 20cm to 645cm and if an object is closer than 20 cm is present, it continues to output 20 but this is not true in my case)

  • If i put an object in front of the sonar and then i move it away to capture a longer distance, it displays values which are not in according to the real position: for example, the wall is at 70 cm, i put an object to 50 cm and the sonar output 120 cm, but this is not possible because there are only 70 cm in front of the sonar since then there is the wall, after few seconds, it displays the correct distance.

I tried to use a scope, but if i consider the analog output on pin3, i just have a costant line. Can i measure the analog envelope?

Just a question: can the analog envelope be more precise than the analog output? What kind of signal is it? Can i read it with Arduino?

marcusbarnet:

  • If i put an object in front of the sonar and then i move it away to capture a longer distance, it displays values which are not in according to the real position: for example, the wall is at 70 cm, i put an object to 50 cm and the sonar output 120 cm, but this is not possible because there are only 70 cm in front of the sonar since then there is the wall, after few seconds, it displays the correct distance.
I know English is not your native language but I just can't understand the above. Are you saying it takes a few seconds for the sonar to output a voltage on pin3 that corresponds to the correct distance ? If so perhaps that's what it's supposed to do. The description for the pin3 output is very vague IMO. Does it always end up outputting a correct voltage ? If so isn't that what you're looking for ? Is it the response time that's the problem now ?

marcusbarnet:
I tried to use a scope, but if i consider the analog output on pin3, i just have a costant line. Can i measure the analog envelope?

Again I’d expect a constant voltage on pin3 … if the range to the target is not changing.

marcusbarnet:
Just a question: can the analog envelope be more precise than the analog output? What kind of signal is it? Can i read it with Arduino?

It could be more accurate. You’d have to come up with a calibration curve of time delay vs distance. I’d set the scope to trigger off the input (not the line voltage) and adjust the trigger level starting from high (not triggering) and adjut it downwar until it just triggers reliably. Looking at the graphs in the PDF I see that the transmit pulse is always present in the envelope and the biggest peak as well. Use this as the start time and measure the time difference from this to the target return. That time difference should be proportional to the range-to-target. With fast enough sampling and some arduino trickery (see posts above) you should be able to have a system the detects a target and measures the range to it using just the envelope output. Afterall that’s what the PIC in the sonar is doing.

Have you looked for a robot building forum where someone has used this device and figured out what it really does ?

I’m sorry for my english, i’ll try to explain better what’s the problem.

In the datasheet, there is written this:

Objects from 3-cm to 20-cm

range as 20-cm or closer.

This is not true for me because:
  • if i put an object to 30 cm, sonar is able to detect it correctly

  • if i put the same objectt to 15 cm, sonar detect it and outputs on pin3 about 0,5V which isn’t correct because 0,5V is about 100 centimeters.

Furthermore, if i put the sensor in front of a wall at a distance of 200 centimeters and then i put an object between the sonar and the wall, the sonar detects the object with a distance which is longer than the wall distance.

For example: the distance between the sonar and the wall is 200 centimeters and sonar outputs 1,5V which is about 250 centimeters and this is not physically possible.

I added a capacitor between V+ and GND and i added also a 10K resistor in series with the pin3 analog output but nothing changed.

I tried to ask on robot building forum without any success: some guys had my same problem, but nobody helped them.

I tried also to ask to maxbotix support without any helpful answer.

I’d like to try the analog envelop output, but i don’t know how to use it: i have to read the output as i do for pin3?

What kind of serial inverted should i use to test serial data?

marcusbarnet:
I’m sorry for my english, i’ll try to explain better what’s the problem.

In the datasheet, there is written this:

Objects from 3-cm to 20-cm

range as 20-cm or closer.

This is not true for me because:
  • if i put an object to 30 cm, sonar is able to detect it correctly

  • if i put the same objectt to 15 cm, sonar detect it and outputs on pin3 about 0,5V which isn’t correct because 0,5V is about 100 centimeters.

Is this a problem in your usage ? Will you have objects closer than 20 cm ? If so there's probably no good solution other than to use a different sensor.

marcusbarnet:
Furthermore, if i put the sensor in front of a wall at a distance of 200 centimeters and then i put an object between the sonar and the wall, the sonar detects the object with a distance which is longer than the wall distance.

For example: the distance between the sonar and the wall is 200 centimeters and sonar outputs 1,5V which is about 250 centimeters and this is not physically possible.

I'll guess your sensor is detecting reflections from the close object coming off the back wall. What i think is happening is this. The transmitted burst hits the close object and the echo off that gets detected early. I'd expect pin3 to output a voltage proportional to this range, *but only until the next detection happens*. Then the transmitted burst hits the back wall and the echo from that gets back to the sensor and detected sometime later than the 1'st echo. Again I'd expect pin3 to output a voltage proportional to the 200 cm range, replacing the 1'st voltage output. Then some of the sound reflecting off the back wall hits the back of close object. It bounces off of the back and hits the back wall, for a 2'nd time. The echo from this, coming off the back wall, now travels to the sensor and gets detected last. For a third time pin 3 outputs a voltage proportional to this long distance, replacing the last output. The distance indicated should be = (the 200 cm to the wall + some distance from that wall to the close object times 2 + the distance to the wall again) / 2. If you had another object 100 cm from the sensor, which is also 100 cm from the wall, I might expect the voltage to be proportional to (200 + 100*2 +200)/2 = 300 cm or ~1.5 V.

Does this make sense ? Does it agree with your measurements ?

I note that I’d think that 1.5V would be about a 300 cm distance. IIRC the scale factor was 4.9 mV/cm for a sensor running off 5V.

The solution to this problem, if I’m correct, is not easy. You need to reduce the output power or decrease the sensitivity of the sonar. You might be able to do the first by reducing the supply voltage. Be aware this changes the scale factor at pin3. You could try to “muffle” the sonar by placing some acoustic foam in front of it. How big a problem do you expect this to be in your usage ?

marcusbarnet:
I’d like to try the analog envelop output, but i don’t know how to use it: i have to read the output as i do for pin3?

Read the posts above about reading pin2 with the Arduino. You'll need to sampe very quickly and then do some processing to decide what reflection (if there are multiple ones) is the one you want. Look at the graphs in the PDF file. They show the output of pin2 for some differing cases.

marcusbarnet:
What kind of serial inverted should i use to test serial data?

See if you can find a 74LS04.

http://www.ti.com/lit/ds/symlink/sn74ls04.pdf

You could also make a logic inverter with a transistor and 2 resistors.

http://4.bp.blogspot.com/_sqidiQSxJp0/T … 1600/1.JPG

Your English is fine. It just means you have to be very specific in saying what you want to say. Like talking to a dumb child. :mrgreen:

A couple of thoughts.

  • this wouldn’t be the first time (nor last!) that a datasheet was incorrect.

  • if your scope is digital then you should be able to capture the pin 3 envelope output and see the waveforms. if it’s analog with no storage, you can still see the pin 3 envelope. Set your sweep fairly low, 10 hz if possible (datasheet says measurement period is 99 mS).

  • If the envelope output is noisy, I’d consider using a simple low pass filter with a cutoff of say 20-50Khz.

If you want to use the envelope output, look at my posting earlier describing how to do it. I’d first dump the data to your PC and look at a graph of the data to see if it makes sense. It should be similar to the o’scope display. From there, I’d modify the capture code to save information about each peak and then use that for range.

Hi to all,

thanks a lot for your help and for all your suggestions!

Yesterday i tested my sonars in lab with one of my friends who has been studying sonars for three years.

We have realized that sonars work fine, but they are not suitable for my application and, in particular, they are designed for water tanks (or similar) applications; it’s for these reason they have a very narrow beam and give a lots of random values when they are used in open environment.

Unfortunately, all these information were not written in the datasheet.

I used the inverter to read the rs232 data and they were according to the analog output, so nothing changed.

I decided to move to laser range sensors which are more reliable since sonars are not good for my application: they can be affected by wheater conditions (enve if they are temperature-compensated), by different temperature and by the doppler effect if they pinging while they are moving on. (I’m testing a LiDAR, at the moment)

As Philba said, wouldn’t be the 1’st time a datasheet was incorrect (or insufficient) ! Well at least you found out before you went too too far. Let me ask, does “for water tanks” mean it is supposed to be submerged ? Because there have been people asking for an underwater sonar and it would be good to know that this is one intended for that application. Most of the “hobby” ones are intended for atmospheric use and for object detection and avoidance on various robot projects. The ones SF sell are of this later type.

http://www.sparkfun.com/search/results? … t=products

You can see how different the above look, in their physical construction, when compared to the one in your pics (which seems to be in a plastic pipe fitting). I guess that should have been a clue.

(my mind is swimming with thoughts of an underwater ROV w/a true sonar for obstacle avoidance and/or mapping)