|

Un RTC (Real Time Clock), è un dispositivo che dispone di una memoria interna contenente informazioni di calendario quindi ora, data, giorno, mese, anno. La fine del mese è corretta automaticamente per i mesi con meno di 31 giorni e viene considerata anche la bisestilità degli anni. L'orologio può funzionare sia in AM che in PM.
Il DS1307 inoltre ha un sistema interno che gli permette di sentire quando cessa l'alimentazione esterna e quindi gli segnala quando alimentarsi con la batteria da 3V.
Questo tipo di integrato necessita di un quarzo generalmente a 32KHz ed ha un consumo minore di 500nA quando funziona con la batteria di backup.
Qui troverete la libreria per l'utilizzo del DS1307 e questo è lo schema per collegare arduino all'RTC.

Potrete usare questo codice di esempio per testare il vostro rtc.
Includete le librerie WProgram.h, Wire.h e DS1307.h
/*Reads the value from a Real Time Clock (RTC) DS1307 and displays it in the serial monitor
*
*Created by D. Sjunnesson 1scale1.com d.sjunnesson (at) 1scale1.com
*
*Created with combined information from
*http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1180908809
*http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1191209057
*
*
*Big credit to mattt (please contact me for a more correct name...) from the Arduino forum
*which has written the main part of the library which I have modified
*
*/
void setup()
{
Serial.begin(9600);
RTC.stop();
RTC.set(DS1307_SEC,1); //set the seconds
RTC.set(DS1307_MIN,23); //set the minutes
RTC.set(DS1307_HR,12); //set the hours
RTC.set(DS1307_DOW,4); //set the day of the week
RTC.set(DS1307_DATE,5); //set the date
RTC.set(DS1307_MTH,3); //set the month
RTC.set(DS1307_YR,9); //set the year
RTC.start();
}
void loop()
{
Serial.print(RTC.get(DS1307_HR,true)); //read the hour and also update all the values by pushing in true
Serial.print(":");
Serial.print(RTC.get(DS1307_MIN,false));//read minutes without update (false)
Serial.print(":");
Serial.print(RTC.get(DS1307_SEC,false));//read seconds
Serial.print(" "); // some space for a more happy life
Serial.print(RTC.get(DS1307_DATE,false));//read date
Serial.print("/");
Serial.print(RTC.get(DS1307_MTH,false));//read month
Serial.print("/");
Serial.print(RTC.get(DS1307_YR,false)); //read year
Serial.println();
delay(1000);
}
Oppure potrete decidere di non usare questa libreria allora il codice sarà più complicato, seguite questo altro esempio
Includete la libreria wire.h
int clockAddress = 0x68; // This is the I2C address
int command = 0; // This is the command char, in ascii form, sent from the serial port
long previousMillis = 0; // will store last time Temp was updated
byte second, minute, hour, dayOfWeek, dayOfMonth, month, year;
byte test;
// Convert normal decimal numbers to binary coded decimal
byte decToBcd(byte val)
{
return ( (val/10*16) + (val%10) );
}
// Convert binary coded decimal to normal decimal numbers
byte bcdToDec(byte val)
{
return ( (val/16*10) + (val%16) );
}
// 1) Sets the date and time on the ds1307
// 2) Starts the clock
// 3) Sets hour mode to 24 hour clock
// Assumes you're passing in valid numbers,
// Probably need to put in checks for valid numbers.
void setDateDs1307()
{
// Use of (byte) type casting and ascii math to achieve result.
second = (byte) ((Serial.read() - 48) * 10 + (Serial.read() - 48));
minute = (byte) ((Serial.read() - 48) *10 + (Serial.read() - 48));
hour = (byte) ((Serial.read() - 48) *10 + (Serial.read() - 48));
dayOfWeek = (byte) (Serial.read() - 48);
dayOfMonth = (byte) ((Serial.read() - 48) *10 + (Serial.read() - 48));
month = (byte) ((Serial.read() - 48) *10 + (Serial.read() - 48));
year= (byte) ((Serial.read() - 48) *10 + (Serial.read() - 48));
Wire.beginTransmission(clockAddress);
Wire.send(0x00);
Wire.send(decToBcd(second)); // 0 to bit 7 starts the clock
Wire.send(decToBcd(minute));
Wire.send(decToBcd(hour)); // If you want 12 hour am/pm you need to set
// bit 6 (also need to change readDateDs1307)
Wire.send(decToBcd(dayOfWeek));
Wire.send(decToBcd(dayOfMonth));
Wire.send(decToBcd(month));
Wire.send(decToBcd(year));
Wire.endTransmission();
}
// Gets the date and time from the ds1307 and prints result
void getDateDs1307() {
// Reset the register pointer
Wire.beginTransmission(clockAddress);
Wire.send(0x00);
Wire.endTransmission();
Wire.requestFrom(clockAddress, 7);
// A few of these need masks because certain bits are control bits
second = bcdToDec(Wire.receive() & 0x7f);
minute = bcdToDec(Wire.receive());
// Need to change this if 12 hour am/pm
hour = bcdToDec(Wire.receive() & 0x3f);
dayOfWeek = bcdToDec(Wire.receive());
dayOfMonth = bcdToDec(Wire.receive());
month = bcdToDec(Wire.receive());
year = bcdToDec(Wire.receive());
Serial.print(hour, DEC);
Serial.print(":");
Serial.print(minute, DEC);
Serial.print(":");
Serial.print(second, DEC);
Serial.print(" ");
Serial.print(month, DEC);
Serial.print("/");
Serial.print(dayOfMonth, DEC);
Serial.print("/");
Serial.print(year, DEC);
}
void setup() {
Wire.begin();
Serial.begin(57600);
}
void loop() {
if (Serial.available()) { // Look for char in serial que and process if found
command = Serial.read();
if (command == 84) { //If command = "T" Set Date
setDateDs1307();
getDateDs1307();
Serial.println(" ");
}
else if (command == 81) { //If command = "Q" RTC1307 Memory Functions
delay(100);
if (Serial.available()) {
command = Serial.read();
// If command = "1" RTC1307 Initialize Memory - All Data will be set to 255 (0xff).
// Therefore 255 or 0 will be an invalid value.
if (command == 49) {
// 255 will be the init value and 0 will be cosidered an error that
// occurs when the RTC is in Battery mode.
Wire.beginTransmission(clockAddress);
// Set the register pointer to be just past the date/time registers.
Wire.send(0x08);
for (int i = 1; i <= 27; i++) {
Wire.send(0xff);
delay(100);
}
Wire.endTransmission();
getDateDs1307();
Serial.println(": RTC1307 Initialized Memory");
}
else if (command == 50) { //If command = "2" RTC1307 Memory Dump
getDateDs1307();
Serial.println(": RTC 1307 Dump Begin");
Wire.beginTransmission(clockAddress);
Wire.send(0x00);
Wire.endTransmission();
Wire.requestFrom(clockAddress, 64);
for (int i = 1; i <= 64; i++) {
test = Wire.receive();
Serial.print(i);
Serial.print(":");
Serial.println(test, DEC);
}
Serial.println(" RTC1307 Dump end");
}
}
}
Serial.print("Command: ");
Serial.println(command); // Echo command CHAR in ascii that was sent
}
command = 0; // reset command
delay(100);
}
Articolo scritto da Calamaro, l'immagine in alto è tratta da Sparkfun, le altre immagini sono tratte dal datasheet dell'integrato.
![]()
