The ISBoT Ultrasonic Rangefinder System

A detailed report for receiving distance data from four Ultrasonic Rangefinders in NI LabVIEW.

ISBoT creators: John Rehm and Joe Gallo, 2004
ISBT (Integrated Science, Business, and Technology )Program @ La Salle University
Philadelphia, PA

 

 


In order to navigate, the ISBoT must be capable of receiving distances from each of its four SRF08 Ultrasonic Range Finder’s. The SRF08 range finders are high performance sensors that use sonar to detect objects. They require only 5 Volts, connect through an I2C Bus, operate at a 40 kHz frequency, have a max. range of 6 meters and a min of 3 cm, and even do all of their own pulse timing internally. The best way to integrate the information coming from the SRF08’s is to do so through a Basic Stamp2 microcontroller.

An SRF08 rangefinder (back / front)

 

The Basic Stamp II

The Basic Stamp 2 (BS2) is a small microcontroller (tiny computer) that has a chip, that responds to commands in the BASIC Language. The BS2 has internal memory (RAM and EEPROM), its own 5Volt regulator, many I/O pins, and many built in commands for math and I/O pin operations. PBASIC (Parallax BASIC) is the language developed by the BS2’s manufacturer, Parallax. Updated versions of “The BASIC Stamp Windows Editor” (we used version 2.1 beta1) can be found on Parallax’s ‘downloads’ section of www.parallax.com. This small program will upload PBASIC code to the internal memory map on the BS2 through a serial (RS232) cable from the PC to the Stamps’ I/O pins.

The above has been reproduced from the ‘Basic Stamp programming manual’ (http://www.parallax.com/dl/docs/prod/stamps/BasicStampMan.pdf) for reference and educational purposes. To connect the BS2 to the RS232 serial cable we connected one end of an RS232 to a PC - then spliced the other end and connected the four appropriate wires (only four are needed) to the BS2 positions 1 – 4 (SOUT, SIN, ATN, VSS). We found the RS232 pins by testing for continuity using a digital multimeter. The stamp is also powered by connecting positive 5V to position 24 (VIN) and ground to position 23 (VSS). A Heathkit regulates power with a built-in voltage regulator.

We could then verify our connection by running a simple ‘debug’ command through the Stamp editor and receive the echo.

'{$STAMP BS2}
DEBUG ‘Hello World!’

The above PBASIC code run in the editor window will return a ‘Hello World!’ window when the connection is made.

Once the BS2 is connected to the PC, the SRF08’s could be connected to the Stamp. The SRF08’s utilize the I2C Bus for communication. The SDA (data) and SCL (clock) lines connect to position 13 (P8) and 14 (P9) on the BS2 respectively. 4.7 k pull-up resistors are also on the SDA and SCL lines to VDD as recommended by Parallax. (The wiring diagram and code has been significantly modified for this specific case, but was based on the original source @ http://www.robot-electronics.co.uk/htm/srf08stamp.shtml)

Next, the code below must be run once for each SRF08 range finder (4 times) – changing the I2C address for each at a time. We chose e0, e2, e4, and e6.

Important note! :: Only the SRF08 for which the address is being programmed can be plugged into the circuit with the BS2, otherwise the same address will be assigned to all of the SRF08’s and noisy/inaccurate data will be returned. Therefore, the following steps must be taken to assign addresses to each range finder individually:

1) Wire only one range finder in circuit with the BS2 and turn on the power.
2) Run the below code in the editor window to program the SRF08’s unique address into the BS2’s memory.
3) Run a simple ‘DEBUG’ through the BS2’s memory to clear it.

Repeat steps 1 – 3 for each SRF08 changing only the address number in the PBASIC code each time.

PBASIC code for assigning SRF08 Address:

 

'{$STAMP BS2}

'***********************************************************
'**                                                                                                              **
'**                             I2C Routines for the Basic Stamp                           **
'**                     to change the address of SRF08 Rangefinder                   **
'**                                                                                                              **
'**                            Copyright 2002 - Devantech Ltd                             **
'**                 Commercial use of this software is prohibited                    **
'**                   Private and educational use only is permitted                   **
'**                                                                                                              **
'**                       Written by Gerald Coe - January 2002                         **
'**                                                                                                              **
'**                   This Code has been Tested on BS2 and BS2p                  **
'**               It should work equally well on the BS2e and BS2sx             **
'**                                                                                                              **
'***********************************************************

