miércoles, 30 de octubre de 2013

Configurando Adecuadamente el módulo Tiny RTC

En esta ocasión se comparte la manera adecuada para la programación del módulo Tiny RTC, gracias a un compañero quien me facilito el módulo pude explorarlo y hacerle funcionar, en primera instancia lo que les recomiendo es que no se confíen de algunas librerías que están publicadas para el manejo de este módulo, remítanse a la documentación del fabricante que se encuentra en este link:

http://www.dfrobot.com/wiki/index.php/Real_Time_Clock_Module_(DS1307)_(SKU:DFR0151)

La conexión que se debe realizar con arduino es la siguiente:


Es importante que se realice la conexión del pin 2 al arduino, este pin permite realizar la configuración de la hora y los días de manera adecuada. Los pasos a seguir para programar el módulo son:


  1. Se debe instalar la librería que les comparto al arduino.
  2. Una vez instalada la librería (que es simplemente copiar la carpeta del rar en la carpeta arduino->libraries), abrir el archivo .ino que se comparte.
  3. Allí simplemente se le quita el comentario en las líneas indicadas, se cambia la fecha y la hora, se programa el arduino conectado al módulo.
  4. Hecho el paso anterior, poner las líneas de nuevo en comentario y volver a programar.
  5. Terminado, por fin el módulo funciona.
  6. Las líneas que se deben modificar están de color rojo.

#include <Wire.h>                       // For some strange reasons, Wire.h must be included here
#include <DS1307new.h>

// *********************************************
// DEFINE
// *********************************************

// *********************************************
// VARIABLES
// *********************************************
uint16_t startAddr = 0x0000;            // Start address to store in the NV-RAM
uint16_t lastAddr;                      // new address for storing in NV-RAM
uint16_t TimeIsSet = 0xaa55;            // Helper that time must not set again

// *********************************************
// SETUP
// *********************************************
void setup()
{
  pinMode(2, INPUT);                    // Test of the SQW pin, D2 = INPUT
  digitalWrite(2, HIGH);                // Test of the SQW pin, D2 = Pullup on

  Serial.begin(9600);

/*
   PLEASE NOTICE: WE HAVE MADE AN ADDRESS SHIFT FOR THE NV-RAM!!!
                  NV-RAM ADDRESS 0x08 HAS TO ADDRESSED WITH ADDRESS 0x00=0
                  TO AVOID OVERWRITING THE CLOCK REGISTERS IN CASE OF
                  ERRORS IN YOUR CODE. SO THE LAST ADDRESS IS 0x38=56!
*/
  RTC.setRAM(0, (uint8_t *)&startAddr, sizeof(uint16_t));// Store startAddr in NV-RAM address 0x08 

/*
   Uncomment the next 2 lines if you want to SET the clock
   Comment them out if the clock is set.
   DON'T ASK ME WHY: YOU MUST UPLOAD THE CODE TWICE TO LET HIM WORK
   AFTER SETTING THE CLOCK ONCE.
*/
// TimeIsSet = 0xffff;
//  RTC.setRAM(54, (uint8_t *)&TimeIsSet, sizeof(uint16_t));  

/*
  Control the clock.
  Clock will only be set if NV-RAM Address does not contain 0xaa.
  DS1307 should have a battery backup.
*/
  RTC.getRAM(54, (uint8_t *)&TimeIsSet, sizeof(uint16_t));
  if (TimeIsSet != 0xaa55)
  {
    RTC.stopClock();
        
    RTC.fillByYMD(2013,10,30);
    RTC.fillByHMS(14,52,0);
    
    RTC.setTime();
    TimeIsSet = 0xaa55;
    RTC.setRAM(54, (uint8_t *)&TimeIsSet, sizeof(uint16_t));
    RTC.startClock();
  }
  else
  {
    RTC.getTime();
  }

/*
   Control Register for SQW pin which can be used as an interrupt.
*/
  RTC.ctrl = 0x00;                      // 0x00=disable SQW pin, 0x10=1Hz,
                                        // 0x11=4096Hz, 0x12=8192Hz, 0x13=32768Hz
  RTC.setCTRL();

  Serial.println("Tiempo Actual");
  
  uint8_t MESZ;
      
  Serial.println();
}

