Shop OBEX P1 Docs P2 Docs Learn Events
I'm trying to make time based light contoller ,,but hit a road block. need some — Parallax Forums

I'm trying to make time based light contoller ,,but hit a road block. need some

lockadoclockadoc Posts: 115
edited 2008-09-12 20:46 in BASIC Stamp
Hello All,,,
····· I don't want the answers given to me. I just want· to know where I can find the answers. I tried posting the start of this project in the STAMPS IN CLASS Forum but seem to get better help in this forum

My goal to to make a· eight channel light display for my boat club dock lights, when dusk comes all eight leds will light (they will be replaced later to 120 volt lights).When the button is pushed it will go to one of the display
sequences.But after two minutes return to all lights on,I think I can do that with loops and counters,and then making the stamp do a hard reset to go back to the first mode. The tricky part is at 11:00 pm I want 2 channels to turn off, 12:00 am another two channels are to go off,1:00am two more cannels are to go off, leaving· the two remaining channels on, then at 2:00 am the last two channels blink for 20 seconds, then remain on untill morning before goin off at dawn.
·

····· Now what I want to know it how do I get the progarm to get the clock data to work with?
···
···· I have the ROBOTICS WITH THE BOE-BOT, and the STAMPWORKS with the Professional Development Board
···· and could not find any way to start the program with· all the leds to come on without replacing· the first
···· sequence with
······················· SeqA· Data %11111111
···· I Know there must be a way to do it before it gets to the read button line.

·the code I have so far follows ,,··


