Exemplo de RTC Bluetooth com Arduino UNO R4 WiFi - Tutorial de Sincronização do Relógio de Tempo Real via BLE

Visão Geral

O exemplo de RTC Bluetooth oferece a sincronização do relógio de tempo real pelo app DIYables Bluetooth STEM. Feito para o Arduino UNO R4 WiFi usando BLE (Bluetooth Low Energy) para sincronizar o RTC de hardware embutido da placa com o relógio do seu smartphone e exibir a hora. O Arduino UNO R4 WiFi tem um módulo RTC embutido, o que o torna ideal para projetos de marcação de tempo sem precisar de hardware RTC externo. Perfeito para relógios, registro de dados com carimbo de data/hora, automação agendada e projetos baseados em horário.

Nota: O Arduino UNO R4 WiFi só suporta BLE (Bluetooth Low Energy). Ele não suporta Bluetooth Clássico. O app DIYables Bluetooth suporta BLE e Bluetooth Clássico no Android, e BLE no iOS. Como esta placa usa BLE, o app funciona no Android e no iOS.

Exemplo de RTC Bluetooth com Arduino UNO R4 WiFi - Tutorial de Sincronização do Relógio de Tempo Real via BLE

Recursos

  • RTC de Hardware Embutido: usa o RTC integrado do Arduino UNO R4 WiFi — não precisa de módulo externo
  • Sincronização com a Hora do Celular: sincronize o horário do smartphone por timestamp Unix ou por componentes da hora local
  • Exibição em Tempo Real: mostra a hora atual no app, atualizada a cada segundo
  • Solicitação de Hora: o app pode pedir a hora atual à placa
  • Marcação de Tempo Persistente: o RTC mantém a hora enquanto a placa estiver alimentada
  • Funciona no Android e no iOS: o BLE é suportado nas duas plataformas
  • Sem Necessidade de Pareamento: o BLE conecta automaticamente, sem pareamento manual

Hardware Necessário

1×Arduino UNO R4 WiFi
1×Alternatively, DIYables STEM V4 IoT
1×Alternatively, DIYables STEM V4B IoT
1×Cabo USB Tipo-A para Tipo-C (para PC com USB-A)
1×Cabo USB Tipo-C para Tipo-C (para PC com USB-C)
1×(Recomendado) Shield com Bornes de Parafuso para Arduino Uno R4
1×(Recomendado) Sensors/Servo Expansion Shield for Arduino UNO R4
1×(Recomendado) Shield de Protoboard para Arduino Uno R4
1×(Recomendado) Case para Arduino Uno R4
1×(Recomendado) Divisor de Alimentação para Arduino Uno R4
1×(Recomendado) Placa Base de Prototipagem e Kit de Protoboard para Arduino Uno

Or you can buy the following kits:

1×DIYables STEM V4 IoT Starter Kit (Arduino included)
1×DIYables STEM V4B IoT Starter Kit (Arduino included)
1×DIYables Sensor Kit (18 sensors/displays)
Divulgação: Alguns dos links desta seção são links de afiliado da Amazon. Podemos receber uma comissão pelas compras feitas por meio desses links, sem custo adicional para você. Agradecemos o seu apoio.
Arduino Uno R4 WiFi Compatible Boards

Nota: Não é preciso nenhum módulo RTC externo! O Arduino UNO R4 WiFi tem um RTC de hardware embutido, acessível pela biblioteca RTC.h.

Código Arduino UNO R4 WiFi

Passos Rápidos

Siga estas instruções passo a passo:

  • Se esta é a primeira vez que você usa o Arduino UNO R4 WiFi, consulte o guia de primeiros passos do Arduino UNO R4 WiFi.
  • Conecte a placa Arduino UNO R4 WiFi ao seu computador usando um cabo USB.
  • Abra o Arduino IDE no seu computador.
  • Selecione a placa Arduino UNO R4 WiFi e a porta COM apropriada.
  • Vá até o ícone Libraries na barra lateral esquerda do Arduino IDE.
  • Pesquise "DIYables Bluetooth" e encontre a biblioteca DIYables Bluetooth, da DIYables
  • Clique no botão Install para instalar a biblioteca.
