5주차 스마트디바이스(블루투스) - jungjaeyeol/jyeol03 GitHub Wiki

1. 근거리 무선통신이란?

  • 근거리 무선통신이란 짧은 거리(보통 수 센티미터에서 수십 미터 이내)에서 케이블 없이 데이터를 주고받는 기술을 말합니다. 이 기술은 간편성, 휴대성, 저전력 등의 장점 덕분에 스마트폰, 웨어러블, 결제 시스템 등 다양한 분야에 활용되고 있습니다.

대표적인 근거리 무선통신 기술

1. 블루투스(Bluetooth)

  • 범위 : 약 10m 내외 (버전에 따라 최대 100m)

  • 특징 : 저전력, 간편한 페어링, 이어폰/키보드/스피커 등에 활용

2. 와이파이 다이렉트(Wi-Fi Direct)

  • 범위 : 수십 m
  • 특징 : 무선 인터넷 없이도 기기 간 직접 연결, 대용량 파일 전송 가능

3. NFC(Near Field Communication)

  • 범위 : 약 10cm 이내
  • 특징: 아주 짧은 거리에서 빠른 연결, 모바일 결제(삼성페이, 애플페이 등)에 주로 사용

4. 적외선 통신(IrDA)

  • 범위 : 수 m 이내
  • 특징 : 과거 휴대폰에서 많이 사용, 현재는 거의 사라짐

5. ZigBee / Z-Wave

  • 범위 : 약 10 ~ 100m
  • 특징 : 스마트홈, IoT 기기용, 전력 소모가 매우 적음

2. 블루투스의 개념

  • 블루투스는 근거리 무선 통신 기술로, 스마트폰, 스피커, IoT 기기 등에서 널리 사용됩니다. ESP32에서는 **클래식 블루투스(Classic Bluetooth)**와 BLE(Bluetooth Low Energy) 두 가지 방식을 지원합니다. 일반적으로 10m 이내의 거리에서 사용되며, 전력을 적게 사용하면서도 간편한 연결을 제공하는 것이 특징입니다.

2-1. 블루투스의 주요 특징

  • 1.단거리 무선 통신 : 일반적으로 10m 이내, 고출력 장비는 최대 100m까지 지원합니다.

  • 2.페어링(Pairing) 기능 : 기기 간의 연결을 위해 처음에 인증을 거치는 과정입니다.

  • 3.저전력 소비 : 특히 블루투스 저에너지(BLE) 버전은 스마트워치, 센서 등에 활용됩니다.

  • 4.보안 기능 : 암호화와 인증 기술을 통해 사용자 정보를 안전하게 보호합니다.

2-2. 블루투스의 활용 예시

  • 무선 이어폰, 스피커

  • 스마트폰과 차량 연결

  • 스마트워치와 건강 추적기

  • 무선 키보드, 마우스

  • IoT(사물인터넷) 기기 제어

3. 실습

1. 클래식 블루투스 데이터 전송

  • 회로연결 : ESP32 단독 사용 (별도의 회로 연결 없음)
  • 코드
#include "BluetoothSerial.h"

BluetoothSerial SerialBT;

void setup() {
  Serial.begin(115200);
  SerialBT.begin("ESP32-BT-Slave"); // 블루투스 장치 이름 설정
  Serial.println("Bluetooth Started! Pair with ESP32-BT-Slave");
}

void loop() {
  if (Serial.available()) {
    char incoming = Serial.read();
    SerialBT.write(incoming); // 시리얼 데이터를 블루투스로 전송
  }
  if (SerialBT.available()) {
    char incoming = SerialBT.read();
    Serial.write(incoming); // 블루투스 데이터를 시리얼로 출력
  }
}
  1. 실습을 하기 위해서 Play Store 에서 "Serial Bluetooth Terminal" 프로그램을 설치
  2. 블루투스에서 "ESP32-BT"로 연결
  3. 그 후 디바이스를 페어링.
  4. 디바이스 챗에 문자를 적으면 다음과 같이 출력된다
KakaoTalk_20250405_232044216.mp4

