| The Indoor Unit Picaxe Code | |
|
The Indoor Unit Picaxe CodeThis is the latest code but is subject to change. [10/03/2011]
Variable Assignment Table Note: The code for the LCD is for an old serial backback that is no longer available. To help you convert the code to match the LCD you will be using, this page explains what the codes I've used actually do.
;============================================================================
; Main Indoor (Receiver) Program.
;
; Receives data from outdoor unit, displays on LCD and passes data on to PC
; Also measures the barometric pressure (thanks to 'matherp')
;============================================================================
#PICAXE 18M2
; Variable Definitions (b2 to b5 are re-used for mBar code when they become available)
symbol Quotient = b2
symbol Fract = b3
symbol SignBit = b4
symbol Humidity = b5
symbol HFract = b14
symbol Dir = w5
symbol DirLo = b10
symbol DirHi = b11
symbol Speed = w3
symbol SpeedLo = b6
symbol SpeedHi = b7
symbol RainCountThisHour = b12
symbol RainCountLastHour = b13
symbol LCDRainWhole = b21
symbol LCDRainFract = b22
symbol LastOrThis = b23
; MCP3422 ADC variables
symbol mb900 = 17429 ; ADC reading for 900Mbar, then add 72.288 counts per mbar
symbol adj0 = 72
symbol mBarADCValue = w0
symbol adj1 = b4 ; used to add 1 count every 4 mbar
symbol adj2 = b5 ; used to add 1 count every 24 mbar
symbol mBar = w4
; Housekeeping variables
symbol lastmbar = w8 ; Remember previous mBar reading
symbol RiseFall = b18 ; Indicator for pressure rising or falling (up arrow or down arrow)
symbol active = b19 ; Telltale shows activity on LCD screen
symbol LCD_Status = b20 ; Is LCD Backlight on or off (0 or 1)?
; Hardware Definitions
symbol Wireless = C.7 ; Incoming connection from Wireless receiver/decoder
symbol Computer = C.2 ; Outgoing serial connection to computer
symbol LCD = pinC.5 ; Front-panel button to blank / unblank LCD backlight
symbol ClearRiseFall = pinC.0 ; Front-panel button to clear pressure 'rising / falling' indicator
symbol LastOrThisSwitch = pinC.1 ; Front-panel button to display current or previous hour's rainfall
Init:
hsersetup B9600_4, %10000 ; Use LCD Pin 1, no hserin
; ByVac 20x4 IASI-2 Serial LCD
hi2csetup i2cmaster, %11010000, i2cfast, i2cbyte ; Initialize I2C for MCP3422 ADC chip.
hi2cout (%00011000) ; set MCP3422 for 16 bit continuous conversion
pause 500
hserout 0, (13) : pause 100 ; Initialize LCD
hserout 0, (13) : pause 100
hserout 0, (13) : pause 100
pause 500
hserout 0, ("ac50", 13)
hserout 0, ("ad", 32, 32, 32, 32, 49, 42, 36, 32, 13) ; Define down arrow character (char 10)
hserout 0, ("ac1", 13) ; Clear display
pause 50
hserout 0, ("acc", 13) ; Hide cursor
hserout 0, ("ac81", 13, "ad ", $df, "C", 13) ; Print the headings
hserout 0, ("ac88", 13, "admBar", 13)
hserout 0, ("ac8e", 13, "adRH %", 13)
hserout 0, ("acd5", 13, "ad", "dir", 13) ; Print footings
hserout 0, ("acdc", 13, "ad", "mph", 13) ;
hserout 0, ("ace3", 13, "ad", "mm", 13)
lastmbar = 0 ; Initialize variables
LastOrThis = "c"
;==========================================================================
; Main Loop
;==========================================================================
main:
; Check if a front-panel switch is pressed. The Picaxe interrupt mechanism is
; almost permanently disabled due to the large number of serin and serout commands
; so sprinkling the program with 'gosub switches' to check the switch status is more
; effective that interrupts.
gosub switches
; Get first group of values from outdoor unit via 433MHz radio link.
serin Wireless, N2400, ("t"), SignBit, Quotient, Fract, Humidity, HFract, b15, b15
; Flash 'telltale' on LCD to indicate activity and successful 'serin' from wireless.
gosub telltale
; Display first group on LCD
hserout 0, ("acc0", 13)
hserout 0, ("ad", SignBit, #Quotient, ".", #Fract, " ", 13)
hserout 0, ("acce", 13)
hserout 0, ("ad", #Humidity,".", #HFract, " ", 13)
gosub switches
; Send first group to computer COM port
; Each group has a start identifier, data and an end identifier:
; Start = "xS", End is "xE" eg Wind Start is WS, Wind End is WE
; Multiple data are separated by a single space character.
serout Computer, N2400, ("TS", SignBit, #Quotient,".", #Fract, "TE") ; Temperature
serout Computer, N2400, ("HS", #Humidity, ".", #HFract, "HE") ; Humidity
; Check switches again and at regular intervals throughout program.
gosub switches
; Get second group of values from outdoor unit radio link.
serin Wireless, N2400, ("m"), DirHi, DirLo, SpeedHi, SpeedLo, RainCountLastHour, RainCountThisHour, b15
gosub telltale
Speed = Speed * 36 / 10 ; Estimated conversion from pulses/sec to mph
Dir = Dir * 64 / 182 ; Convert 0 - 1023 to 0 - 359 degrees
; To preserve precision, rain gauge has to be calibrated by adjusting the
; mechanical stops on the tipping bucket so that 1 tip is 0.5 mm of rain.
if LastOrThis = "c" then ; Decide whether to display previous hour's
LCDRainWhole = RainCountThisHour / 2 ; rainfall or the current hour's.
LCDRainFract = RainCountThisHour * 5 // 10
else
LCDRainWhole = RainCountLastHour / 2 ;
LCDRainFract = RainCountLastHour * 5 // 10
endif
; Send second group to LCD
hserout 0, ("ac95", 13)
hserout 0, ("ad", #Dir, " ", 13)
hserout 0, ("ac9c", 13)
hserout 0, ("ad", #Speed, " ", 13)
hserout 0, ("aca1", 13)
hserout 0, ("ad", LastOrThis, " ", #LCDRainWhole, ".", #LCDRainFract, " ", 13)
; Send second group to computer COM port
serout Computer, N2400, ("WS", #Dir," ", #Speed, "WE") ; Wind
serout Computer, N2400, ("RS", #RainCountLastHour," ", #RainCountThisHour, "RE") ; Rain
gosub switches
; Thanks to 'matherp' on the Picaxe forum for the mbar code loop:
; Measuring atmosperic pressure with a MPX4115A
; Analogue to digital conversion using a MCP3422
; MPX output to V+, 2.5V to V-
; ADC in 16 bit mode
hi2cin (b1,b0,b2) ; Read in the ADC reading and the status byte from MCP3422
adj1 = 0
adj2 = 0
w1 = mb900
mbar = 900
do while mBarADCValue > w1 ; mBarADCValue = w0 = b1:b0
inc mbar
w1 = w1 + adj0
inc adj1
if adj1 = 4 then
inc adj2
w1 = w1 + 1
adj1 = 0
endif
if adj2 = 6 then
w1 = w1 + 1
adj2 = 0
endif
loop
gosub switches
gosub telltale
; Send pressure to computer COM port
serout Computer, N2400, ("PS:", #mbar, "PE")
; Initialize previous pressure reading (lastmbar) if not already set
if lastmbar = 0 then
lastmbar = mbar
RiseFall = " "
endif
; Display up arrow or down arrow if pressure has changed
if mbar > lastmbar then
RiseFall = "^" ; ^
lastmbar = mbar
endif
if mbar < lastmbar then
RiseFall = 10 ; Custom LCD character. Down arrow
lastmbar = mbar
endif
hserout 0, ("acc7", 13)
hserout 0, ("ad", RiseFall, #mbar, " ",13)
gosub telltale
goto main
; Check if one of the front panel buttons is pressed.
switches:
if LCD = 1 then ; LCD Backlight on/off Button is pressed
if LCD_Status = 0 then ; Backlight is on so...
hserout 0, ("ab0", 13) ; Turn it off
LCD_Status = 1
else
hserout 0, ("ab1", 13) ; Else turn it on.
LCD_Status = 0
endif
do: loop while LCD = 1 ; Don't return while button is pressed
endif
if ClearRiseFall = 1 then ; Pressure rise/fall button is pressed
RiseFall = " " ; Clear indicator and...
hserout 0, ("acc7", 13) ; ... update display.
hserout 0, ("ad", RiseFall, #mbar, " ",13)
do: loop while ClearRiseFall = 1
endif
if LastOrThisSwitch = 1 then ; Rain Previous Hour / Last Hour button.
if LastOrThis = "c" then
LastOrThis = "p"
LCDRainWhole = RainCountLastHour / 2 ; Recalculate values and re-display to
LCDRainFract = RainCountLastHour * 5 // 10 ; give visual confirmation of button-press
else
LastorThis = "c"
LCDRainWhole = RainCountThisHour / 2 ;
LCDRainFract = RainCountThisHour * 5 // 10
endif
hserout 0, ("aca1", 13)
hserout 0, ("ad", LastOrThis, " ", #LCDRainWhole, ".", #LCDRainFract, " ", 13)
do : loop while LastOrThisSwitch = 1
endif
return
; Flash "tell-tale" on LCD display to show activity
telltale:
if active = "*" then
active = " "
else
active = "*"
endif
hserout 0, ("ac80", 13, "ad", active, 13)
return
{Memory used = 764 bytes out of 2048}
| |