NEW_SRF08_ADDRESS con $e2          ' Place new address for SRF08 here
'available addresses are: e0, e2, e4, e6, e8, ea, ec, ee
'                         f0, f2, f4, f6, f8, fa, fc, fe

SCL con 9                          ' I2C clock
SDA con 8                          ' I2C data
SDAin var in8
SDAout var out8                    ' To change the pins used, alter these 5 lines
SDAdir var dir8                    ' The 4 SDA numbers must be the same, of course

loop var byte                      ' just a looping counter
I2cBuf var byte                    ' I2c read/write buffer
I2cAddr var byte                   ' Address of I2C device
I2cReg var byte                    ' Register number within I2C device
I2cData var word                   ' Data to read/write
I2cAck var bit                     ' Acknowledge bit

Main:

I2cAddr = 0                        ' use general broadcast address ($00) if don't know current SRF08 address
I2cReg = 0                         ' command register
I2cData = $a0                      ' 1st command in address change sequence
gosub I2cByteWrite
I2cData = $aa                      ' 2nd command in address change sequence
gosub I2cByteWrite
I2cData = $a5                      ' 3rd command in address change sequence
gosub I2cByteWrite
I2cData = NEW_SRF08_ADDRESS
gosub I2cByteWrite

endlessloop:
I2cAddr = NEW_SRF08_ADDRESS
I2cReg = 0
I2cData = 81                       ' one of the ranging commands
gosub I2cByteWrite
pause 70                           ' wait for ranging to complete
goto endlessloop

'--------------------------------------------------------------------------------------------
' I2C subroutines follow
'--------------------------------------------------------------------------------------------

I2cByteWrite:                      ' writes I2cData.lowbyte to I2cReg at I2cAddr
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
I2cBuf = I2cData.lowbyte
gosub I2cOutByte                   ' send the data
gosub I2cStop
return

I2cWordWrite:                      ' writes I2cData to I2cReg at I2cAddr
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
I2cBuf = I2cData.highbyte
gosub I2cOutByte                   ' send the data - high byte
I2cBuf = I2cData.lowbyte
gosub I2cOutByte                   ' send the data - low byte
gosub I2cStop
return

I2CByteRead:
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
gosub I2cStart                     ' repeated start
I2cBuf = I2cAddr | 1
gosub I2cOutByte                   ' send device address (with read set)
I2cAck = 0                         ' send Nak
gosub I2cInByte
I2cData.lowbyte = I2cBuf           ' read the data
I2cData.highbyte = 0
gosub I2cStop
return

I2CWordRead:
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
gosub I2cStart                     ' repeated start
I2cBuf = I2cAddr | 1
I2cAck = 1                         ' send Ack
gosub I2cOutByte                   ' send device address (with read set)
gosub I2cInByte
I2cData.highbyte = I2cBuf          ' read the data
I2cAck = 0                           ' send Nak
gosub I2cInByte
I2cData.lowbyte = I2cBuf
gosub I2cStop
return

I2cOutByte:
shiftout SDA, SCL, MSBFIRST, [I2cBuf]
input SDA
high SCL                           ' clock in the ack' bit
low SCL
return

I2cInByte:
shiftin SDA, SCL, MSBPRE, [I2cBuf]
SDAout = 0
SDAdir = I2cAck
high SCL                           ' clock out the ack' bit
low SCL
input SDA
return

I2cStart                           ' I2C start bit sequence
high SDA
high SCL
low SDA
low SCL
return

I2cStop:                           ' I2C stop bit sequence
low SDA
high SCL
high SDA
return

 

Once the I2C address’ have been assigned for each, then all of the SRF08’s can be connected to the BS2 circuit to give range readings and light data through the Stamp editor’s Debug window. Use the code below:

'{$STAMP BS2}

'***********************************************************
'**                                                                                                              **
'**                             I2C Routines for the Basic Stamp                           **
'**                     Controlling Two SRF08 Ultrasonic Rangers                   **
'**                                                                                                              **
'**                            Copyright 2002 - Devantech Ltd                             **
'**                 Commercial use of this software is prohibited                    **
'**                   Private and educational use only is permitted                   **
'**                                                                                                              **
'**                       Written by Gerald Coe - January 2002                         **
'**                                                                                                              **
'**                   This Code has been Tested on BS2 and BS2p                  **
'**               It should work equally well on the BS2e and BS2sx             **
'**                                                                                                              **
'***********************************************************

