아두이노 우노 R4 WiFi 블루투스 RTC 예제 BLE를 통한 실시간 시계 동기화 튜토리얼

개요

블루투스 RTC 예제는 DIYables 블루투스 STEM 앱을 통해 실시간 시계 동기화 기능을 제공합니다. BLE(Bluetooth Low Energy) 를 사용하는 Arduino UNO R4 WiFi 전용으로 설계되어 보드의 내장 하드웨어 RTC를 스마트폰 시계와 동기화하고 시간을 표시합니다. Arduino UNO R4 WiFi에는 내장 RTC 모듈이 있어 외부 RTC 하드웨어 없이도 시간 관리 프로젝트에 이상적입니다. 시계, 타임스탬프가 있는 데이터 로깅, 예약된 자동화, 시간 기반 프로젝트에 적합합니다.

참고: Arduino UNO R4 WiFi는 BLE(Bluetooth Low Energy)만 지원합니다. 클래식 블루투스는 지원하지 않습니다. DIYables 블루투스 앱은 Android에서 BLE와 클래식 블루투스를 모두 지원하고, iOS에서는 BLE를 지원합니다. 이 보드는 BLE를 사용하므로 앱은 Android와 iOS 모두에서 작동합니다.

아두이노 우노 R4 와이파이 블루투스 rtc 예제 - BLE를 통한 실시간 시계 동기화 튜토리얼

기능

  • 내장 하드웨어 RTC: Arduino UNO R4 WiFi의 온보드 RTC 사용 - 외부 모듈 불필요
  • 스마트폰 시간 동기화: Unix 타임스탬프 또는 로컬 시간 구성 요소를 통해 스마트폰에서 시간 동기화
  • 실시간 표시: 앱에 현재 시간 표시, 매초 업데이트
  • 시간 요청: 앱에서 보드에서 현재 시간 요청 가능
  • 지속적인 시간 유지: 보드에 전원이 있는 동안 RTC가 시간 유지
  • Android 및 iOS에서 작동: BLE는 두 플랫폼 모두에서 지원
  • 페어링 불필요: BLE는 수동 페어링 없이 자동 연결

필요한 하드웨어

1×아두이노 우노 R4 와이파이 쿠팡 | 아마존
1×(또는) DIYables STEM V4 IoT 쿠팡 | 아마존
1×USB 케이블 타입-A to 타입-C (USB-A PC용) 쿠팡 | 아마존
1×USB 케이블 타입-C to 타입-C (USB-C PC용) 아마존
1×(추천) 아두이노 우노 R4용 스크루 터미널 블록 쉴드 쿠팡 | 아마존
1×(추천) Sensors/Servo Expansion Shield for Arduino UNO R4 아마존
1×(추천) 아두이노 우노 R4용 브레드보드 쉴드 쿠팡 | 아마존
1×(추천) 아두이노 우노 R4용 케이스 쿠팡 | 아마존
1×(추천) 아두이노 우노 R4용 전원 분배기 쿠팡 | 아마존
1×(추천) 아두이노 우노용 프로토타이핑 베이스 플레이트 & 브레드보드 키트 아마존
공개: 이 포스팅 에 제공된 일부 링크는 아마존 제휴 링크입니다. 이 포스팅은 쿠팡 파트너스 활동의 일환으로, 이에 따른 일정액의 수수료를 제공받습니다.
Arduino Uno R4 WiFi Compatible Boards

참고: 외부 RTC 모듈은 필요하지 않습니다! Arduino UNO R4 WiFi에는 RTC.h 라이브러리를 통해 접근할 수 있는 내장 하드웨어 RTC가 있습니다.

Arduino UNO R4 WiFi 코드

빠른 단계

다음 단계를 순서대로 따라하세요:

  • Arduino UNO R4 WiFi를 처음 사용하는 경우 아두이노 우노 R4 - 소프트웨어 설치를 참조하세요.
  • USB 케이블을 사용하여 Arduino UNO R4 WiFi 보드를 컴퓨터에 연결합니다.
  • 컴퓨터에서 Arduino IDE를 실행합니다.
  • Arduino UNO R4 WiFi 보드와 적절한 COM 포트를 선택합니다.
  • Arduino IDE 왼쪽 바에서 Libraries 아이콘으로 이동합니다.
  • "DIYables Bluetooth"를 검색한 다음 DIYables의 DIYables Bluetooth 라이브러리를 찾습니다.
  • Install 버튼을 클릭하여 라이브러리를 설치합니다.
아두이노 우노 R4 diyaBLEs 블루투스 라이브러리
  • 다른 라이브러리 종속성 설치를 요청받습니다.
  • Install All 버튼을 클릭하여 모든 라이브러리 종속성을 설치합니다.
아두이노 우노 R4 diyaBLEs 블루투스 종속성

BLE 코드

  • Arduino IDE에서 File Examples DIYables Bluetooth ArduinoBLE_RTC 예제로 이동하거나, 위의 코드를 복사하여 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()); }
  • Arduino IDE에서 Upload 버튼을 클릭하여 코드를 Arduino UNO R4 WiFi에 업로드합니다.
  • 시리얼 모니터를 엽니다.
  • 시리얼 모니터에서 결과를 확인합니다. 아래와 같이 표시됩니다:
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

모바일 앱

  • 스마트폰에 DIYables 블루투스 앱을 설치하세요: Android | iOS