Arduino UNO R4 DIYables Bluetooth library
  • Será pedido que você instale algumas outras dependências da biblioteca
  • Clique no botão Install All para instalar todas as dependências da biblioteca.
Arduino UNO R4 DIYables Bluetooth dependency

Código BLE

  • No Arduino IDE, vá em File Examples DIYables Bluetooth ArduinoBLE_RTC para abrir o exemplo, ou copie o código acima e cole no editor do Arduino IDE
/* * DIYables Bluetooth Library - Bluetooth RTC Example * Works with DIYables Bluetooth STEM app on Android and iOS * * This example demonstrates the Bluetooth RTC (Real-Time Clock) feature: * - Real-time clock display for both Arduino and mobile app * - One-click time synchronization from mobile app to Arduino * - Hardware RTC integration for persistent timekeeping * - Visual time difference monitoring * * Compatible Boards: * - Arduino UNO R4 WiFi (with built-in RTC) * Note: This example requires a board with hardware RTC. * Other BLE boards can be used with an external RTC module (e.g., DS3231). * * Setup: * 1. Upload the sketch to your Arduino * 2. Open Serial Monitor to see connection status * 3. Use DIYables Bluetooth App to connect and sync time * * Tutorial: https://diyables.io/bluetooth-app * Author: DIYables */ #include <DIYables_BluetoothServer.h> #include <DIYables_BluetoothRTC.h> #include <platforms/DIYables_ArduinoBLE.h> #include "RTC.h" // BLE Configuration const char* DEVICE_NAME = "Arduino_RTC"; const char* SERVICE_UUID = "19B10000-E8F2-537E-4F6C-D104768A1214"; const char* TX_UUID = "19B10001-E8F2-537E-4F6C-D104768A1214"; const char* RX_UUID = "19B10002-E8F2-537E-4F6C-D104768A1214"; // Create Bluetooth instances DIYables_ArduinoBLE bluetooth(DEVICE_NAME, SERVICE_UUID, TX_UUID, RX_UUID); DIYables_BluetoothServer bluetoothServer(bluetooth); // Create RTC app instance DIYables_BluetoothRTC bluetoothRTC; void setup() { Serial.begin(9600); delay(1000); Serial.println("DIYables Bluetooth - RTC Example"); // Initialize RTC RTC.begin(); // Check if RTC is running and set initial time if needed RTCTime savedTime; RTC.getTime(savedTime); if (!RTC.isRunning() || savedTime.getYear() == 2000) { Serial.println("RTC is NOT running, setting initial time..."); // Set a default time - you can modify this to match current time RTCTime startTime(28, Month::AUGUST, 2025, 12, 0, 0, DayOfWeek::THURSDAY, SaveLight::SAVING_TIME_ACTIVE); RTC.setTime(startTime); Serial.println("RTC initialized with default time"); } else { Serial.println("RTC is already running"); } // Print initial RTC time RTCTime initialTime; RTC.getTime(initialTime); Serial.print("Initial RTC Time: "); Serial.print(initialTime.getYear()); Serial.print("/"); Serial.print(Month2int(initialTime.getMonth())); Serial.print("/"); Serial.print(initialTime.getDayOfMonth()); Serial.print(" - "); if (initialTime.getHour() < 10) Serial.print("0"); Serial.print(initialTime.getHour()); Serial.print(":"); if (initialTime.getMinutes() < 10) Serial.print("0"); Serial.print(initialTime.getMinutes()); Serial.print(":"); if (initialTime.getSeconds() < 10) Serial.print("0"); Serial.print(initialTime.getSeconds()); Serial.println(); // Initialize Bluetooth server with platform-specific implementation bluetoothServer.begin(); // Add RTC app to server bluetoothServer.addApp(&bluetoothRTC); // Set up connection event callbacks bluetoothServer.setOnConnected([]() { Serial.println("Bluetooth connected!"); // Send current time to app on connection sendCurrentTimeToApp(); }); bluetoothServer.setOnDisconnected([]() { Serial.println("Bluetooth disconnected!"); }); // Set callback for time sync from mobile app (Unix timestamp) bluetoothRTC.onTimeSync(onTimeSyncReceived); // Set callback for local time sync from mobile app (date/time components) bluetoothRTC.onLocalTimeSync(onLocalTimeSyncReceived); // Set callback for time request from mobile app bluetoothRTC.onTimeRequest(onTimeRequested); Serial.println("Waiting for Bluetooth connection..."); Serial.println("Connect via app to sync time"); } void loop() { // Handle Bluetooth server communications bluetoothServer.loop(); // Send current time to mobile app and print to Serial every 1 second static unsigned long lastUpdate = 0; if (millis() - lastUpdate >= 1000) { lastUpdate = millis(); // Get current RTC time RTCTime currentTime; RTC.getTime(currentTime); // Send time to mobile app in human readable format bluetoothRTC.sendTime(currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds()); // Print time to Serial Monitor Serial.print("RTC Time: "); Serial.print(currentTime.getYear()); Serial.print("/"); Serial.print(Month2int(currentTime.getMonth())); Serial.print("/"); Serial.print(currentTime.getDayOfMonth()); Serial.print(" - "); if (currentTime.getHour() < 10) Serial.print("0"); Serial.print(currentTime.getHour()); Serial.print(":"); if (currentTime.getMinutes() < 10) Serial.print("0"); Serial.print(currentTime.getMinutes()); Serial.print(":"); if (currentTime.getSeconds() < 10) Serial.print("0"); Serial.print(currentTime.getSeconds()); Serial.println(); } delay(10); } // Callback function called when mobile app sends time sync command void onTimeSyncReceived(unsigned long unixTimestamp) { Serial.print("Time sync received (Unix): "); Serial.println(unixTimestamp); // Convert Unix timestamp to RTCTime RTCTime newTime; newTime.setUnixTime(unixTimestamp); // Set RTC time RTC.setTime(newTime); Serial.println("Arduino RTC synchronized from Unix timestamp!"); } // Callback function called when mobile app sends local time sync with components void onLocalTimeSyncReceived(int year, int month, int day, int hour, int minute, int second) { Serial.print("Local time sync received: "); Serial.print(year); Serial.print("/"); Serial.print(month); Serial.print("/"); Serial.print(day); Serial.print(" "); Serial.print(hour); Serial.print(":"); Serial.print(minute); Serial.print(":"); Serial.println(second); // Create RTCTime from components (local time) // Convert month integer to Month enum Month monthEnum; switch(month) { case 1: monthEnum = Month::JANUARY; break; case 2: monthEnum = Month::FEBRUARY; break; case 3: monthEnum = Month::MARCH; break; case 4: monthEnum = Month::APRIL; break; case 5: monthEnum = Month::MAY; break; case 6: monthEnum = Month::JUNE; break; case 7: monthEnum = Month::JULY; break; case 8: monthEnum = Month::AUGUST; break; case 9: monthEnum = Month::SEPTEMBER; break; case 10: monthEnum = Month::OCTOBER; break; case 11: monthEnum = Month::NOVEMBER; break; case 12: monthEnum = Month::DECEMBER; break; default: monthEnum = Month::JANUARY; break; } RTCTime newTime(day, monthEnum, year, hour, minute, second, DayOfWeek::MONDAY, SaveLight::SAVING_TIME_ACTIVE); // Set RTC time RTC.setTime(newTime); Serial.println("Arduino RTC synchronized from local time components!"); } // Callback function called when mobile app requests current Arduino time void onTimeRequested() { Serial.println("Time requested by app"); sendCurrentTimeToApp(); } // Helper function to send current time to mobile app void sendCurrentTimeToApp() { // Get current RTC time and send to app in human readable format RTCTime currentTime; RTC.getTime(currentTime); bluetoothRTC.sendTime(currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds()); }
  • Clique no botão Upload no Arduino IDE para carregar o código no Arduino UNO R4 WiFi
  • Abra o Serial Monitor
  • Veja o resultado no Serial Monitor. Ele deve ficar parecido com o abaixo:
∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
Arduino Uno R4 WiFi
Newbiely.ino
···
8 Serial.println("Hello World!");
Output
Serial Monitor
Message (Enter to send message to 'Arduino Uno R4 WiFi' on 'COM15')
New Line
9600 baud
DIYables Bluetooth - RTC Example Waiting for Bluetooth connection... RTC not running or year is 2000, waiting for time sync...
Ln 11, Col 1
Arduino Uno R4 WiFi on COM15
2

App para Celular

  • Instale o app DIYables Bluetooth no seu smartphone: Android | iOS

Nota: O app DIYables Bluetooth suporta BLE e Bluetooth Clássico no Android, e BLE no iOS. Como o Arduino UNO R4 WiFi usa BLE, o app funciona no Android e no iOS. Não é preciso pareamento manual para o BLE — basta procurar e conectar.

  • Abra o app DIYables Bluetooth
  • Ao abrir o app pela primeira vez, ele vai pedir permissões. Conceda as seguintes:
    • Permissão de Dispositivos por Perto (Android 12+) / permissão de Bluetooth (iOS) - necessária para procurar e conectar dispositivos Bluetooth
    • Permissão de Localização (somente Android 11 e anteriores) - exigida por versões mais antigas do Android para procurar dispositivos BLE
  • Verifique se o Bluetooth está ligado no seu celular
  • Na tela inicial, toque no botão Connect. O app vai procurar dispositivos BLE.