SCL con 9                          ' I2C clock
SDA con 8                          ' I2C data
SDAin var in8
SDAout var out8                    ' To change the pins used, alter these 5 lines
SDAdir var dir8                    ' The 4 SDA numbers must be the same, of course

loop var byte                      ' just a looping counter
I2cBuf var byte                    ' I2c read/write buffer
I2cAddr var byte                   ' Address of I2C device
I2cReg var byte                    ' Register number within I2C device
I2cData var word                   ' Data to read/write
I2cAck var bit                     ' Acknowledge bit

Main:

' 1st SRF08 Ranger
I2cAddr = $e0
I2cReg = 0
I2cData = 81                       ' Ranging command - 80 for inches, 81 for cm, 82 for uS
gosub I2cByteWrite
pause 70                           ' wait for ranging to complete
I2cReg = 1                         ' address of light sensor register
gosub I2cByteRead
debug 2,0,0, "Light Sensor1 ", dec3 I2cData
I2cReg = 2                         ' address of first ranging result
gosub I2cWordRead
debug 2,0,1, "Range1 ", dec4 I2cData

' 2nd SRF08 Ranger
I2cAddr = $e2
I2cReg = 0
I2cData = 81                       ' Ranging command - 80 for inches, 81 for cm, 82 for uS
gosub I2cByteWrite
pause 70                           ' wait for ranging to complete
I2cReg = 1                         ' address of light sensor register
gosub I2cByteRead
debug 2,0,3, "Light Sensor2 ", dec3 I2cData
I2cReg = 2                         ' address of first ranging result
gosub I2cWordRead
debug 2,0,4, "Range2 ", dec4 I2cData

goto main

'--------------------------------------------------------------------------------------------
' I2C subroutines follow
'--------------------------------------------------------------------------------------------

I2cByteWrite:                      ' writes I2cData.lowbyte to I2cReg at I2cAddr
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
I2cBuf = I2cData.lowbyte
gosub I2cOutByte                   ' send the data
gosub I2cStop
return

I2cWordWrite:                      ' writes I2cData to I2cReg at I2cAddr
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
I2cBuf = I2cData.highbyte
gosub I2cOutByte                   ' send the data - high byte
I2cBuf = I2cData.lowbyte
gosub I2cOutByte                   ' send the data - low byte
gosub I2cStop
return

I2CByteRead:
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
gosub I2cStart                     ' repeated start
I2cBuf = I2cAddr | 1
gosub I2cOutByte                   ' send device address (with read set)
I2cAck = 0                         ' send Nak
gosub I2cInByte
I2cData.lowbyte = I2cBuf           ' read the data
I2cData.highbyte = 0
gosub I2cStop
return

I2CWordRead:
gosub I2cStart
I2cBuf = I2cAddr
gosub I2cOutByte                   ' send device address
I2cBuf = I2cReg
gosub I2cOutByte                   ' send register number
gosub I2cStart                     ' repeated start
I2cBuf = I2cAddr | 1
I2cAck = 1                         ' send Ack
gosub I2cOutByte                   ' send device address (with read set)
gosub I2cInByte
I2cData.highbyte = I2cBuf          ' read the data
I2cAck = 0                         ' send Nak
gosub I2cInByte
I2cData.lowbyte = I2cBuf
gosub I2cStop
return

I2cOutByte:
shiftout SDA, SCL, MSBFIRST, [I2cBuf]
input SDA
high SCL                           ' clock in the ack' bit
low SCL
return

I2cInByte:
shiftin SDA, SCL, MSBPRE, [I2cBuf]
SDAout = 0
SDAdir = I2cAck
high SCL                           ' clock out the ack' bit
low SCL
input SDA
return

I2cStart                           ' I2C start bit sequence
high SDA
high SCL
low SDA
low SCL
return

I2cStop:                            ' I2C stop bit sequence
low SDA
high SCL
high SDA
return