2. 블루투스를 이용한 LED 제어

  1. 하드웨어 준비
  • ESP32 개발 보드
  • LED 1개
  • 330Ω 저항 1개
  • 브레드보드 및 점퍼 와이어
  1. 회로 연결
  • ESP32의 GPIO 22번 핀에 연결
  • 30Ω 저항을 통해 **GND(접지)**에 연결
  1. 코드
#include "BluetoothSerial.h"

BluetoothSerial SerialBT;

const int ledPin = 22; // LED가 연결된 핀 번호

void setup() {
  Serial.begin(115200);
  SerialBT.begin("ESP32-BT-LED"); // 블루투스 장치 이름 설정
  Serial.println("Bluetooth Started! Pair with ESP32-BT-LED");

  pinMode(ledPin, OUTPUT); // LED 핀을 출력으로 설정
  digitalWrite(ledPin, LOW); // 초기 상태를 OFF로 설정
}

void loop() {
  if (SerialBT.available()) {
    char incoming = SerialBT.read();
    Serial.write(incoming); // 수신된 데이터를 시리얼 모니터에 출력

    if (incoming == '1') {
      digitalWrite(ledPin, HIGH); // '1'을 수신하면 LED ON
      Serial.println("LED ON");
    } else if (incoming == '0') {
      digitalWrite(ledPin, LOW); // '0'을 수신하면 LED OFF
      Serial.println("LED OFF");
    }
  }
}
  • 위 코드를 입력 후 디바이스 챗에 0을 적으면 led off 1을 적으면 led on 상태가 된다.
default.mp4

3. BLE를 이용한 RGB LED 제어 1

BLE 방식으로 ESP32와 스마트폰 통신을 통해 RGB LED 색상을 변경하는 실습

  1. 회로 연결
  • RGB LED 모듈
    • R 핀 → D4
    • G핀 → D15
    • B핀 → D2
    • 전압 → 3.3V
    • 접지 → 접지
  1. 코드

코드를 실행하기에 앞서 https://www.uuidgenerator.net/ 이 링크에서 UUID 값을 받아서 하면 편합니다.

#define SERVICE_UUID "b42238ee-404f-4a11-bd3a-06d6eff0757d" 이 코드를 바꿔야합니다.

//라이브러리를 가져옵니다.
#include <BLEDevice.h>
#include <BLEServer.h>
#include <BLEUtils.h>
#include <BLE2902.h>
//서비스와 특성에 대한 UUID를 정의합니다.
#define SERVICE_UUID        "b42238ee-404f-4a11-bd3a-06d6eff0757d"
#define RGB_CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"
#define NOTYFY_CHARACTERISTIC_UUID "d501d731-f0f9-4121-a7f6-2c0f959f1583"
//RGB LED에 사용될 핀 번호를 정의합니다
#define RED_PIN   4
#define GREEN_PIN 15
#define BLUE_PIN  2
//BLE 관련 객체를 선언합니다.
BLEServer *pServer; //BLE 서버 객체
BLEService *pService; // BLE 서비스 객체
BLECharacteristic *pRGBCharacteristic = NULL; //BLE 특성 객체
BLECharacteristic* pCharacteristic = NULL; //BLE 특성 객체
//RGB 값을 저장할 변수들을 초기화합니
int redValue = 0;
int greenValue = 0;
int blueValue = 0;
//BLE 특성에 대한 콜백 클래스를 정의합니다.
class MyCallbacks : public BLECharacteristicCallbacks {
  //특성의 값을 읽어와 RGB 값을 파싱하고 LED를 제어합니다.
  void onWrite(BLECharacteristic *pCharacteristic) {
    String value = pCharacteristic->getValue().c_str(); //특성의 값을 문자열로 읽어옵니다.

    // 값이 유효한 경우에만 처리
    if (value.length() > 0) {
      // RGB 값을 파싱하여 각각의 변수에 저장
      int delimiterPos1 = value.indexOf(',');
      int delimiterPos2 = value.lastIndexOf(',');

      if (delimiterPos1 != -1 && delimiterPos2 != -1 \
             && delimiterPos2 < value.length() - 1) {
        redValue = value.substring(0, delimiterPos1).toInt();
        greenValue = value.substring(delimiterPos1 + 1, delimiterPos2).toInt();
        blueValue = value.substring(delimiterPos2 + 1).toInt();

        // RGB 값을 LED의 밝기로 변환하여 제어합니다.
        analogWrite(RED_PIN, 255 - redValue);
        analogWrite(GREEN_PIN, 255 - greenValue);
        analogWrite(BLUE_PIN, 255 - blueValue);
      }
    }
  }
};

