Ik heb de klok met temperatuur weergave gemaakt van Galaxy.
http://www.picbasic.org/forum/showthread.php?t=7623&highlight=clock+te…
Als nu de klok loopt met de spanning op de pic en de ds1307 loopt de klok heel langzaam (1 seconde op het display duurt ongeveer tussen de 3-6 seconden).
Als ik echter de klok op tijd zet en dan de voeding uit schakel (de ds1307 loopt verder op batterij) en dan na een uur de voeding weer in schakel heeft de ds1307 wel op tijd gelopen.
Wie kan me hier mee helpen?
Dit is de code.
DEVICE = 16F628A
CONFIG INTRC_OSC_NOCLKOUT, CP_OFF, WDT_OFF, PWRTE_ON, LVP_OFF, MCLRE_OFF, BODEN_off
DELAYMS 200
ALL_DIGITAL=true
PORTB_PULLUPS=true
EDATA 0,0,0,"SUN","MON","TUE","WED","THU","FRI","SAT","JAN","FEB","MAR","APR","MAY","JUN","JUL","AUG","SEP","OCT","NOV","DEC"
DECLARE LCD_DTPIN PORTB.0
DECLARE LCD_RSPIN PORTA.0
DECLARE LCD_ENPIN PORTA.1
DECLARE LCD_LINES 2
CLS
DECLARE SCL_PIN PORTA.2
DECLARE SDA_PIN PORTA.3
DIM secs AS BYTE
DIM mins AS BYTE
DIM hrs AS BYTE
DIM weekday AS BYTE
DIM day AS BYTE
DIM month AS BYTE
DIM year AS BYTE
DIM dummy AS BYTE ;dummy var for calculations
DIM temp AS WORD ;temperature
DIM q AS BYTE ;loopcounter
DIM tablepos AS BYTE ; position of the eeprom lookup table
DIM mode AS BYTE ;mode 0= normal operation, everything else= setting by hand
CLEAR ;reset all variables
TRISA=0 ;all outputs. don't leave floating pins anywhere.
SYMBOL modekey=PORTB.4
SYMBOL upkey=PORTB.5
SYMBOL downkey=PORTB.6
;------------- initial start of RTC-oscillator
BUSIN %11010001,0,[secs] ;read seconds + bit7 (=osc. on/off)
DELAYMS 10
CLEAR secs.7 ; make sure osc. = on
DELAYMS 10
BUSOUT %11010000,0,[secs] ;write back to RTC
;-----------------------
BUSIN %11010001,2,[hrs] ;read hours
CLEAR hrs.6 ;select 24 hr clock
BUSOUT %11010000,2,[hrs] ;write back to rtc
BUSOUT %10010000,172,[1] ;select oneshot mode in t-sensor.
BUSOUT %10010000,[238] ;start a conversion
;-----------------------------
main:
IF mode=0 THEN ;read RTC only if mode=0 (no change by hand)
BUSIN %11010001,0,[secs,mins,hrs,weekday,day,month,year]
;don't allow some values to be 0 when starting for the first time.
IF weekday=0 THEN weekday=1
IF day=0 THEN day=1
IF month=0 THEN month=1
BUSIN %10010001,172,[dummy] ;read config register of T-sensor
IF dummy.7=1 THEN ;1=conversion ready, 0=busy
BUSIN %10010001,170,[temp] ;read T-sensor
BUSOUT %10010000,[238] ;start a new temperature conversion
END IF
; because of the fact that each byte in the RTC is organised as a high nibble,
; containing the tens and a low nibble containing the singles, we have
; to manipulate the data a little. The tens are first masked, so we have
; nothing else than that.
; After that, we shift that value 4 bits to the righ, and we multiply it
; by 10 to get a good value. Then we add the singles to it.
dummy=secs & %11110000 ;bitwise AND
GOSUB calc_tens
secs=secs & %00001111
secs=secs+dummy
dummy=mins & %11110000
GOSUB calc_tens
mins=mins & %00001111
mins=mins+dummy
dummy=hrs & %00110000
GOSUB calc_tens
hrs=hrs & %00001111
hrs=hrs+dummy
dummy=day & %11110000
GOSUB calc_tens
day=day & %00001111
day=day+dummy
dummy=month & %11110000
GOSUB calc_tens
month=month & %00001111
month=month+dummy
dummy=year & %11110000
GOSUB calc_tens
year=year & %00001111
year=year + dummy
END IF
PRINT AT 1,1,DEC2 hrs,":",DEC2 mins,":",DEC2 secs
IF temp.HIGHBYTE<128 THEN ;then we have a positive temperature
PRINT AT 1,10," "
PRINT DEC2 temp.HIGHBYTE
IF temp.LOWBYTE=0 THEN
PRINT ".0"
ELSE
PRINT ".5"
END IF
ELSE ;now we're sure temp=negative
PRINT AT 1,10,"-"
IF temp.LOWBYTE=0 THEN
PRINT DEC2 256-temp.HIGHBYTE
PRINT ".0"
ELSE
PRINT DEC2 255-temp.HIGHBYTE
PRINT ".5"
END IF
END IF
PRINT 223,"C"
PRINT $FE, $C0 ;go to 2nd LCD-line
FOR q=0 TO 2
tablepos=weekday*3+q ; mon, tue etc. have all 3 positons
dummy=EREAD tablepos ;read 3 chars from eeprom table
PRINT dummy
NEXT
PRINT AT 2,5,DEC2 day," "
FOR q=0 TO 2
tablepos=month*3+21+q
dummy=EREAD tablepos
PRINT dummy
NEXT
PRINT " 20",DEC2 year
IF modekey=0 THEN
DELAYMS 10
INC mode
IF mode>7 THEN
mode=0
GOSUB write_to_rtc ;convert time/date values back to BCD and send to rtc
END IF
REPEAT ;wait until modekey is released
UNTIL modekey=1
END IF
;---------- this part of the code is only executed when time/date must be set by hand.
IF mode>0 THEN
DELAYMS 300
SELECT CASE mode
CASE 1
PRINT AT 1,1," "
DELAYMS 300
IF upkey=0 THEN
DELAYMS 10
INC hrs
IF hrs>23 THEN
hrs=0
END IF
END IF
IF downkey=0 THEN
DELAYMS 10
DEC hrs
IF hrs>254 THEN ;in fact: <0
hrs=23
END IF
END IF
CASE 2
PRINT AT 1,4," "
DELAYMS 300
IF upkey=0 THEN
DELAYMS 10
INC mins
IF mins>59 THEN
mins=0
END IF
END IF
IF downkey=0 THEN
DELAYMS 10
DEC mins
IF mins>254 THEN ;<0
mins=59
END IF
END IF
CASE 3
PRINT AT 1,7," "
DELAYMS 300
IF upkey=0 OR downkey=0 THEN
DELAYMS 10
secs=0
END IF
CASE 4
PRINT AT 2,1," "
DELAYMS 300
IF upkey=0 THEN
DELAYMS 10
INC weekday
IF weekday>7 THEN
weekday=1
END IF
END IF
IF downkey=0 THEN
DELAYMS 10
DEC weekday
IF weekday<1 THEN
weekday=7
END IF
END IF
CASE 5
PRINT AT 2,5," "
DELAYMS 300
IF upkey=0 THEN
DELAYMS 10
INC day
IF day>31 THEN
day=1
END IF
END IF
IF downkey=0 THEN
DELAYMS 10
DEC day
IF day<1 THEN
day=31
END IF
END IF
CASE 6
PRINT AT 2,8," "
DELAYMS 300
IF upkey=0 THEN
DELAYMS 10
INC month
IF month>12 THEN
month=1
END IF
END IF
IF downkey=0 THEN
DELAYMS 10
DEC month
IF month<1 THEN
month=12
END IF
END IF
CASE 7
PRINT AT 2,14," "
DELAYMS 300
IF upkey=0 THEN
DELAYMS 10
INC year
IF year>99 THEN
year=0
END IF
END IF
IF downkey=0 THEN
DELAYMS 10
DEC year
IF year<1 THEN
year=99
END IF
END IF
END SELECT
END IF
;-------------------------------------------------------
GOTO main
;----------------------------------------------------------------------------------------
calc_tens:
dummy=(dummy/16)*10 ;shift value 4 positions to the right & multiply by 10.
RETURN
;-----------------------------------------------------------------------------------------
write_to_rtc:
;convert time/date values back to BCD and write it to RTC
dummy=secs/10 ;we only want the 10s here
dummy=dummy*16 ;shift that value to the high nibble
secs=secs//10 ;for the singles we want the remainder of that division.
secs=secs | dummy ;Bitwise OR to combine both values in 1 byte
dummy=mins/10
dummy=dummy*16
mins=mins//10
mins=mins | dummy
dummy=hrs/10
dummy=dummy*16
hrs=hrs//10
hrs=hrs | dummy
dummy=day/10
dummy=dummy*16
day=day//10
day=day | dummy
dummy=month/10
dummy=dummy*16
month=month//10
month=month | dummy
dummy=year/10
dummy=dummy*16
year=year//10
year=year | dummy
BUSOUT %11010000,0,[secs,mins,hrs,weekday,day,month,year] ;write it al back to RTC
RETURN