The code was then modified (shown below) using the Pulse-Width-Modulation (PWM) function of PBASIC to send the data out of assigned pins on the Basic Stamp 2. The PWM function converts the digital data from the sensors to analog data that can then be converted to a representative voltage (V) and sent to LabVIEW.

PWM works with the BS2 (a purely digital device) to output analog signals by alternating the voltages sent out of the Stamp rapidly from high (5V) to low (0V) therefore sending out alternating 1's and 0's which are proportional to the specified 'Duty'. 'Duty' is a variable between 0-255 (low 0V - high 5V). The proportion of 1's to 0's is called the 'Duty Cycle' and represents the voltage data (example: a high duty cycle would mean a high voltage, or a low duty cycle would represnt a low voltage).

Average Voltage = ( Duty / 255 ) * 5 volts

See the information below the code for more on how the PWM process works :

'{$STAMP BS2}

'***********************************************************
'**                                                                                                              **
'**                             I2C Routines for the Basic Stamp                           **
'**                     Controlling Two SRF08 Ultrasonic Rangers                   **
'**                                                                                                              **
'**                            Copyright 2002 - Devantech Ltd                             **
'**                 Commercial use of this software is prohibited                    **
'**                   Private and educational use only is permitted                   **
'**                                                                                                              **
'**                       Written by Gerald Coe - January 2002                         **
'**                                                                                                              **
'**                   This Code has been Tested on BS2 and BS2p                  **
'**               It should work equally well on the BS2e and BS2sx             **
'**                                                                                                              **
'***********************************************************

'***********************************************************
'**                    This program has been modified by the LaSalle                  **
'**                         University ISBOT Team (04.08.2004)                            **
'**                                                                                                                **
'**                   The modification utilizes 4 SRF08's and returns               **
'**                     the values throught the PWM function as an                 **
'**                                            analog output.                                             **
'***********************************************************

SCL CON 9                                     ' I2C clock
SDA CON 8                                    ' I2C data
SDAin VAR IN8
SDAout VAR OUT8                         ' To change the pins used, alter these 5 lines
SDAdir VAR DIR8                           ' The 4 SDA numbers must be the same, of course

loop VAR Byte                                   ' just a looping counter
I2cBuf VAR Byte                                ' I2c read/write buffer
I2cAddr VAR Byte                             ' Address of I2C device
I2cReg VAR Byte                               ' Register number within I2C device
I2cData VAR Word                            ' Data to read/write
I2cAck VAR Bit                                  ' Acknowledge bit

SRF1CM VAR Word                         'SRF 1 value in CM
SRF1D VAR Word                             'SRF 1 value in Duty (0-255)

SRF2CM VAR Word                         'SRF 2 value in CM
SRF2D VAR Word                            'SRF 2 value in Duty (0-255)

SRF3CM VAR Word                         'SRF 3 value in CM
SRF3D VAR Word                            'SRF 3 value in Duty (0-255)

SRF4CM VAR Word                          'SRF 4 value in CM
SRF4D VAR Word                             'SRF 4 value in Duty (0-255)

Main:
' 1st SRF08 Ranger
I2cAddr = $e0
I2cReg = 0
I2cData = 81                                                           ' Rangeing command - 80 for inches, 81 for cm, 82 for uS
GOSUB I2cByteWrite
PAUSE 70                                                               ' wait for ranging to complete
I2cReg = 1                                                               ' address of light sensor register
GOSUB I2cByteRead
DEBUG 2,0,0, "Light Sensor1 ", DEC3 I2cData
I2cReg = 2                                                               ' address of first ranging result
GOSUB I2cWordRead
DEBUG 2,0,1, "Range1 ", DEC4 I2cData
GOSUB CMtoD
                                                                               'PWM Pin, Duty, Cycle (4-7, SRFxD, 40)
PWM 4, SRF1D, 40

' 2nd SRF08 Ranger
I2cAddr = $e2
I2cReg = 0
I2cData = 81                                                         ' Rangeing command - 80 for inches, 81 for cm, 82 for uS
GOSUB I2cByteWrite
PAUSE 70                                                             ' wait for ranging to complete
I2cReg = 1                                                             ' address of light sensor register
GOSUB I2cByteRead
DEBUG 2,0,3, "Light Sensor2 ", DEC3 I2cData
I2cReg = 2                                                             ' address of first ranging result
GOSUB I2cWordRead
DEBUG 2,0,4, "Range2 ", DEC4 I2cData
GOSUB CMtoD2
                                                                              'PWM Pin, Duty, Cycle (4-7, SRFxD, 40)