void setup() {
  // BLE 초기화하고 이름을 "RGB LED Control"로 설정합니다
  BLEDevice::init("RGB LED Control");
  pServer = BLEDevice::createServer();
  pService = pServer->createService(SERVICE_UUID);
  
  // RGB 특성 생성 및 설정
  pRGBCharacteristic = pService->createCharacteristic(
    RGB_CHARACTERISTIC_UUID,
    BLECharacteristic::PROPERTY_WRITE
  );  
  pRGBCharacteristic->setCallbacks(new MyCallbacks());

  // Notify/Indicate 특성 생성 및 설정
  pCharacteristic = pService->createCharacteristic(
                      NOTYFY_CHARACTERISTIC_UUID,
                      BLECharacteristic::PROPERTY_NOTIFY |
                      BLECharacteristic::PROPERTY_INDICATE
                    );
    // Create a BLE Descriptor
  pCharacteristic->addDescriptor(new BLE2902());

  // 서비스를 서버에 추가
  pService->start();

  // BLE 광고 시작
  BLEAdvertising *pAdvertising = pServer->getAdvertising();
  pAdvertising->start();

    // 모든 핀을 HIGH로 설정하여 LED를 꺼진 상태로 초기화합니다.
  digitalWrite(RED_PIN, HIGH);
  digitalWrite(GREEN_PIN, HIGH);
  digitalWrite(BLUE_PIN, HIGH);
}

void loop() {
  // RGB 값을 16진수 형태로 변환하여 Notify
  char hexValue[8]; 
  sprintf(hexValue, "#%02X%02X%02X", redValue, greenValue, blueValue);
  //Notify 특성의 값을 hexValue로 설정합니다.
  pCharacteristic->setValue(hexValue); 
  pCharacteristic->notify(); //Notify를 통해 값을 전달합니다.

  delay(100);  // 알림 간격을 조절할 수 있습니다.
}
  1. 실습 영상
2.mp4

4. BLE를 이용한 RGB LED 제어 2

  1. 코드
#define RED_PIN 4   // 빨간색 핀
#define GREEN_PIN 15 // 초록색 핀
#define BLUE_PIN 2  // 파란색 핀

void setup() {
  pinMode(RED_PIN, OUTPUT);
  pinMode(GREEN_PIN, OUTPUT);
  pinMode(BLUE_PIN, OUTPUT);
  
  // 모든 핀을 HIGH로 설정하여 LED를 꺼진 상태로 초기화합니다.
  digitalWrite(RED_PIN, HIGH);
  digitalWrite(GREEN_PIN, HIGH);
  digitalWrite(BLUE_PIN, HIGH);
}

void loop() {
  // 빨강
  analogWrite(RED_PIN, 0);
  analogWrite(GREEN_PIN, 255);
  analogWrite(BLUE_PIN, 255);
  delay(1000);

  // 초록
  analogWrite(RED_PIN, 255);
  analogWrite(GREEN_PIN, 0);
  analogWrite(BLUE_PIN, 255);
  delay(1000);

  // 파랑
  analogWrite(RED_PIN, 255);
  analogWrite(GREEN_PIN, 255);
  analogWrite(BLUE_PIN, 0);
  delay(1000);

  // 백색
  analogWrite(RED_PIN, 0);
  analogWrite(GREEN_PIN, 0);
  analogWrite(BLUE_PIN, 0);
  delay(1000);

  // 끄기
  analogWrite(RED_PIN, 255);
  analogWrite(GREEN_PIN, 255);
  analogWrite(BLUE_PIN, 255);
  delay(1000);
}
  1. 실습 영상
1.mp4

4. 실습 후기

  • 이번 실습으로 통해서 UUID generator을 사용하면 더 편하게 찾을 수 있다는걸 알게되었다
  • Serial Monitor가 보이지 않은다면 Tool > Serial Monitor 을 선택하면 찾을 수 있다
⚠️ **GitHub.com Fallback** ⚠️