DIYables Bluetooth App - Home Screen with Scan Button
  • Encontre e toque em "Arduino_RTC" nos resultados da busca para conectar.
  • Depois de conectado, o app volta automaticamente para a tela inicial. Selecione o app RTC no menu de apps.
DIYables Bluetooth App - Home Screen with RTC App

Nota: Você pode tocar no ícone de configurações na tela inicial para ocultar/mostrar apps na tela inicial. Para mais detalhes, veja o Manual do Usuário do DIYables Bluetooth App.

  • O app vai exibir a hora atual do RTC do Arduino
  • Use o botão Sync para sincronizar a hora do celular com o Arduino
  • A hora é atualizada a cada segundo
DIYables Bluetooth App - RTC Screen

Agora volte ao Serial Monitor no Arduino IDE. Você verá:

∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
Arduino Uno R4 WiFi
Newbiely.ino
···
8 Serial.println("Hello World!");
Output
Serial Monitor
Message (Enter to send message to 'Arduino Uno R4 WiFi' on 'COM15')
New Line
9600 baud
Bluetooth connected! Time sync received (unix): 1719849600 RTC set to: 2025/07/01 12:00:00 Current time: 2025/07/01 12:00:01 Current time: 2025/07/01 12:00:02
Ln 11, Col 1
Arduino Uno R4 WiFi on COM15
2

Personalização Criativa - Adapte o Código ao Seu Projeto

Métodos de Sincronização de Horário

O app pode sincronizar o horário com o Arduino de duas formas:

// Method 1: Unix timestamp sync bluetoothRTC.onTimeSync([](unsigned long unixTime) { // Convert Unix timestamp and set RTC Serial.print("Unix time: "); Serial.println(unixTime); }); // Method 2: Local time components sync bluetoothRTC.onLocalTimeSync([](int year, int month, int day, int hour, int minute, int second) { // Set RTC directly with components Serial.print("Local time: "); Serial.print(year); Serial.print("/"); Serial.print(month); Serial.print("/"); Serial.println(day); });

Enviar a Hora para o App

// Send current time to the app bluetoothRTC.sendTime(year, month, day, hour, minute, second);

Tratar as Solicitações de Hora