PWM 5, SRF2D, 40

' 3rd SRF08 Ranger
I2cAddr = $e4
I2cReg = 0
I2cData = 81                                                        ' Rangeing command - 80 for inches, 81 for cm, 82 for uS
GOSUB I2cByteWrite
PAUSE 70                                                           ' wait for ranging to complete
I2cReg = 1                                                           ' address of light sensor register
GOSUB I2cByteRead
DEBUG 2,0,6, "Light Sensor3 ", DEC3 I2cData
I2cReg = 2                                                           ' address of first ranging result
GOSUB I2cWordRead
DEBUG 2,0,7, "Range3 ", DEC4 I2cData
GOSUB CMtoD3
                                                                            'PWM Pin, Duty, Cycle (4-7, SRFxD, 40)
PWM 6, SRF3D, 40

' 4th SRF08 Ranger
I2cAddr = $e6
I2cReg = 0
I2cData = 81                                                       ' Rangeing command - 80 for inches, 81 for cm, 82 for uS
GOSUB I2cByteWrite
PAUSE 70                                                           ' wait for ranging to complete
I2cReg = 1                                                           ' address of light sensor register
GOSUB I2cByteRead
DEBUG 2,0,9, "Light Sensor4 ", DEC3 I2cData
I2cReg = 2                                                           ' address of first ranging result
GOSUB I2cWordRead
DEBUG 2,0,10, "Range4 ", DEC4 I2cData
GOSUB CMtoD4
                                                                             'PWM Pin, Duty, Cycle (4-7, SRFxD, 40)
PWM 7, SRF4D, 40

GOTO main


'--------------------------------------------------------------------------------------------
' I2C subroutines follow
'--------------------------------------------------------------------------------------------

I2cByteWrite:                                  ' writes I2cData.lowbyte to I2cReg at I2cAddr
GOSUB I2cStart
I2cBuf = I2cAddr
GOSUB I2cOutByte                        ' send device address
I2cBuf = I2cReg
GOSUB I2cOutByte                        ' send register number
I2cBuf = I2cData.LOWBYTE
GOSUB I2cOutByte                        ' send the data
GOSUB I2cStop
RETURN


I2cWordWrite:                                ' writes I2cData to I2cReg at I2cAddr
GOSUB I2cStart
I2cBuf = I2cAddr
GOSUB I2cOutByte                         ' send device address
I2cBuf = I2cReg
GOSUB I2cOutByte                         ' send register number
I2cBuf = I2cData.HIGHBYTE
GOSUB I2cOutByte                         ' send the data - high byte
I2cBuf = I2cData.LOWBYTE
GOSUB I2cOutByte                         ' send the data - low byte
GOSUB I2cStop
RETURN


I2CByteRead:
GOSUB I2cStart
I2cBuf = I2cAddr
GOSUB I2cOutByte                        ' send device address
I2cBuf = I2cReg
GOSUB I2cOutByte                        ' send register number
GOSUB I2cStart                              ' repeated start
I2cBuf = I2cAddr | 1
GOSUB I2cOutByte                        ' send device address (with read set)
I2cAck = 0                                      ' send Nak
GOSUB I2cInByte
I2cData.LOWBYTE = I2cBuf         ' read the data
I2cData.HIGHBYTE = 0
GOSUB I2cStop
RETURN


I2CWordRead:
GOSUB I2cStart
I2cBuf = I2cAddr
GOSUB I2cOutByte                       ' send device address
I2cBuf = I2cReg
GOSUB I2cOutByte                       ' send register number
GOSUB I2cStart                             ' repeated start
I2cBuf = I2cAddr | 1
I2cAck = 1                                      ' send Ack
GOSUB I2cOutByte                        ' send device address (with read set)
GOSUB I2cInByte
I2cData.HIGHBYTE = I2cBuf          ' read the data
I2cAck = 0                                       ' send Nak
GOSUB I2cInByte
I2cData.LOWBYTE = I2cBuf
GOSUB I2cStop
RETURN