참고: DIYables 블루투스 앱은 Android에서 BLE와 클래식 블루투스를 모두 지원하고, iOS에서는 BLE를 지원합니다. Arduino UNO R4 WiFi는 BLE를 사용하므로 앱은 Android와 iOS 모두에서 작동합니다. BLE에는 수동 페어링이 필요 없으며 스캔하고 연결하기만 하면 됩니다.

  • DIYables 블루투스 앱을 엽니다.
  • 처음 앱을 열면 권한을 요청합니다. 다음을 허용해 주세요:
    • 주변 기기(Nearby Devices) 권한(Android 12+) / 블루투스 권한(iOS) - 블루투스 기기를 스캔하고 연결하는 데 필요합니다.
    • 위치(Location) 권한(Android 11 이하만 해당) - 구형 Android 버전에서 BLE 기기를 스캔하는 데 필요합니다.
  • 휴대폰에서 블루투스가 켜져 있는지 확인합니다.
  • 홈 화면에서 Connect 버튼을 탭합니다. 앱이 BLE 기기를 스캔합니다.
diyaBLEs 블루투스 앱 - 스캔 버튼이 있는 홈 화면
  • 스캔 결과에서 "Arduino_RTC"를 찾아 탭하여 연결합니다.
  • 연결되면 앱이 자동으로 홈 화면으로 돌아갑니다. 앱 메뉴에서 RTC 앱을 선택합니다.
diyaBLEs 블루투스 앱 - rtc 앱이 있는 홈 화면

참고: 홈 화면의 설정 아이콘을 탭하면 앱을 표시하거나 숨길 수 있습니다. 자세한 내용은 DIYables 블루투스 앱 사용 설명서를 참조하세요.

  • 앱에 Arduino의 RTC에서 가져온 현재 시간이 표시됩니다.
  • 동기화(Sync) 버튼을 사용하여 스마트폰의 시간을 Arduino에 동기화하세요.
  • 시간은 매초 업데이트됩니다.
diyaBLEs 블루투스 앱 - rtc 화면

이제 Arduino IDE의 시리얼 모니터를 다시 확인하세요. 다음과 같이 표시됩니다:

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

창의적인 커스터마이징 - 프로젝트에 맞게 코드 적용하기

시간 동기화 방법

앱은 두 가지 방법으로 Arduino에 시간을 동기화할 수 있습니다:

// 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); });

앱으로 시간 전송

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

시간 요청 처리

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() ); });

내장 RTC 사용

Arduino UNO R4 WiFi의 내장 RTC는 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();

프로그래밍 예제

시리얼 표시가 있는 시계

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() ); } } }

타임스탬프가 있는 데이터 로거

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); }

문제 해결

일반적인 문제

1. 앱에서 기기를 찾을 수 없음

  • Arduino UNO R4 WiFi가 전원이 켜져 있고 스케치가 업로드되어 있는지 확인하세요.
  • 휴대폰의 블루투스가 활성화되어 있는지 확인하세요.
  • Android 11 이하에서는 위치 서비스도 활성화하세요.

2. 시간이 2000/01/01 또는 잘못된 시간을 표시함

  • RTC는 전원 투입 후 최소 한 번 동기화되어야 합니다.
  • 앱의 동기화 버튼을 사용하여 시간을 설정하세요.
  • 보드 전원이 꺼지면 RTC가 시간을 잃습니다(배터리 백업 없음).

3. 앱에서 시간 동기화가 안 됨

  • onTimeSynconLocalTimeSync 콜백이 설정되어 있는지 확인하세요.
  • 동기화 메시지에 대한 시리얼 모니터를 확인하세요.
  • BLE 연결이 안정적인지 확인하세요.

4. 시간이 지남에 따라 오차가 생김

  • 내장 RTC 크리스탈의 정확도는 제한적입니다.
  • 앱을 통해 주기적으로 재동기화하세요.
  • 중요한 시간 측정의 경우 WiFi를 통한 NTP 사용도 고려하세요.

5. 월 변환 문제

  • Arduino UNO R4 WiFi RTC는 정수가 아닌 Month 열거형을 사용합니다.
  • 정수 월에는 변환 함수(예제의 Month2int())를 사용하세요.
  • 월은 1부터 시작합니다(1월 = 1).

6. 업로드 실패 또는 보드를 인식하지 못함

  • 보드 관리자를 통해 최신 Arduino UNO R4 보드 패키지를 설치하세요.
  • 다른 USB 케이블이나 포트를 사용해 보세요.

프로젝트 아이디어

  • BLE 시간 동기화가 있는 디지털 시계
  • 정확한 타임스탬프가 있는 데이터 로거
  • 예약된 작업 자동화(특정 시간에 켜기/끄기)
  • 스마트폰으로 제어하는 알람 시계
  • 타임스탬프가 찍힌 이벤트 기록기

다음 단계

블루투스 RTC 예제를 마스터한 후 다음을 시도해 보세요:

  1. 블루투스 모니터 - 타임스탬프가 있는 텍스트 기반 상태 표시용
  2. 블루투스 테이블 - 시간 필드가 있는 구조화된 데이터용
  3. 블루투스 채팅 - 양방향 통신용
  4. 다중 블루투스 앱 - RTC와 다른 앱 결합

지원

추가 도움이 필요하면:

  • API 레퍼런스 문서를 확인하세요.
  • DIYables 튜토리얼을 방문하세요.
  • Arduino 커뮤니티 포럼