bluetoothRTC.onTimeRequest([]() { // App is requesting the current time // Read RTC and send time back RTCTime currentTime; RTC.getTime(currentTime); bluetoothRTC.sendTime( currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds() ); });

Usando o RTC Embutido

O RTC embutido do Arduino UNO R4 WiFi é acessado pela biblioteca RTC.h:

#include "RTC.h" void setup() { RTC.begin(); // Initialize the hardware RTC } // Set time on the RTC RTCTime timeToSet; timeToSet.setYear(2025); timeToSet.setMonth(Month::JULY); timeToSet.setDayOfMonth(1); timeToSet.setHour(12); timeToSet.setMinute(0); timeToSet.setSecond(0); RTC.setTime(timeToSet); // Read time from the RTC RTCTime currentTime; RTC.getTime(currentTime); int year = currentTime.getYear(); int month = Month2int(currentTime.getMonth()); int day = currentTime.getDayOfMonth(); int hour = currentTime.getHour(); int minute = currentTime.getMinutes(); int second = currentTime.getSeconds();

Exemplos de Programação

Relógio com Exibição no Serial

void loop() { bluetoothServer.loop(); static unsigned long lastTime = 0; if (millis() - lastTime >= 1000) { lastTime = millis(); RTCTime currentTime; if (RTC.getTime(currentTime)) { char timeStr[20]; sprintf(timeStr, "%04d/%02d/%02d %02d:%02d:%02d", currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds()); Serial.println(timeStr); // Also send to the app bluetoothRTC.sendTime( currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds() ); } } }

Registrador de Dados com Carimbo de Data/Hora

void logSensorData() { RTCTime currentTime; RTC.getTime(currentTime); float temperature = readSensor(); char logEntry[50]; sprintf(logEntry, "%04d/%02d/%02d %02d:%02d:%02d - Temp: %.1f°C", currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds(), temperature); Serial.println(logEntry); }

Tutorial em Vídeo

O vídeo de demonstração abaixo usa o código abaixo:

/* * Este código de Arduino UNO R4 foi desenvolvido por pt.newbiely.com * Este código de Arduino UNO R4 é disponibilizado ao público sem nenhuma restrição. * Para tutoriais completos e diagramas de ligação, visite: * https://pt.newbiely.com/tutorials/arduino-uno-r4/arduino-uno-r4-diyables-bluetooth-app-rtc */ /* * DIYables Bluetooth Library - Bluetooth RTC Example * Works with DIYables Bluetooth STEM app on Android and iOS * * This example demonstrates the Bluetooth RTC (Real-Time Clock) feature: * - Real-time clock display for both Arduino and mobile app * - One-click time synchronization from mobile app to Arduino * - Hardware RTC integration for persistent timekeeping * - Visual time difference monitoring * * Compatible Boards: * - Arduino UNO R4 WiFi (with built-in RTC) * Note: This example requires a board with hardware RTC. * Other BLE boards can be used with an external RTC module (e.g., DS3231). * * Setup: * 1. Upload the sketch to your Arduino * 2. Open Serial Monitor to see connection status * 3. Use DIYables Bluetooth App to connect and sync time * * Tutorial: https://diyables.io/bluetooth-app * Author: DIYables */ #include <DIYables_BluetoothServer.h> #include <DIYables_BluetoothRTC.h> #include <platforms/DIYables_ArduinoBLE.h> #include "RTC.h" #include <MD_Parola.h> #include <MD_MAX72xx.h> // BLE Configuration const char* DEVICE_NAME = "Arduino_RTC"; const char* SERVICE_UUID = "19B10000-E8F2-537E-4F6C-D104768A1214"; const char* TX_UUID = "19B10001-E8F2-537E-4F6C-D104768A1214"; const char* RX_UUID = "19B10002-E8F2-537E-4F6C-D104768A1214"; // Create Bluetooth instances DIYables_ArduinoBLE bluetooth(DEVICE_NAME, SERVICE_UUID, TX_UUID, RX_UUID); DIYables_BluetoothServer bluetoothServer(bluetooth); // Create RTC app instance DIYables_BluetoothRTC bluetoothRTC; // --- DISPLAY SUBSYSTEM CONFIGURATION --- #define HARDWARE_TYPE MD_MAX72XX::FC16_HW // Hardware register layout variant for physical modules #define MAX_DEVICES 4 // Number of cascaded 8x8 matrix blocks #define CS_PIN 9 // SPI Chip Select active-low hardware pin MD_Parola ledMatrix = MD_Parola(HARDWARE_TYPE, CS_PIN, MAX_DEVICES); // --- ALARM SUBSYSTEM ARCHITECTURE --- const int BUZZER_PIN = 8; bool isAlarming = false; // State flag to prevent redundant re-initialization of display buffers struct AlarmTime { int hour; int minute; }; // Scheduled alarm matrices for daily medication dispatch const int TOTAL_ALARMS = 3; AlarmTime medicationAlarms[TOTAL_ALARMS] = { {12, 53}, // Slot 1: Morning Dose {12, 54}, // Slot 2: Noon Dose {12, 55} // Slot 3: Evening Dose }; // Fixed-size static allocation to prevent dangling pointers during stack deallocation char AlertMsg[50] = ""; void setup() { Serial.begin(9600); delay(1000); // Configure GPIO peripherals pinMode(BUZZER_PIN, OUTPUT); digitalWrite(BUZZER_PIN, LOW); // Initialize SPI-driven LED Matrix ledMatrix.begin(); ledMatrix.setIntensity(3); // Brightness optimization register value to prevent camera sensor overexposure ledMatrix.displayClear(); // Set initial boot token into display queue ledMatrix.displayText("Medicine Reminder System READY", PA_LEFT, 60, 2000, PA_SCROLL_LEFT, PA_SCROLL_LEFT); Serial.println("DIYables Bluetooth - RTC Example"); // Initialize RTC RTC.begin(); // Check if RTC is running and set initial time if needed RTCTime savedTime; RTC.getTime(savedTime); if (!RTC.isRunning() || savedTime.getYear() == 2000) { Serial.println("RTC is NOT running, setting initial time..."); // Set a default time - you can modify this to match current time RTCTime startTime(25, Month::MAY, 2026, 8, 13, 0, DayOfWeek::THURSDAY, SaveLight::SAVING_TIME_ACTIVE); RTC.setTime(startTime); Serial.println("RTC initialized with default time"); } else { Serial.println("RTC is already running"); } // Print initial RTC time RTCTime initialTime; RTC.getTime(initialTime); Serial.print("Initial RTC Time: "); Serial.print(initialTime.getYear()); Serial.print("/"); Serial.print(Month2int(initialTime.getMonth())); Serial.print("/"); Serial.print(initialTime.getDayOfMonth()); Serial.print(" - "); if (initialTime.getHour() < 10) Serial.print("0"); Serial.print(initialTime.getHour()); Serial.print(":"); if (initialTime.getMinutes() < 10) Serial.print("0"); Serial.print(initialTime.getMinutes()); Serial.print(":"); if (initialTime.getSeconds() < 10) Serial.print("0"); Serial.print(initialTime.getSeconds()); Serial.println(); // Initialize Bluetooth server with platform-specific implementation bluetoothServer.begin(); // Add RTC app to server bluetoothServer.addApp(&bluetoothRTC); // Set up connection event callbacks bluetoothServer.setOnConnected([]() { Serial.println("Bluetooth connected!"); // Send current time to app on connection sendCurrentTimeToApp(); }); bluetoothServer.setOnDisconnected([]() { Serial.println("Bluetooth disconnected!"); }); // Set callback for time sync from mobile app (Unix timestamp) bluetoothRTC.onTimeSync(onTimeSyncReceived); // Set callback for local time sync from mobile app (date/time components) bluetoothRTC.onLocalTimeSync(onLocalTimeSyncReceived); // Set callback for time request from mobile app bluetoothRTC.onTimeRequest(onTimeRequested); Serial.println("Waiting for Bluetooth connection..."); Serial.println("Connect via app to sync time"); } void loop() { // Handle Bluetooth server communications bluetoothServer.loop(); // Non-blocking shift engine: Calculates next step pixel translations on every pass if (ledMatrix.displayAnimate()) { ledMatrix.displayReset(); } // Send current time to mobile app and print to Serial every 1 second static unsigned long lastUpdate = 0; if (millis() - lastUpdate >= 1000) { lastUpdate = millis(); // Get current RTC time RTCTime currentTime; RTC.getTime(currentTime); int currentH = currentTime.getHour(); int currentM = currentTime.getMinutes(); int currentS = currentTime.getSeconds(); // Send time to mobile app in human readable format bluetoothRTC.sendTime(currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds()); // Print time to Serial Monitor Serial.print("RTC Time: "); Serial.print(currentTime.getYear()); Serial.print("/"); Serial.print(Month2int(currentTime.getMonth())); Serial.print("/"); Serial.print(currentTime.getDayOfMonth()); Serial.print(" - "); if (currentTime.getHour() < 10) Serial.print("0"); Serial.print(currentTime.getHour()); Serial.print(":"); if (currentTime.getMinutes() < 10) Serial.print("0"); Serial.print(currentTime.getMinutes()); Serial.print(":"); if (currentTime.getSeconds() < 10) Serial.print("0"); Serial.print(currentTime.getSeconds()); Serial.println(); // Sequential search scan across active alarm vectors for (int i = 0; i < TOTAL_ALARMS; i++) { if (currentH == medicationAlarms[i].hour && currentM == medicationAlarms[i].minute && currentS == 0) { // Conditional gate to prevent continuous buffer overwrites within the same second if (!isAlarming) { isAlarming = true; // Low-level buffer formatting to map runtime integers into locked memory space // %02d pads leading zeros to preserve fixed structural layout formatting [HH:MM] sprintf(AlertMsg, "TAKE MEDICATION ! [%02d:%02d] ", currentH, currentM); ledMatrix.displayClear(); // Link the safe static memory pointer directly into the display rendering core ledMatrix.displayText(AlertMsg, PA_LEFT, 60, 0, PA_SCROLL_LEFT, PA_SCROLL_LEFT); Serial.print("[ALARM] Array index match detected at slot ID: "); Serial.println(i + 1); } } } // Auto-timeout block: Clears state metrics after 30 elapsed duty seconds if (currentS >= 20 && isAlarming) { isAlarming = false; ledMatrix.displayClear(); ledMatrix.displayText("Medicine Reminder System With APP RTC", PA_LEFT, 60, 0, PA_SCROLL_LEFT, PA_SCROLL_LEFT); Serial.println("[ALARM] Trigger window expired. Display registers reset to default state."); } } // Asynchronous Active Buzzer Duty Cycle Control (50% duty cycle, 1Hz rate square-wave generator) if (isAlarming) { static unsigned long lastBuzzerToggle = 0; if (millis() - lastBuzzerToggle >= 500) { lastBuzzerToggle = millis(); digitalWrite(BUZZER_PIN, !digitalRead(BUZZER_PIN)); // Invert state logic } } else { digitalWrite(BUZZER_PIN, LOW); // Enforce noise suppression when system state is idle } delay(10); } // Callback function called when mobile app sends time sync command void onTimeSyncReceived(unsigned long unixTimestamp) { Serial.print("Time sync received (Unix): "); Serial.println(unixTimestamp); // Convert Unix timestamp to RTCTime RTCTime newTime; newTime.setUnixTime(unixTimestamp); // Set RTC time RTC.setTime(newTime); Serial.println("Arduino RTC synchronized from Unix timestamp!"); } // Callback function called when mobile app sends local time sync with components void onLocalTimeSyncReceived(int year, int month, int day, int hour, int minute, int second) { Serial.print("Local time sync received: "); Serial.print(year); Serial.print("/"); Serial.print(month); Serial.print("/"); Serial.print(day); Serial.print(" "); Serial.print(hour); Serial.print(":"); Serial.print(minute); Serial.print(":"); Serial.println(second); // Create RTCTime from components (local time) // Convert month integer to Month enum Month monthEnum; switch(month) { case 1: monthEnum = Month::JANUARY; break; case 2: monthEnum = Month::FEBRUARY; break; case 3: monthEnum = Month::MARCH; break; case 4: monthEnum = Month::APRIL; break; case 5: monthEnum = Month::MAY; break; case 6: monthEnum = Month::JUNE; break; case 7: monthEnum = Month::JULY; break; case 8: monthEnum = Month::AUGUST; break; case 9: monthEnum = Month::SEPTEMBER; break; case 10: monthEnum = Month::OCTOBER; break; case 11: monthEnum = Month::NOVEMBER; break; case 12: monthEnum = Month::DECEMBER; break; default: monthEnum = Month::JANUARY; break; } RTCTime newTime(day, monthEnum, year, hour, minute, second, DayOfWeek::MONDAY, SaveLight::SAVING_TIME_ACTIVE); // Set RTC time RTC.setTime(newTime); Serial.println("Arduino RTC synchronized from local time components!"); } // Callback function called when mobile app requests current Arduino time void onTimeRequested() { Serial.println("Time requested by app"); sendCurrentTimeToApp(); } // Helper function to send current time to mobile app void sendCurrentTimeToApp() { // Get current RTC time and send to app in human readable format RTCTime currentTime; RTC.getTime(currentTime); bluetoothRTC.sendTime(currentTime.getYear(), Month2int(currentTime.getMonth()), currentTime.getDayOfMonth(), currentTime.getHour(), currentTime.getMinutes(), currentTime.getSeconds()); }

Solução de Problemas

Problemas Comuns

1. Não consigo encontrar o dispositivo no app

  • Verifique se o Arduino UNO R4 WiFi está ligado e se o sketch foi carregado
  • Verifique se o Bluetooth do seu celular está ativado
  • No Android 11 e anteriores, ative também os serviços de Localização

2. A hora mostra 2000/01/01 ou um horário incorreto

  • O RTC precisa ser sincronizado pelo menos uma vez após ligar a placa
  • Use o botão Sync do app para definir a hora
  • O RTC perde a hora quando a placa é desligada (não há bateria de reserva)

3. A hora não sincroniza a partir do app

  • Confirme que os callbacks onTimeSync e onLocalTimeSync estão configurados
  • Verifique as mensagens de sincronização no Serial Monitor
  • Garanta que a conexão BLE está estável

4. O RTC se desvia com o tempo

  • O cristal do RTC embutido tem precisão limitada
  • Sincronize novamente de tempos em tempos pelo app
  • Para uma marcação de tempo crítica, considere usar também NTP via WiFi

5. Problemas na conversão do mês

  • O RTC do Arduino UNO R4 WiFi usa um enum Month, não um inteiro
  • Use uma função de conversão (como Month2int() no exemplo) para obter o mês como inteiro
  • Os meses começam em 1 (janeiro = 1)

6. O upload falha ou a placa não é reconhecida

  • Instale o pacote de placas Arduino UNO R4 mais recente pelo Board Manager
  • Tente outro cabo ou outra porta USB

Ideias de Projetos

  • Relógio digital com sincronização de horário por BLE
  • Registrador de dados com carimbos de data/hora precisos
  • Automação de tarefas agendadas (ligar/desligar em horários específicos)
  • Despertador controlado pelo smartphone
  • Registrador de eventos com carimbo de data/hora

Próximos Passos

Depois de dominar o exemplo de RTC Bluetooth, experimente:

  1. Bluetooth Monitor - Para exibir o status em texto com carimbos de data/hora
  2. Bluetooth Table - Para dados estruturados com campos de horário
  3. Bluetooth Chat - Para comunicação nos dois sentidos
  4. Multiple Bluetooth Apps - Combinando o RTC com outros apps

Suporte

Para ajuda adicional:

  • Consulte a documentação de Referência da API
  • Fóruns da comunidade Arduino

※ NOSSAS MENSAGENS

  • Fique à vontade para compartilhar o link deste tutorial. Porém, por favor, não use nosso conteúdo em outros sites. Investimos muito esforço e tempo para criar este conteúdo, por favor respeite nosso trabalho!