I2cOutByte:
SHIFTOUT SDA, SCL, MSBFIRST, [I2cBuf]
INPUT SDA
HIGH SCL                                                       ' clock in the ack' bit
LOW SCL
RETURN


I2cInByte:
SHIFTIN SDA, SCL, MSBPRE, [I2cBuf]
SDAout = 0
SDAdir = I2cAck
HIGH SCL                                                     ' clock out the ack' bit
LOW SCL
INPUT SDA
RETURN


I2cStart                                                          ' I2C start bit sequence
HIGH SDA
HIGH SCL
LOW SDA
LOW SCL
RETURN


I2CSTop:                                                      ' I2C stop bit sequence
LOW SDA
HIGH SCL
HIGH SDA
RETURN

CMtoD:
SRF1CM = I2cData
SRF1D = ((42 * SRF1CM) - 27 ) / 100
RETURN

CMtoD2:
SRF2CM = I2cData
SRF2D = ((42 * SRF2CM) - 27 ) / 100
RETURN

CMtoD3:
SRF3CM = I2cData
SRF3D = ((42 * SRF3CM) - 27 ) / 100
RETURN

CMtoD4:
SRF4CM = I2cData
SRF4D = ((42 * SRF4CM) - 27 ) / 100
RETURN

 

Additionally, since the BS2 is sending out pulses of voltages on each assigned pin, the voltages must be filtered so that only the average voltage is stored. To acomplish this task the signal conditioning circuit below is constructed for the output voltage from each individual pin and is filtered through it on its way to the host PC's DAQ.

The capacitor / resistor circuit will hold the charge sent from the PWM function for a short period after the function has finished - allowing for a steady signal to be sent. The capactitor must be charged and and allowed to discharge for the appropriate amount of time in between signals.

Charge time = 4 * R * C

The equation to calculate the charge time (Cycle) uses the value of the resistor (R) and the value of the capacitor (C) to calculate the time in milliseconds. Therefore for the example above using a 10k (10 x 103 ohm) resistor and a 1 µF (1 x 10-6 F) capacitor:

Charge time = 4 * 10 x 103 * 1 x 10-6 =

40 x 10-3 seconds = ( 40 ms.)

(A great deal of further detail on the above information on the PWM function can be found starting on page 247 in the Basic Stamp II Manual found here: http://www.parallax.com/dl/docs/prod/stamps/BasicStampMan.pdf )

 

* * * *

 

 

The distances from the rangefinders must be converted to a representative voltage before being output.

The following equation can be generated from the data given by the above graph:

Duty = ( ( 42 * X ) - 27 ) / 100

The duty can be calculated in the PBASIC code for each rangefinder's distance data (X) using the slope equation ( y=mx+b) where m=0.4255 (slope) and b=0.2764 (y-intercept). The equation compensates for the y-intercept and uses the slope to give a representative Duty value (in Volts) for each SRF08 rangefinders distance (in centimeters). This is the data format that will allow the BS2 to send the analog data to the host PC.

The graph above is useful in translating the Duty (V) back again into a distance (cm) when received by a host PC.

Additional adjustments need to be made to the data because it was found that as Duty went up (0 to 255) the calculated voltages (what would be the voltages in an error-free World) increasingly varied from the actual (measured, real-World) measurements by as much as 15% error. The above graph was drawn to show the percentage error calibrations that need to be made for the specific SRF08 rangefinders being used.

A trendline yields a polynomial equation representative of the error :

0 = 0.0407 x2 + 1.0571 x+ (- 0.0175 - y)

The quadratic equation can then be used to solve for X (= distance in cm) :

 

* * * *

 

Once the data is output from the Basic Stamp II, processed through the capacitor circuit, and received by the DAQ Card on the Host PC, it must be translated back from Duty-voltage to distance in centimeters again. To acomplish this task a program is written that mathmatically uses the original BS2 PWM equation for calculating Duty ( Duty = ( ( 42 * X ) - 27 ) / 100 ) and works it backwards.

Below is the LabVIEW sub-VI that accepts Volts (Duty) as an input and returns a distance in centimeters as the output:

 

Although the above VI (Virtual Instrument) manipulates the data to the desired format, the data needs to be received by the DAQ Card and the Host PC before anyother step (shown below) :

 

 

Once again, The Systems View :