// *********************************************
// MAIN (LOOP)
// *********************************************
void loop()
{
  RTC.getTime();
  if (RTC.hour < 10)                    // correct hour if necessary
  {
    Serial.print("0");
    Serial.print(RTC.hour, DEC);
  } 
  else
  {
    Serial.print(RTC.hour, DEC);
  }
  Serial.print(":");
  if (RTC.minute < 10)                  // correct minute if necessary
  {
    Serial.print("0");
    Serial.print(RTC.minute, DEC);
  }
  else
  {
    Serial.print(RTC.minute, DEC);
  }
  Serial.print(":");
  if (RTC.second < 10)                  // correct second if necessary
  {
    Serial.print("0");
    Serial.print(RTC.second, DEC);
  }
  else
  {
    Serial.print(RTC.second, DEC);
  }
  Serial.print(" ");
  if (RTC.day < 10)                    // correct date if necessary
  {
    Serial.print("0");
    Serial.print(RTC.day, DEC);
  }
  else
  {
    Serial.print(RTC.day, DEC);
  }
  Serial.print("-");
  if (RTC.month < 10)                   // correct month if necessary
  {
    Serial.print("0");
    Serial.print(RTC.month, DEC);
  }
  else
  {
    Serial.print(RTC.month, DEC);
  }
  Serial.print("-");
  Serial.print(RTC.year, DEC);          // Year need not to be changed
  Serial.print(" ");
  switch (RTC.dow)                      // Friendly printout the weekday
  {
    case 1:
      Serial.print("MON");
      break;
    case 2:
      Serial.print("TUE");
      break;
    case 3:
      Serial.print("WED");
      break;
    case 4:
      Serial.print("THU");
      break;
    case 5:
      Serial.print("FRI");
      break;
    case 6:
      Serial.print("SAT");
      break;
    case 7:
      Serial.print("SUN");
      break;
  }
  uint8_t MESZ = RTC.isMEZSummerTime();
   
  RTC.getRAM(0, (uint8_t *)&lastAddr, sizeof(uint16_t));
  Serial.print("\n");
  lastAddr = lastAddr + 1;              // we want to use it as addresscounter for example
  RTC.setRAM(0, (uint8_t *)&lastAddr, sizeof(uint16_t));
  RTC.getRAM(54, (uint8_t *)&TimeIsSet, sizeof(uint16_t));
  if (TimeIsSet == 0xaa55)              // check if the clock was set or not
  {
  
  }
  else
  {
  
  }    
  delay(1000);                          // wait a second
}

11 comentarios:

  1. mi problema es el siguiente, tengo el módulo RTC Tiny con chip DS 1307, las conexiones realizadas funcionan perfecto de hecho funciona bien tomando lectura del reloj, el problema es cuando desconecto el reloj del arduino la hora se congela y cuando vuelvo a conectarlo arranca desde la hora en que fue desconectado del arduino, no es problema de batería, ya lo comprobé, tampoco conexiones y menos software, he probado con muchos y no consigo solucionar ese problema, agradezco si me ayudan con este problema tiene bloqueado mi proyecto. yO HICE TODO LO QUE DICE, PERO LA VERDAD SIGUE CON ESE PROBLEMA.

    ResponderEliminar
    Respuestas
    1. seguro quitaste las diagonales de estas lineas
      // TimeIsSet = 0xffff;
      // RTC.setRAM(54, (uint8_t *)&TimeIsSet, sizeof(uint16_t));
      debes dejarlas con ellas

      Eliminar
  2. gracias por tu post, funciono al 100

    ResponderEliminar
  3. Saludos, comentarles que detecte un detalle en el ejemplo:
    switch (RTC.dow) // Friendly printout the weekday
    {
    case 1:
    Serial.print("MON");
    break;
    case 2:
    Serial.print("TUE");
    break;
    case 3:
    Serial.print("WED");
    break;
    case 4:
    Serial.print("THU");
    break;
    case 5:
    Serial.print("FRI");
    break;
    case 6:
    Serial.print("SAT");
    break;
    case 7:
    Serial.print("SUN");
    break;

    SUN, no corresponde al dia 7, mas bien al dia 0

    gracias por su excelente trabajo...

    ResponderEliminar
  4. Amigo no entiendo algo en el codigo, por que es necesario ese if, por que no solo imprimir lo que esta en el else
    if (RTC.hour < 10) // correct hour if necessary
    {
    Serial.print("0");
    Serial.print(RTC.hour, DEC);
    }
    else
    {
    Serial.print(RTC.hour, DEC);
    }

    ResponderEliminar
    Respuestas
    1. al parecer, si la hora es menor que 10, imprimira un 0 antes
      es decir si son las 3 am pondra 03, si son las 2 pm pone 14

      Eliminar
  5. Este comentario ha sido eliminado por el autor.

    ResponderEliminar
  6. Este comentario ha sido eliminado por el autor.

    ResponderEliminar
  7. me gustaria saber si esta libreria y este modulo son compatibles con arduino mega adk 2560

    ResponderEliminar
  8. Hola: es posible conectar este módulo y el módulo de presión BMP180 juntos? los dos trabajan con I2C. Cómo se redireccionaría en este caso? Gracias

    ResponderEliminar
  9. hola amigo excelente explicacion tengo un problema con el reloj cuando lo desconecto de la alimentacion del arduino se ierde la configuracion ya compre bateria nueva del reloj y ni aun asi que pudiera ser o vino con defecto de fabrica que no reconoce la bateria

    ResponderEliminar