DS3231 RTC (Real Time Clock) Interfacing with Arduino to build DIY Digital Clock

Published  May 11, 2022   0
Arduino DS3231 RTC Module

In today's world, time is everything, and when it comes to specific electronics, timing is critical; just like us, humans, they also need a way to keep track of time. So how do electronics do it? The answer is DS3231, a Real-Time Clock, often known as an RTC, is a timekeeping device built into an Integrated Circuit, or IC. It is used in many time-critical applications and devices, such as servers, GPS, and data loggers. Let's see what makes it TICK.

DS3231 RTC Module Introduction

The DS3231 is an I2C real-time clock (RTC) with an inbuilt temperature compensated crystal oscillator (TCXO) and crystal that is both low-cost and exceptionally precise. When the module's power is interrupted, the device has a battery input and keeps a precise time. The device's long-term precision is improved by the inclusion of the crystal oscillator. The RTC keeps track of seconds, minutes, hours, days, dates, months, and years. For months with less than 31 days, the date at the end of the month is automatically modified, including leap year corrections. The clock has an AM/PM indication and works in either a 24-hour or 12-hour mode. Two programmable time-of-day alarms are included, as well as a programmable square-wave output. An I2C bidirectional bus is used to transport address and data serially.

DS3231 Module Pinout

The DS3231 module has 6 pins to get data from the module and supply power to the board. The pinout of DS3231 is as follows:-

DS3231 RTC Module Pinout

32K 32K oscillator output

SQW Square Wave output pin

SCL Serial Clock pin (I2C interface)

SDA Serial Data pin (I2C interface)

VCC Connected to the positive of power source

GND connected to the ground

When we probe the DS3231 Module’s 32k pin using an Oscilloscope, we get a 32kHz signal from the IC’s internal oscillator.

DS3231 RTC Signal

DS3231 Module Parts

The key components of a typical DS3231 RTC Module board are the DS3231 IC and the AT24C32 EEPROM IC to store the time and date data. Other components include a Power ON LED, a few resistors, capacitors, a battery holder, and pins for connecting to the microcontroller.

DS3231 RTC Module Components

When the main power to the module is stopped, the DS3231 contains a battery input and maintains accurate time. The built-in power-sense circuit constantly checks the condition of VCC to identify power outages and switches to the backup supply automatically. So, even if the power goes out, your MCU will still be able to maintain track of time. On the DS3231 RTC Module, there is a CR2032 battery holder. A battery holder for a 20mm 3V lithium coin cell is located on the board's bottom side. Any CR2032 battery will work.

Charging Capability:

The module is designed in such a way that when powered externally, it can charge the battery installed on the module. But one must be careful while using a non-rechargeable CR2032 Cell, as the module will also charge the cell. The CR2032 is a 3V cell that is not rechargeable, but a rechargeable cell can be charged to 4.2V. To stop the module from charging the CR2032 non-rechargeable cell, the U4(220R) Resistor or D1 (1N4148) Diode should be desoldered.

Frequently Asked Questions about the DS3231

Q. What is the difference between DS1307 and DS3231?

The most significant difference between the DS3231 and the DS1370 is the timekeeping accuracy. For timekeeping, the DS1307 has an external 32kHz crystal oscillator, while the DS3231 has an internal oscillator.

Q. How accurate is DS3231?

The temperature-compensated crystal oscillator (TCXO) in the DS3231 and DS3234 fits the bill, with precision as good as ±2 ppm in temperatures ranging from 0°C to +40°C.

Q. What battery does DS3231 use?

The DS3231 uses a CR2032 rechargeable cell but if one wants to use a non-rechargeable cell, a minor modification is to be made to the module.

DS3231 Module Schematic

DS3231 RTC Module Internal Schematic

Programming the DS3231 and Setting Time

Setting up time in the DS3231 module is fairly simple. All you need to do is connect it to the Arduino in the below configuration.

Arduino DS3231 RTC Module Circuit

After making the above connections, you need to connect the Arduino UNO to your PC, open Arduino IDE, and install Arduino DS3231 Time Set Library. Open the Arduino IDE and select Library Manager from the menu bar. Now look for RTCLib and DS3231 and get the most recent version, as shown in the figure below.

Arduino DS3231 Library

Code for Setting time in DS3231

The code is quite straightforward. It will set the time and then show it on the serial monitor.

rtc.adjust(DateTime(F(__DATE__),F(__TIME__)));

The rtc object sets the time according to the time on your computer in this line. It will change your system's current clock time.

rtc.adjust(DateTime(2014, 1, 21, 3, 0, 0));

You may manually set the time in this line by passing the date-time value to the function in the following order: year, month, date, hour, minute, and second. We'll set the time of the system in the code below. As a result, we have commented out this line.

#include <RTClib.h>
#include <Wire.h>
RTC_DS3231 rtc;
char t[32];
void setup()
{
  Serial.begin(9600);
  Wire.begin();
  rtc.begin();
  rtc.adjust(DateTime(F(__DATE__),F(__TIME__)));
  //rtc.adjust(DateTime(2019, 1, 21, 5, 0, 0));
}
void loop()
{
  DateTime now = rtc.now();
  sprintf(t, "%02d:%02d:%02d %02d/%02d/%02d", now.hour(), now.minute(), now.second(), now.day(), now.month(), now.year());  
  Serial.print(F("Date/Time: "));
  Serial.println(t);
  delay(1000);
}