' {$STAMP BS2}
' {$PBASIC 2.5}
'
[noparse][[/noparse] Program Description ]
'
'············· This program uses the external real-time-clock chip, (the DS1307).
'············· To be used with an eight channel dock light display
'
'
[noparse][[/noparse] I/O Definitions ]
SDA PIN 14 ' I2C serial data line
SCL PIN 15 ' I2C serial clock line
BtnBus VAR INC ' four buttons inputs, pins 8 - 11 to change clock time
Lights VAR OUTL ' light control outputs
LightsDirs VAR DIRL ' DIRS for lights outputs
LTMODE PIN 12 ' MODE SELect input
'
[noparse][[/noparse] Constants ]
Ack CON 0 ' acknowledge bit
Nak CON 1 ' no ack bit
DS1307 CON %1101 << 4
'
[noparse][[/noparse] Variables ]
counter VAR Word 'loop counter
slvAddr VAR Byte ' I2C slave address
devNum VAR Nib ' device number (0 - 7)
addrLen VAR Nib ' bytes in word addr (0 - 2)
wrdAddr VAR Word ' word address
i2cData VAR Byte ' data to/from device
i2cWork VAR Byte ' work byte for TX routine
i2cAck VAR Bit ' Ack bit from device
secs VAR Byte ' DS1307 time registers
mins VAR Byte
hrs VAR Byte
day VAR Byte ' weekday
date VAR Byte ' day in month, 1 - 31
month VAR Byte
year VAR Byte
control VAR Byte ' SQW I/O control
btns VAR Nib ' debounced button inputs
btnBack VAR btns.BIT3 ' roll back
btnDay VAR btns.BIT2 ' +/- day
btnHr VAR btns.BIT1 ' +/- hours
btnMn VAR btns.BIT0 ' +/- minutes
idx VAR Nib ' loop control
pntr VAR Byte ' ee pointer
char VAR Byte ' character for display
'DELAY VAR Word ' time between patterns
btnVar VAR Byte ' workspace for BUTTON
mode VAR Byte ' selected mode
offset VAR Byte ' offset into patterns
rndVal VAR Word ' workspace for RANDOM
'
[noparse][[/noparse] EEPROM Data ]
'······ *****
· THIS IS THE DISPLAY PATTERN SET-UP·
*****
·· SeqA· DATA %11111111
·· SeqB DATA %10000000, %01000000, %00100000, %00010000, %00001000
······· DATA %00000100, %00000010, %00000001,· %00000010, %00000100, %00001000
······· DATA %00010000, %00100000, %01000000
·· SeqC DATA %11111111, %00000000, %00011000, %00100100, %01000010, %10000001, %00000000, %11111111,
············ %10000001, %01000010, %00100100, %00011000
·· SeqD DATA %10010000, %01001000, %00100100, %00010010, %00001001,· %00001001, %00010010, %0010010, %01001000
·· SeqE DATA %0· ' THIS IS THE RANDOM PATTERN
AMax CON SeqB - SeqA ' calculate length
BMax CON SeqC - SeqB
CMax CON SeqD - SeqC
DMax CON SeqE - SeqD
DayNames DATA "SunMonTueWedThuFriSat"
'
[noparse][[/noparse] Initialization ]
Reset:
LightsDirs = %11111111 ' make outputs
SETUP:
slvAddr = DS1307 ' 1 byte in word address
addrLen = 1
DEBUG CLS,
"DS1307 Demo", CR,
"
"
Reset_Clock:
GOSUB Get_Buttons ' scan buttons
idx = btns & %0011 ' isolate hrs & mins
IF (idx = %11) THEN ' if both pressed, reset
secs = $00
mins = $00
hrs = $06 ' 6:00 AM
day = $07 ' Saturday
date = $25 ' 1st
month = $09 ' January
year = $2008 ' 2008
control = 0 ' disable SQW output
GOSUB Set_Clock ' block write clock regs
ENDIF
'
[noparse][[/noparse] Program Code ]
Main:
'IF (IN13 = 0)THEN
·'·· delay = 2
· 'ELSE
·· ' delay = 5
··· 'ENDIF
'PAUSE delay ' wait between patterns
Switch_Check:
BUTTON LtMode, 0, 255, 0, btnVar, 0, Show ' new mode?
mode = mode + 1 // 5 ' yes, update mode var
Show:
ON mode GOSUB ModeA, ModeB, ModeC, ModeD, ModeE
GOSUB Get_Clock ' read DS1307
hrs = hrs & $3F
DEBUG CRSRXY, 0, 2,
HEX2 hrs, ":", HEX2 mins, ":", HEX2 secs, CR
GOSUB Print_Day
DEBUG CRSRXY, 0, 4,
HEX2 month,"-", HEX2 date,"-", HEX2 year
PAUSE 100
GOSUB Get_Buttons
IF (btns > %0000) THEN ' button pressed?
IF (btns <> %1000) THEN ' ignore back only
hrs = hrs.NIB1 * 10 + hrs.NIB0 ' BCD to decimal
··················· mins = mins.NIB1 * 10 + mins.NIB0
IF (btnBack = 0) THEN ' increment values
day = ((day - 1) + btnDay // 7) + 1 ' keep 1 - 7
hrs = hrs + btnHr // 24 ' keep 0 - 23
mins = mins + btnMn // 60 ' keep 0 - 59
ELSE
day = ((day - 1) + (btnDay * 6) // 7) + 1
hrs = hrs + (btnHr * 23) // 24
mins = mins + (btnMn * 59) // 60
ENDIF
hrs = (hrs / 10 << 4) + (hrs // 10) ' decimal to BCD
mins = (mins / 10 << 4) + (mins // 10)
secs = $00
GOSUB Set_Clock ' update DS1307
ENDIF
ENDIF
GOTO Main
'
[noparse][[/noparse] Subroutines ]
Get_Buttons:
btns = %1111 ' enable all four inputs
FOR idx = 1 TO 5
btns = btns & ~BtnBus ' test inputs
PAUSE 5 ' delay between tests
NEXT
RETURN
Print_Day:
pntr = DayNames + ((day - 1) * 3) ' point to 1st char
FOR idx = 0 TO 2 ' print 3 letters
READ (pntr + idx), char ' read letter
DEBUG char ' print it
NEXT
RETURN
' Do a block write to clock registers
Set_Clock:
GOSUB I2C_Start ' send Start
i2cWork = slvAddr & %11111110 ' send slave ID (write)
GOSUB I2C_TX_Byte
IF (i2cAck = Nak) THEN Set_Clock ' wait until not busy
i2cWork = 0 ' point at secs register
GOSUB I2C_TX_Byte
FOR idx = 0 TO 7 ' write secs to control
······· i2cWork = secs(idx)
GOSUB I2C_TX_Byte
NEXT
GOSUB I2C_Stop
RETURN
' Do a block read from clock registers
Get_Clock:
GOSUB I2C_Start ' send Start
i2cWork = slvAddr & %11111110 ' send slave ID (write)
GOSUB I2C_TX_Byte
IF (i2cAck = Nak) THEN Get_Clock ' wait until not busy
i2cWork = 0 ' point at secs register
GOSUB I2C_TX_Byte
GOSUB I2C_Start
i2cWork = slvAddr | %00000001 ' send slave ID (read)
GOSUB I2C_TX_Byte
FOR idx = 0 TO 6 ' read secs to year
GOSUB I2C_RX_Byte
secs(idx) = i2cWork
NEXT
GOSUB I2C_RX_Byte_Nak ' read control
control = i2cWork
GOSUB I2C_Stop
RETURN
MODEA:
offset = offset + 1 // AMax ' update offset (0 - 5)
READ (SeqA + offset), Lights ' output new light pattern
RETURN
ModeB:
offset = offset + 1 // BMax
READ (SeqB + offset), Lights
'····· testing loop counter
'
'
RETURN
ModeC:
offset = offset + 1 // CMax
READ (SeqC + offset), Lights
RETURN
ModeD:
offset = offset + 1 // DMax
READ (SeqD + offset), Lights
RETURN
ModeE:
RANDOM rndVal ' get random number
Lights = rndVal & %11111111 ' light random channels
RETURN
'PIN 0 THRU 7 ARE LED OUTPUTS
'PIN 12 IS BUTTON OUTPUT
'PIN 13 IS DELAY CONTROL
' =====[noparse][[/noparse] High Level I2C Subroutines]=======================================
' Random location write
' -- pass device slave address in "slvAddr"
' -- pass bytes in word address (0, 1 or 2) in "addrLen"
' -- word address to write passed in "wrdAddr"
' -- data byte to be written is passed in "i2cData"
Write_Byte:
GOSUB I2C_Start ' send Start
i2cWork = slvAddr & %11111110 ' send slave ID (write)
GOSUB I2C_TX_Byte
IF (i2cAck = Nak) THEN Write_Byte ' wait until not busy
IF (addrLen > 0) THEN
IF (addrLen = 2) THEN
i2cWork = wrdAddr.BYTE1 ' send word address (1)
GOSUB I2C_TX_Byte
ENDIF
i2cWork = wrdAddr.BYTE0 ' send word address (0)
GOSUB I2C_TX_Byte
ENDIF
i2cWork = i2cData ' send data
GOSUB I2C_TX_Byte
······· GOSUB I2C_Stop
RETURN
' Random location read
' -- pass device slave address in "slvAddr"
' -- pass bytes in word address (0, 1 or 2) in "addrLen"
' -- word address to write passed in "wrdAddr"
' -- data byte read is returned in "i2cData"
Read_Byte:
GOSUB I2C_Start ' send Start
IF (addrLen > 0) THEN
i2cWork = slvAddr & %11111110 ' send slave ID (write)
GOSUB I2C_TX_Byte
IF (i2cAck = Nak) THEN Read_Byte ' wait until not busy
IF (addrLen = 2) THEN
i2cWork = wrdAddr.BYTE1 ' send word address (1)
GOSUB I2C_TX_Byte
ENDIF
i2cWork = wrdAddr.BYTE0 ' send word address (0)
GOSUB I2C_TX_Byte
GOSUB I2C_Start
ENDIF
i2cWork = slvAddr | %00000001 ' send slave ID (read)
GOSUB I2C_TX_Byte
GOSUB I2C_RX_Byte_Nak
GOSUB I2C_Stop
i2cData = i2cWork
RETURN
'
[noparse][[/noparse] Low Level I2C Subroutines]
' *** Start Sequence ***
I2C_Start: ' I2C start bit sequence
INPUT SDA
INPUT SCL
LOW SDA
Clock_Hold:
DO : LOOP UNTIL (SCL = 1) ' wait for clock release
RETURN
' *** Transmit Byte ***
I2C_TX_Byte:
SHIFTOUT SDA, SCL, MSBFIRST, [noparse][[/noparse]i2cWork\8] ' send byte to device
SHIFTIN SDA, SCL, MSBPRE, [noparse][[/noparse]i2cAck\1] ' get acknowledge bit
RETURN
······ ' *** Receive Byte ***
I2C_RX_Byte_Nak:
i2cAck = Nak ' no Ack = high
GOTO I2C_RX
I2C_RX_Byte:
i2cAck = Ack ' Ack = low
I2C_RX:
SHIFTIN SDA, SCL, MSBPRE, [noparse][[/noparse]i2cWork\8] ' get byte from device
SHIFTOUT SDA, SCL, LSBFIRST, [noparse][[/noparse]i2cAck\1] ' send ack or nak
RETURN
' *** Stop Sequence ***
I2C_Stop: ' I2C stop bit sequence
LOW SDA
INPUT SCL
INPUT SDA
RETURN

Comments

  • Mike GreenMike Green Posts: 23,101
    edited 2008-09-11 21:56
    Since a number of Parallax products (like the Professional Development Board) have DS1307 RTCs on the board, it's supported, particularly in some of the Nuts and Volts Columns on I2C. Most of the sample code is probably written for the BS2p/pe/px because those have built-in I2C statements, but the subroutines you're using functionally are equivalent, just need to be called in order. Make sure you have a datasheet for the DS1307. It shows the sequence of I2C communications needed to access the RTC's registers.
  • Chris SavageChris Savage Parallax Engineering Posts: 14,406
    edited 2008-09-11 22:50
    You actually had two replies to your original message in the other forum. You never followed up on that thread. Since cross-posting is not allowed, if you wanted your message answered in the BASIC Stamp Forum you should have asked a forum moderator to move it. Now you have two active threads on the same subject. I will remove the other thread for now, but you will have lost the replies (including mine). This is why you should always follow up when asking for help. One more thing that would help is posting entire programs into the message body. It makes the message hard to follow and even the code since the formatting is lost. Instead attach your code unless it’s only a few lines.

    As a note, I realized I asked you questions in my other reply you never answered.· If you don't follow up on your posts you will never be able to get complete answers to your questions.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Chris Savage
    Parallax Engineering
  • lockadoclockadoc Posts: 115
    edited 2008-09-12 20:46
    Thank for your replies and support,,
    As far as checking my replies from the last post , its seems there is a problrem with the linking system on my computer.
    Today I recieved two Email reponses to this post the first on (latest) seems to take me to some-one elses question and answer this was the link

    http://forums.parallax.com/forums/default.aspx?f=6&m=293070#m293286

    I had the problem with the post I had in the other forum, while in the forum I could see some replies I
    had I could not get to them.
    I will remember not to cross questions in the forum again please allow my foolishness, and I will not place large code in the main body again.

    Billy
Sign In or Register to comment.