Buongiorno a tutti!
L'argomento su cui mi sono incaponito in questi giorni è l'impiego di un RTC all'interno del mio primo vero progettino (lettura di sensori multipli e scrittura dei risultati su SD).
Per quanto riguarda l'RTC, anzichè utilizzare le svariate librerie già pronte, ai fini didattici, ho preferito studiare la libreria "wire" e provare ad estrarre i valori direttamente dai registri cercando di "interpretare" il datasheet. E qui arriva il primo problema.
Per quanto riguarda la data e l'orario sono riuscito senza particolari difficoltà ad ottenere il risultato sperato. Relativamente alla temperatura, dal datasheet ho visto che viene fornita sotto forma di due componenti, ossia la parte intera MSB e la parte frazionaria LSB. Cercando info al riguardo ho trovato la formulazione che ho inserito nel codice per determinare il valore in Celsius, ma non riesco a comprenderne pienamente il significato, oltre a non sapere se tale formulazione risulta corretta. Qualche dritta al riguardo? (suggerimenti, articoli, ecc... )
Il secondo problema che sto incontrando verte invece sul trattamento dei dati ottenuti dall' RTC. Sulla SD card, desidero accompagnare il valore letto dai sensori con la data e l'ora di lettura, nello specifico tale indicazione, per come sto strutturando la restante parte del codice dovrebbe essere nel formato "aaaammgg_hhmmss" (anno mese giorno _ ora minuti secondi). La prova che ho fatto ora nel codice allegato consiste nel concatenare una stringa con i vari "pezzi" per ottenere quello che mi serve. Dato che per non avere problemi di "ricerca" dei record all'interno dei files salvati sulla SD desidero che ogni riga del file stesso non cambi la propria lunghezza, è necessario modificare la stringa sopra descritta inserendo degli "zeri" nel momento in cui le singole componenti (mese, giorno, ora, ecc...) diano valori a cifra singola (l'RTC per esempio per il mese di febbraio fornisce il valore "2" anzichè "02" come mi servirebbe. Ho fatto "n" tentativi utilizzando semplici cicli "if" ma mi sto incasinando con i tipi di variabile in gioco e non riesco a venirne a capo. Qualche dritta? Durante le ricerche di una possibile soluzione a tale problemino ho letto che le stringhe sarebbe opportuno non utilizzarle perchè occupano un sacco si spazio; esisiste una migliore soluzione a quanto ho per il momento elaborato?
Ringrazio per la cortese attenzione e per gli eventuali suggerimenti.
Ciao, Giuliano.
PS: Il codice in oggetto è il seguente:
// Collegamenti RTC DS3231 Arduino UNO
// GND RTC --> GND Arduino UNO
// Vcc RTC --> 5V Arduino UNO
// SDA RTC --> A4 Arduino UNO
// SLC RTC --> A5 Arduino UNO
// Collegamenti Arduino MEGA
// Includo la libreria per comunicazione I2C
#include <Wire.h> //http://arduino.cc/en/Reference/Wire (incluso con Arduino IDE)
// Dichiarazione costanti
const unsigned int baud_rate_seriale=9600; // velocità di comunicazione porta seriale
// Dichiarazione variabili RTC DS3231
byte errore_RTC; // Errore generico di comunicazione con modulo RTC
float temperatura_RTC; // Temperatura misurata dal modulo RTC
void setup(){
// Inizializzazione porta seriale
Serial.begin(baud_rate_seriale);
// Inizializzazione libreria Wire
Wire.begin();
delay(1000);
}
void loop(){
// Inizializzazione trasmissione RTC DS3231 (0x68) per lettura data e ora
Wire.beginTransmission(0x68); // Indirizzo I2C RTC
Wire.write((byte)0x00); // Inizio registro data-ora
errore_RTC = Wire.endTransmission();
if (errore_RTC != 0){
Serial.println(errore_RTC);
}
// Lettura data e ora
// Recupero i 7 byte relativi ai corrispondenti registri (vedi datasheet)
Wire.requestFrom(0x68,7);
byte secondi=Wire.read();
byte minuti=Wire.read();
byte ore=Wire.read();
byte giorno_sett=Wire.read();
byte giorno_mese=Wire.read();
byte mese=Wire.read();
byte anno=Wire.read();
// Inizializzazione trasmissione RTC DS3231 (0x68) per lettura temperatura
Wire.beginTransmission(0x68); // Indirizzo I2C RTC
Wire.write((byte)0x11); // Inizio registro temperatura
Wire.endTransmission();
// Lettura temperatura
// Recupero i 2 byte relativi ai corrispondenti registri (vedi datasheet)
Wire.requestFrom(0x68,2);
int MSBtemp=Wire.read(); // Parte intera
int LSBtemp=Wire.read(); // Parte frazionaria
// Trasformazione in gradi Celsius dei dati letti dal sensore
// sistemare questa formula ---------------------------------
temperatura_RTC = MSBtemp + (LSBtemp >> 6)*0.25; // E' corretto ???
// Temperatura misurata internamente all'RTC DS3231
Serial.print(F("Temperatura "));
Serial.print(temperatura_RTC);
Serial.print(F(" *C "));
// Data RTC DS3231
Serial.print(F("Data "));
Serial.print(anno,HEX);
Serial.print(F("-"));
Serial.print(mese,HEX);
Serial.print(F("-"));
Serial.print(giorno_mese,HEX);
// Serial.print(giorno_sett,HEX);
// Orario RTC DS3231
Serial.print(F(" Ora "));
Serial.print(ore,HEX);
Serial.print(F(":"));
Serial.print(minuti,HEX);
Serial.print(F(":"));
Serial.println(secondi,HEX);
// Stringa per DataOra per successiva scrittura su MicroSD Card
String DataOra = ("20" + String(anno,HEX) + String(mese,HEX) + String (giorno_mese,HEX) + "_" + String(ore,HEX) + String(minuti,HEX) + String(secondi,HEX)); // ???????????????????????
Serial.println(DataOra);
delay(5000);
}