Hi Guys,
Well as I mentioned in the first posting the device basically works, but acts unpredictably on short range. Hence the need to observe the readings from the SRF02
The device is part of a monitoring system for water tank. Basically it reads the level & displays the result as a percentage. Obviously this is a very stripped down version of the code and works as it stands.
On turn on one of the LED's counts from 0 to 9, and it then starts to measure distance, and hence percentage.
The problem was the debug only responded to the first occurrence in the program, but the device was working.
I now know the problem code is in using the address $59 to store depth,
Depth = $C0
poke depth,temp1
Initially I had the "Depth = $5A The code below uses address$C0 and works well. From my reading of the manual; " ADdresses $50 to $7E are freely available for use.
Does anyone know why there is an apparent clash between Debug/poke @ address $5A, and an SRF02 in i2c mode?
Code:
#Picaxe 28x
#Gosubs 256
#Freq M4 'Set CPU Frequency at 4 mhz.
'
'System Variables
'EEPROM Allocations
symbol TOP = 4 'Tank distance from Sensor to water when full in CM
symbol BOT = 6 'Tank distance from Sensor to water when empty in CM
'
'Temporary Storage registers accesed by Pek & Poke ($50 to $7F) & ($C0 to $EF)
symbol READSTART = $50 'Location of first of 10 tank readings as a reader
symbol READSTOP = $59 'Location of last of 10 tank readings as a tank evel reader.
Symbol Depth = $C0 'Value of max depth, i.e. Top-bottom in cm
'
'Temporary PICAXE registers 13 available
symbol TEMP1 = b0
symbol TEMP2 = b1
symbol TEMP3 = b2
symbol TEMP4 = b3
symbol TEMP5 = b4
symbol TEMP6 = b5
symbol TEMP7 = b6
symbol TEMP8 = b7
symbol TEMPN = b8 'Address pointer for storing readings
symbol Counter1 = b9
symbol Counter2 = b10
symbol DATAPER = b11'Reading of the tanks in % as Binary 0% to 100%
symbol DATAL = b13 'LSB of tank reading in% 0-9 as BCD
symbol DATAH = b12 'MSB of tank reading in% 10-90 as BCD
'Picaxe Pins Allocation
Symbol LEDMSB = 1
Symbol LEDLSB = 0
'
'7 segment display look-up table
'DISPLAY ELEMENTS ABCDEFG
'bit 76543210
'pin 22222222
' 87654321
symbol SEGZ = %00000001 'Blank
symbol SEG0 = %11111101 '0
symbol SEG1 = %01100001 '1
symbol SEG2 = %11011011 '2
symbol SEG3 = %11110011 '3
symbol SEG4 = %01100111 '4
symbol SEG5 = %10110111 '5
symbol SEG6 = %10111111 '6
symbol SEG7 = %11100001 '7
symbol SEG8 = %11111111 '8
symbol SEG9 = %11110111 '9
symbol SEGM = %10011111 'E
symbol SEGH = %01101111 'H
symbol SEGL = %00011101 'L
symbol SEGP = %11001111 'P
Symbol SEGT = %00011111 't
Symbol SEGA = %00000011 'Segment a O/P 0
Symbol SEGB = %00000101 'Segment b O/P 1
Symbol SEGC = %00001001 'Segment c O/P 2
Symbol SEGD = %00010001 'Segment d O/P 3
Symbol SEGE = %00100001 'Segment e O/P 4
Symbol SEGF = %01000001 'Segment f O/P 5
Symbol SEGG = %10000001 'Segment g O/P 6
Symbol Dpoint = 0
'
'START OF PROGRAM
'Running sequence is
'1 Power up
'2 Initialisation
'3 Read Level
'4 Average level over ten readngs
'5 Convert for display: 7 seg display decoding done in 28x
'6 Display Results
'7 Go back to 2
'
'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
'X X
'X START and MAIN PROGRAM X
'X X
'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
'
Main:
gosub inital 'Sets up I/O Ports
starta:
startb:
gosub level 'Obtains Water Level
goto startb
'
'INITIALISATION
'
inital:
'Set-up I/O Pins C
'there is 2 modes for these pins.
'Mode 1 The pins are used for outputtimg data to the 7 segment displays.
'Mode 2 Pins C0 & C1 are input pins for sensing the state of the outboard level sensors.
'I/O C0-C6 are data and it does not matter as they change at the first O/P
'I/O C7 is the serial I/P pin and is left as an input
'
'Set-up of O/P pins Out 0to7
'I/O 0 Pin 11 Not used default is 1 I/P Dir 0
'I/O 2 Pin 13 Enables 7 seg Disp 1 RHS LSB default is 0 O/P Dir 1
'I/O 3 Pin 14 Enables 7 seg Disp 2 LHS MSB default is 0 O/P Dir 1
'I/O 4 Pin 15 Not Used default is 1 I/P Dir 0
let pinsc = %01010011 'As above
'this section sets the limits for the tank
Write top,10 'Distance from SRF02 to water when full
Write BOT,250 'Distance from SRF02 to bottom of tank
i2cslave $E0,i2cfast,i2cbyte
'
initiala: 'This section displays 0 through 9 on the 7 seg displays, as a lamp check
TEMP2 = SEGZ
TEMP1 = SEGZ
Temp7 = 1
gosub disply 'displays blanks, clears display.
TEMP7 = 1 'Time LED's are on set to 1 for debug,
For Counter2 = 0 to 9
DATAL = Counter2 'Set LSB digit at Counter Number
DATAH = 0
gosub disphl '
next Counter2
TEMPN = readstart
return
'
'LEVEL
'
'This section
'1 Calculates the distance between the full & empty % readings of the tank
'2 reads from the SRF02, @levela
'3 then calculates the water level as a %
'4 Stores that % in one of ten addresses $50-$59
'5 Then averages the 10 readings, this is to avoid false readings @ dataaverage
'6 Stores result in DATAPER
'
Level:
'
Writei2c 0,(81) 'Initata reading process
'Calculate the depth of water between full & empty i.e.Bottom - top
read BOT,Temp1
read TOP,Temp2
Temp1 = Temp1 - temp2 'calculate range in cm
poke depth,temp1 'Store result range =$62 =98
'
LevelA:
readi2c 2,(Temp2,temp1)
debug
if Temp1 =255 then LevelA
'temp1 contains the water distance in cm.
'Temp 2 has no significance as the max valid reading is 240
'
'adjust for distance between senor & water level when full
read top,temp2 'read distance from sensor t water when 100% full
Temp1 = Temp1-temp2 'temp1 now has corrected level
peek depth,Temp2 'Value of 100% empty Range Location is $62
w1 = Temp1 * 100/ Temp2 'Value as a %
dataper = 100 - temp3
poke TEMPN , DataPer 'Store in next available address within group of ten
dataverage:
'Then averages the last 10 readings and stores result in DataPer
w1 = 0 'Clear Range
for Counter1 = READSTART to READSTOP '$50 to $59
peek Counter1 , TEMP5
w1=w1 + TEMP5
next Counter1
w1=w1/10 'Data now as a % in a range of 0 to 100: in Temp3
DATAPER = temp3 'Stash it away
' Next incresae loop counter by 1, and if over READSTOP then reset it to READSTART.
inc TEMPN
if TEMPN <= READSTOP then dataverage1
TEMPN = READSTART
dataverage1:
'Next calculate DATAH & DATAL as a % in the range 0 to 99
'MSB into DATAH; LSB into DATAL
DATAH = DATAPER/10
DATAL = DATAPER//10
TEMP7 = 2 'set to 2 to speed-up debug
'LED strobe ON pulse time. Set to 50 @ 4 mHz; 200 @ 16 mhz
'
'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
'X X
'X DISPHL and DISPLY Display Routines X
'X X
'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
disphl:
'This section converts DATAH & DATAL into 7 segment data.
disp: TEMP3 = DATAL 'prepare LSB for conversion
gosub dispA 'convert into 7 seg data into TEMP1;FP=%11111101=$FD
DATAL = TEMP1 'load LSB 7 seg data into TEMP2
TEMP3 = DATAH 'prepare MSB for conversion
gosub dispA 'convert into 7 seg data into TEMP1;FP=%10110111=$D7
'dispA:branch TEMP3,(disp0,disp1,disp2,disp3,disp4,disp5,disp6,disp7,disp8,disp9,disp10,disp11,disp12,disp13,disp14,disp15)
'0-9 = 0 to 9;10=E; 11=t; 12=H; 13=E; 14=L; 15=P
'At this point TEMP1 contains the seven segments for the MSB; and TEMP2
DATAH = TEMP1
goto DISPLY
dispA:
lookup TEMP3, (SEG0,SEG1,SEG2,SEG3,SEG4,SEG5,SEG6,SEG7,SEG8,SEG9,SEGM,SEGt,SEGH,SEGE,SEGL,SEGP), TEMP1
return
'DISPLY
'THIS SECTION SETS THE DATA INTO THE DISPLAY.
'Display routine
'places the contents of TEMP1 in RHS LSB display & TEMP2 in LHS MSB display
'disply displays the informa=tion for 20 milliseconds being 10 millseconds each.
'TEMP 7 is the delay for the display. 1 = 1 mSec @ 4 MHz
disply:
for Counter1 = 1 to TEMP7 'Loop Counter
let pins = DATAL 'place lsb onto portc pins
high portc LEDLSB 'enable LSB digit driver
pause 1 'remain active for 10 milli seconds
low portc LEDLSB 'dissable MSB digit driver
let pins = DATAH 'Place MSB onto portc pins
high portc LEDMSB 'enable MSB driverM
pause 1 'remain active for 10 milli seconds
low portc LEDMSB 'dissable MSB driver
next Counter1
return