Now Let's Make a DIY Arduino Digital Clock using DS3231 and LCD

Material Required:

  • Arduino Uno
  • DS3231 RTC Module
  • LCD Display 16*2
  • Jumper Wire
  • 10K Preset
  • 3V coin cell (CR2032)

Arduino Digital Clock Circuit Diagram 

Arduino Digital Clock Circuit

  • Connect SCL of RTC module to the Arduino A5
  • Connect SDA of RTC module to the Arduino A4
  • Connect VCC to 5v and GND to GND
  • Connect RS of LCD to pin 7 of Arduino
  • Connect E of LCD to pin 6 of Arduino
  • Connect D7 of LCD to pin 2 of Arduino
  • Connect D6 of LCD to pin 3 of Arduino
  • Connect D5 of LCD to pin 4 of Arduino
  • Connect D4 of LCD to pin 5 of Arduino
  • Connect VSS,K,RW,D0,D1,D2,D3 to the GND
  • Connect VDD & A to the 5v
  • Connect VO to the potentiometer output pin ( To control the contrast of text)

Code to display time on LCD

We include the below header files to the code, Wire.h to use I2C to communicate with the module, LiquidCrystal.h to show time on the LCD display, RTClib.h to set time to the display and format it.

#include <Wire.h>
#include <LiquidCrystal.h>
#include <RTClib.h>

This line in the code specifies which pin of the LCD is connected to which pin of the Arduino.

LiquidCrystal lcd(7, 6, 5, 4, 3, 2); // (rs, e, d4, d5, d6, d7)

If the project is fired up with some break in the connection, the code will print RTC Module not Present, in the serial monitor.

if (! rtc.begin())
  {
    Serial.println(" RTC Module not Present");
    while (1);
  }

If in case the RTC loses power and the time in the module goes wrong, the code will automatically set the time in the module and it will take the time from the computer's clock. So make sure while setting time, the clock on your PC is set at the right time.

if (rtc.lostPower())
  {
    Serial.println("RTC power failure, reset the time!");
    rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
  }

This section of the code sets the cursor on the LCD to 0 and prints the date in the format Date/Month/Year.

void displayDate()
 {
  lcd.setCursor(0,0);
  lcd.print("Date:");
  lcd.print(now.day());
  lcd.print('/');
  lcd.print(now.month());
  lcd.print('/');
  lcd.print(now.year());
 }

This section of the code sets the cursor to 1 and prints the time in the format Hour:Minute:Second.

 void displayTime()
 {
  lcd.setCursor(0,1);
  lcd.print("Time:");
  lcd.print(now.hour());
  lcd.print(':');
  lcd.print(now.minute());
  lcd.print(':');
  lcd.print(now.second());
  lcd.print("    ");
 }

After uploading the code you will be able to see the date and time on the LCD screen.

Supporting Files

Code

#include <Wire.h>

#include <LiquidCrystal.h>

#include <RTClib.h>

DateTime now;

RTC_DS3231 rtc;

LiquidCrystal lcd(7, 6, 5, 4, 3, 2); // (rs, e, d4, d5, d6, d7)

void displayDate(void);

void displayTime(void);

void setup ()

{

  Serial.begin(9600);

  lcd.begin(16,2);

  if (! rtc.begin())

  {

    Serial.println(" RTC Module not Present");

    while (1);

  }

  if (rtc.lostPower())

  {

    Serial.println("RTC power failure, reset the time!");

    rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));

  }

}

void loop ()

{

  now = rtc.now();

  displayDate();

  displayTime();

}

 void displayDate()

 {

  lcd.setCursor(0,0);

  lcd.print("Date:");

  lcd.print(now.day());

  lcd.print('/');

  lcd.print(now.month());

  lcd.print('/');

  lcd.print(now.year());

 }

 void displayTime()

 {

  lcd.setCursor(0,1);

  lcd.print("Time:");

  lcd.print(now.hour());

  lcd.print(':');

  lcd.print(now.minute());

  lcd.print(':');

  lcd.print(now.second());

  lcd.print("    ");

 }

 

To set the Time

#include <RTClib.h>

#include <Wire.h>

RTC_DS3231 rtc;

char t[32];

void setup()

{

  Serial.begin(9600);

  Wire.begin();

  rtc.begin();

  rtc.adjust(DateTime(F(__DATE__),F(__TIME__)));

  //rtc.adjust(DateTime(2014, 1, 21, 3, 0, 0));

}

void loop()

{

  DateTime now = rtc.now();

  sprintf(t, "%02d:%02d:%02d %02d/%02d/%02d",  now.hour(), now.minute(), now.second(), now.day(), now.month(), now.year());  

  Serial.print(F("Date/Time: "));

  Serial.println(t);

  delay(1000);

}