ESP32-S3-DevkitC-1

コンピュータ、組み込み

ESP32 S3搭載 ESP32-S3-DevkitC-1基板を入手しました。
少し大柄な基板ですが使用できるピンが多いです。
基本的な入出力と、通信(UART, I2C, SPI)、BLE UARTを使ってみます。

紹介するもの

ESP32-S3-DevkitC-1

特徴

大判基板ですが、使用できるピンが多い。
COMドライバ搭載しているのでUSBでUART通信ができる。
技適付き無線での通信ができる。

接続Micro B
UART側 : CP210x
USB側 : ESP32-S3
CPUESP32-S3 Xtensa 32bit LX7 Dual core 240MHz
GPIO36
ADC20 (12bit 0 – 4095)
PWM36 (8bit 0 – 255)
同時に設定できるのは8本まで
UART1 COMシリアルとGPIO43(TX), GPIO44(RX)と共通
I2C1(デフォルトは無いが、任意のピンに設定可能)
SPI2(デフォルト有るが、任意のピンに設定可能)
ボタンBOOT
Reset
そのほかW2812 (GPIO 48) GPIO出力ピンと共通
入手Dec/2022現在 Ali Express 送料込みで\1,500~\1,700
秋月 送料込み \2,400前後
ピン配置

外観

購入は秋月です。
本体モジュールに技適はありませんが、パッケージにシールがあります。
本体にない場合付属品に技適マークが含まれていることがあるので、大切に保管してください。

400穴ブレッドボードでは、左右2列使用することができます。

使ってみて

全体的にパフォーマンスも高く自由度の高い基板です。
ESP32-S3にはS3の使い方があるようなので、慣れることで自由度の高く高性能な基板として活用できると思います。

基板は少し大きめなので400穴ブレッドボードでは手狭です。
830穴ブレッドボードを使用するか、400穴ブレッドボードをもう一つ準備すると作業がはかどると思います。

USBコネクタの使い分けも慣れが必要ですが、UART側で使用することで従来の基板と同等の使用ができるので、迷ったらUART側に接続するとよいと思います。

準備

ライブラリ

ボードライブラリ

Arduino IDEのボードマネージャからESP32用のライブラリのインストールとボードの選択をします。

ボードマネージャのURLhttps://raw.githubusercontent.com/espressif/arduino-esp32/gh-pages/package_esp32_index.json
検索ESP
ボードライブラリesp32 by Espressif Systems バージョン x.x.x※
選択するボードツール > ボード > esp32 > ESP32S3 Dev Module
※ x.x.x 動作確認は2.0.3を使用しています

モジュールライブラリ

機能やモジュールを使用しない場合インストールの必要はありません。

機能/モジュールライブラリ名検索確認時のバージョン
SSD1306Adafruit SSD1306 by AdafruitSSD13062.5.1
ST7735Adafruit ST7735 and ST7789
Library by Adafruit
ST77351.9.3
関連
SSD1306
ST7735
Adafruit GFX Library by AdafruitGFX1.11.3
WS2812Adafruit NeoPixel by AdafruitNEOPIXEL1.10.5

スケッチの書き込み

スケッチの書き込みは、書き込みモードで起動します。
BOOTボタンを押下しながらResetボタンの押下または電源を投入します。
Arduino IDEから書き込みボタンを押下することで書き込みができます。

トラブル

W2812が勝手に光る

現象

通電状態で、GPIO48ピンに触れるとW2812が発光することがある。
色や明るさはまちまち。

通電状態でブレッドボードに挿抜したり、RSTボタン押下時などにGPIO48ピンに触れることで発光する。

原因

触れたことによりノイズなどがW2812の命令(信号)に相当して発光しているものと推測。

対応

一度電源を切って、再度電源を投入すると消える。
GPIO48ピンに触れるとまた発光するので、オープン状態のGPIO48とGNDを導通させる。

基本スケッチ

ボタンLED

説明

基板上のボタン押下するとLEDを点灯させます。
ボタンを離すとLEDを消灯させます。

配線

基板実装LEDを使用するので、LEDは配線不要です。
ワイヤで回路を作成する場合の保護抵抗は、適値求めて使用してください。

GPIO(LED出力用) -> 保護抵抗(約200Ω) -> LED -> GND
3.3V -> タクトスイッチ -> ボタンピン(GPIO2)

保護抵抗は目安です。使用されるLEDの適値を求めてください。
ボタンは基板実装ボタン GPIO2を使用します。

スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevkitC-1 で利用できます。

【スケッチの説明】
プルダウンしたピンの状態がHighならLEDを点灯、LowならLEDを消灯させます。

【ライブラリ】
esp32 > ESP32S3 Dev Module

【準備】
LEDピン(GPIO1) -> 保護抵抗(約200Ω) -> LED Anode, LED Cathode -> GND
3.3V -> タクトスイッチ -> ボタンピン(GPIO2)

【バージョン情報】
2022/12/4 : 新規
**********************************************************************/
//ESP32-S3-DevkitC-1
// 4, 5, 6, 7, 15, 16, 17, 18, 8, 3, 46, 9, 10, 11, 12, 13, 14, 43, 44, 1, 2, 42, 41, 40, 39, 38, 37, 36, 35, 0, 45, 48, 47, 21, 20, 19 //all pins
// 4, 5, 6, 7, 15, 16, 17, 18, 8, 3, 46, 9, 10, 11, 12, 13, 14, 43, 44, 1, 2, 42, 41, 40, 39, 38, 37, 36, 35, 0, 45, 48, 47, 21, 20, 19 //all pins

#define LED 1      //LED
#define BUTTON 2    //タクトスイッチ

void setup()
{
  pinMode(LED, OUTPUT);               //ピン出力設定
  pinMode(BUTTON, INPUT_PULLDOWN);    //プルダウンで入力
}

void loop()
{
  int iStat = digitalRead(BUTTON);
  digitalWrite(LED, iStat);           //ボタンの状態をLEDに出力
}
結果

ボタンを押下するとLEDが点灯し、離すことでLEDが消灯しました。

PWM

説明

PWMを使ってLEDをゆっくり点灯、ゆっくり消灯します。

ESP32-S3-DevkitC-1の同時に使用できるPWMの数は8です。
9個以上設定してもコンパイルエラーにはなりませんが、9番目以降に設定されたピンからは信号はでないようです。

配線

PWMピン – 保護抵抗(約200Ω) – LED Anode, LED Cathode – GND
ワイヤとLEDで動作させる場合の抵抗値は使用するLEDにより適切な抵抗値を求めてください。

スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevkitC-1で利用できます。

【スケッチの説明】
PWM出力でのフェード点灯(ゆっくり点灯)とフェード消灯(ゆっくり消灯)を行います。

【ライブラリ】
esp32 > ESP32S3 Dev Module

【準備】
GPIO1 - 保護抵抗(約200Ω) - LED Anode, LED Cathode - GND
ワイヤとLEDで動作させる場合の抵抗値は使用するLEDにより適切な抵抗値を求めてください。

【バージョン情報】
2022/12/4 : 新規
**********************************************************************/
//ESP32-S3-DevkitC-1 (8bit 0 to 255, 同時に8個まで)
//4, 5, 6, 7, 15, 16, 17, 18, 8, 3, 46, 9, 10, 11, 12, 13, 14, 43, 44, 1, 2, 42, 41, 40, 39, 38, 37, 36, 35, 0, 45, 48, 47, 21, 20, 19 //PWM


#define PWM 1        //PWM 出力は 46th pin

void setup()
{
  pinMode(PWM , OUTPUT);
}

void loop()
{
  for(int i = 0; i < 256; i ++)
  {
    analogWrite(PWM, i);
    delay(2);
  }

  for(int i = 0; i < 256; i ++)
  {
    analogWrite(PWM, 255 - i);
    delay(2);
  }
}
結果

LEDがゆっくり点灯し、ゆっくり消灯しました。

ADC

説明

ADCに入力された電圧を読み取りCOMに出力します。

電圧の入力にLOLIN32 Liteを使用します。
0~255(約3.3V) まで2msごとに1ずつ上昇し、255(約3.3V)~0までを2msごとに1ずつ下降する設定を繰り返します。

配線
ESP32-S3-DevkitC-1配線LOLIN32 Lite
GPIO4(ADC)GPIO26(DAC)
GNDGND
スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
 ESP32-S3-DevkitC-1で利用できます。

【スケッチの説明】
入力された電圧を読み取ります。

【ライブラリ】
 esp32 > ESP32S3 Dev Module

【準備】
ESP32-S3-DevkitC-1 <-> LOLIN32 Lite
GPIO4(ADC)         <-> GPIO26(DAC)
GND                <-> GND

【バージョン情報】
2022/12/4 : 新規
**********************************************************************/
//ESP32-S3-DevkitC-1 で設定できる analogRead (12bit 0 ~ 4095)
//4, 5, 6, 7, 15, 16, 17, 18, 8, 3, 9, 10, 11, 12, 13, 14,  1, 2, 20, 19 //analogRead

#define ADC 4

void setup()
{
  Serial.begin(115200);

  pinMode(ADC, INPUT);
}

void loop()
{
  int iADC = 0;

  //外部から入力された電圧を読み取り、結果をCOMに出力します。
  iADC = analogRead(ADC);
  Serial.printf("(ADC) = %d\r\n", iADC);
  delay(2);
}
結果

入力した電圧を読み取った結果をグラフにしました。
電圧の変化は0V -> 3.3Vまでを約500msで上昇し、3.3V -> 0Vまで約500msで下降します。

ADC読み取り値が高くなる(4000付近)で感度が若干高くなっていますが、ほかのESP系の中ではきれいな波形と思います。

電圧と読み取り値の同期はできていませんが、参考程度に入力電圧を添付します。

UART

説明

UART0(COM)から読み取ったデータをUART1に送信します。
UART1から読み取ったデータをUART0(COM)に送信します。

配線

ESP32-S3-DevkitC-1には、USB側のコネクタと、UART側のコネクタがあります。

UART側のコネクタでは、USBケーブルを使いUART通信を行うことができます。
USB側では、USBケーブルを使ってUART通信を行うことができません。
GPIO43(TX), GPIO44(RX)からのUART信号をUSB-シリアル変換モジュールを使い通信を行います。

今回USB側の通信がうまくできなかったので準備できていません。
UART側の通信について記載します。

UART0の信号はUSBケーブルにより通信を行う。
UART1はソフトウエアUARTによりGPIO4(TX), GPIO(5)で入出力するのでもう1個のFT232RLと通信する。

ESP32-S3-DevkitC-1配線FT232RL
GPIO4(UART1 TX)RX
GPIO5(UART1 RX)TX
スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevkitC-1 で利用できます。

【スケッチの説明】
 UART0から読み取った情報を UART1へ出力します。
 UART1から読み取った情報を UART0へ出力します。
 
 ESP32-S3-DevkitC-1 にはUART1の記載がありますが、
 デフォルトで使用できなかったので、今回ソフトウエアuartで通信します。

【ライブラリ】
esp32 > ESP32S3 Dev Module

【準備】
ESP32-S3-DevkitC-1では、USBコネクタに USBとUARTの2つのポートが用意されています。
UART側では、USBをUART0で使用することができます。
USB側では、USBコネクタからUART0の通信ができないので、GPIO43(TX), GPIO44(RX)での通信を行います。

今回ピンによるUART通信ができなかったため、UART側の記載をします。

 ESP32-S3-DevkitC-1 <-> FT232RL(UART1側)
 GPIO4(TX) <-> RX
 GPIO5(RX) <-> TX

【バージョン情報】
2022/12/5 : 新規
**********************************************************************/

#define PIN_TX 4
#define PIN_RX 5

void setup()
{
  Serial.begin(115200);                                   //GPIO 43(TX), 44(RX)に入出力されます
  Serial1.begin(115200, SERIAL_8N1, PIN_RX, PIN_TX);      //Serial1 オブジェクトは ピン指定で使用します
}

void loop()
{
  if(Serial1.available() != 0)          //UART1にデータがあれば、読み取った内容をUART0に送信
  {
      Serial.write(Serial1.read());
  }

  if(Serial.available() != 0)           //UART0にデータがあれば、読み取った内容をUART1に送信
  {
      Serial1.write(Serial.read());
  }
}
結果

結果はTeratermを2つ起動して確認します。
1つはUART0用で、もう一つはソフトウエアUARTのUART1用。

TeratermのCOM選択ではBananaPi PicoWの番号も表示されますがシリアル通信はできません。
Teratermは2つともFT232RLのCOMポート番号を選択します。

結果は掲載しませんが、片側のTeratermから入力した文字が反対のTeratermの画面に表示されます。

I2C(SSD1306)

説明

I2Cを使ってSSD1306(OLED 0.96inch)モニタのサンプルを動作させます。

そのほかの図形描画サンプルは、Arduinoサンプルを参照してください。
ファイル(F) > スケッチ例 > Adafruit SSD1306 > ssd1306_128x64_i2c

配線
ESP32-S3-DevkitC-1配線SSD1306(0.96inch)
3.3VVCC
GNDGND
GPIO2(SCL)SCL
GPIO1(SDA)SDA
[2022/12/17 スケッチとの配線間違い修正]
スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevKitC-1で利用できます。

【スケッチの説明】
SSD1306 OLEDの制御をします。

【ライブラリ】
esp32 > ESP32 Dev Module
Adafruit SSD1306 by Adafruit
Adafruit GFX Library by Adafruit

【準備】
マイコン基板 <-> SSD1306
3V3         <-> VCC
GND         <-> GND
GPIO1(SDA)  <-> SDA
GPIO2(SCL)  <-> SCL
ESP32-S3-DevKitC-1 の I2Cでは、 Wire.setPins()により任意の位置にI2CのSDA, SCLを設定することができます。

【バージョン情報】
2022/11/30 : 新規
**********************************************************************/

#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SCREEN_WIDTH 128                //解像度 128 x 64 で使用します。
#define SCREEN_HEIGHT 64                //SCREEN_HEIGHTは 32 に設定することができます。

#define OLED_RESET     -1               //使用しないので -1を設定する。
#define SCREEN_ADDRESS 0x3C             //I2Cアドレスは 0x3C
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
                                        //表示制御にはAdafruit製 SSD1306を使用する。

#define PIN_SDA 1
#define PIN_SCL 2                                   
void setup()
{
  Wire.setPins(PIN_SDA, PIN_SCL);

  if(!display.begin(SSD1306_SWITCHCAPVCC, SCREEN_ADDRESS)) {
    for(;;);
  }

  display.clearDisplay();               //何か表示されている場合に備えて表示クリア

  display.setTextSize(2);               //フォントサイズは2(番目に小さい)
  display.setTextColor(SSD1306_WHITE);  //色指定はできないが必要
  display.setCursor(20, 5);            //テキストの表示開始位置
  display.print(F("TAMANEGI"));         //表示文字列
  display.setCursor(20, 25);
  display.print(F("ESP32-S3"));
  display.setCursor(15, 45);
  display.print(F("DevKitC-1"));

  display.display();                    //バッファ転送(表示)
}

void loop()
{
}
結果

SSD1306のサンプルスケッチが動作しました。
(配線で説明しているワイヤと色が違いますが、使用しているピンは同じです)

SPI(ST7735)

説明

SPIを使ってST7735(LCD 1.8inch)モニタのサンプルを動作させます。

そのほかの図形描画サンプルは、Arduinoサンプルを参照してください。
ファイル(F) > スケッチ例 > Adafruit ST7735 and ST7789 Library > graphicstest

配線
ESP32-S3-DevkitC-1配線ST7735(1.8inch)
3.3VVCC
3.3VLED
GNDGND
GPIO10(SPI CS)CS
GPIO8RESET
GPIO3AO(DC)
GPIO11(SPI MOSI)SDA
GPIO12(SPI SCK)SCK
スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevkitC-1 で利用できます。

【スケッチの説明】
ST7735 LCDの表示制御します。
ESP32-S3-DevkitC-1 ではSPIを2系統使用できます。
ESP32-S3-DevkitC-1 のSPIはデフォルトで設定されているため、CS, RST, DCは任意のピンを指定しますが、
MOSI, SCK, MISOについても のbegin()関数で任意のピンを設定できます。

2系統のSPIを使用する方法と、S/W SPIを使用する方法を記載します。

【ライブラリ】
esp32 > ESP32S3 Dev Module

【準備】
VSPIを使用する場合
マイコン基板 <-> ST7735
3V3            <-> VCC
GND            <-> GND
GPIO10(CS)     <-> CS
GPIO8(Reset)   <-> Reset
GPIO3(DC)      <-> AO
GPIO11(MOSI)   <-> SDA
GPIO12(SCK)    <-> SCK

【バージョン情報】
2022/12/2 : 新規
**********************************************************************/

#include <Adafruit_GFX.h> 
#include <Adafruit_ST7735.h>
#include <SPI.h>

#define TFT_CS    10
#define TFT_RST   8
#define TFT_DC    3
#define TFT_MOSI  11
#define TFT_SCK   12

//1系統目を使う場合
Adafruit_ST7735 tft = Adafruit_ST7735(TFT_CS, TFT_DC, TFT_RST);

// 2系統目を使用する場合はコメント解除
// SPIClass hspi(HSPI);
// Adafruit_ST7735 tft = Adafruit_ST7735(&hspi, TFT_CS, TFT_DC, TFT_RST);

//S/W SPIはこちら。遅いが任意のピンを使用できる。
//Adafruit_ST7735 tft = Adafruit_ST7735(TFT_CS, TFT_DC, TFT_MOSI, TFT_SCK, TFT_RST);

void setup(void) 
{
  //1系統目を使う場合
//SPI.begin(TFT_SCK, -1, TFT_MOSI, TFT_CS);       //FSPIピンを変更して使用する場合、この行のコメントを解除

//  2系統目を使用する場合はコメント解除
//  hspi.begin(TFT_SCK, -1, TFT_MOSI, TFT_CS);       //FSPIピンを変更して使用する場合、この行のコメントを解除

  tft.initR(INITR_BLACKTAB);                  //Init ST7735S初期化
  
  tft.fillScreen(ST77XX_BLACK);               //背景の塗りつぶし

  //テキスト表示
  tft.setRotation(3);                         //画面回転
  tft.setTextSize(3);                         //サイズ

  tft.setCursor(0, 20);                      //カーソル位置                      
  tft.setTextColor(ST77XX_RED);              //赤
  tft.printf("TAMANEGI\n");

  tft.setTextColor(ST77XX_GREEN);            //緑
  tft.printf("TAMANEGI\n");

  tft.setTextColor(ST77XX_BLUE);             //青
  tft.printf("TAMANEGI\n");

  tft.setTextColor(ST77XX_YELLOW);           //黄
  tft.printf("TAMANEGI\n");
}

void loop()
{
}
結果

ST7735のサンプルスケッチが動作しました。

特別な機能のスケッチ

Neopixel(W2812)

説明

1秒ごとに、LEDの色を変化させます。
赤->緑->黄->青->紫->水->白

配線

基板実装W2812を使用するので配線不要。

スケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevkitC-1 で利用できます。

【スケッチの説明】
基板実装WS2812を点灯させます。
1秒間隔で、赤->緑->黄->青->紫->水->白 の順で点灯させます。

【ライブラリ】
esp32 > ESP32S3 Dev Module
Adafruit NeoPixel by Adafruit 1.10.6

【準備】
配線不要

【バージョン情報】
2022/12/5 : 新規
**********************************************************************/

#include <Adafruit_NeoPixel.h>

#define DIN_PIN 48            // NeoPixel の出力ピン番号
#define LED_COUNT 1           // LEDの連結数
#define WAIT_MS 1000          // 次の点灯までのウエイト
#define BRIGHTNESS 128        // 輝度
Adafruit_NeoPixel pixels(LED_COUNT, DIN_PIN, NEO_GRB + NEO_KHZ800);

void setup()
{
  pixels.begin();             //NeoPixel制御開始
}

void loop()
{
  pixels.clear();
  
  //pixels.Color(Red, Green, Blue)で、パレット情報を作成する。
  //赤点灯
  pixels.setPixelColor(0, pixels.Color(BRIGHTNESS, 0, 0));
  pixels.show();
  delay(WAIT_MS);

  //緑点灯
  pixels.setPixelColor(0, pixels.Color(0, BRIGHTNESS, 0));
  pixels.show();
  delay(WAIT_MS);

  //赤 + 緑 で 黄点灯
  pixels.setPixelColor(0, pixels.Color(BRIGHTNESS, BRIGHTNESS, 0));
  pixels.show();
  delay(WAIT_MS);

  //青点灯
  pixels.setPixelColor(0, pixels.Color(0, 0, BRIGHTNESS));
  pixels.show();
  delay(WAIT_MS);

  //赤 + 青 で 紫点灯
  pixels.setPixelColor(0, pixels.Color(BRIGHTNESS, 0, BRIGHTNESS));
  pixels.show();
  delay(WAIT_MS);

  //緑 + 青 で 水点灯
  pixels.setPixelColor(0, pixels.Color(0, BRIGHTNESS, BRIGHTNESS));
  pixels.show();
  delay(WAIT_MS);

  //赤 + 緑 + 青 で 白点灯
  pixels.setPixelColor(0, pixels.Color(BRIGHTNESS, BRIGHTNESS, BRIGHTNESS));
  pixels.show();
  delay(WAIT_MS);
}
結果

Nexpixelが1秒毎に色の変化をしました。

BLE-UART

スケッチの説明

スマートフォンからBTシリアル通信を行います。

ESP32-S3-DevkitC-1のCOMから読み取ったデータを、BLEを使いスマートフォンに送信します。
スマートフォンから読み取ったBLEデータは、COMへ出力します。

サンプルスケッチ
/**********************************************************************
【ライセンスについて】
Copyright(c) 2022 by tamanegi
Released under the MIT license
'http://tamanegi.digick.jp/about-licence/

【マイコン基板】
ESP32-S3-DevkitC-1

【スケッチの説明】
BLE UART通信します。

ESP32-S3-DevkitC-1にはUSBケーブルからUSB-シリアル(COM)接続を行います。
(UARTシルク側のUSBコネクタに接続します)

COMから読み取ったデータをBLEクライアントに送信します。
BLEクライアントから読み取ったデータはCOMに送信します。

参考
ファイル > スケッチ例 > ESP32 BLE Arduino > BLE_uart
を送信、受信できるように修正しています。

【ライブラリ】
esp32 > ESPS3 Dev Module

【準備】
配線不要
BLEクライアントアプリが必要です。

【バージョン情報】
2023/1/10 : 新規
**********************************************************************/

#include <BLEDevice.h>
#include <BLEServer.h>
#include <BLEUtils.h>
#include <BLE2902.h>

#define BUFFER 64

BLEServer *pServer = NULL;
BLECharacteristic * pTxCharacteristic;
bool deviceConnected = false;
bool oldDeviceConnected = false;
uint8_t txValue[BUFFER] = "";

// See the following for generating UUIDs:
// https://www.uuidgenerator.net/

#define SERVICE_UUID           "6E400001-B5A3-F393-E0A9-E50E24DCCA9E" // UART service UUID
#define CHARACTERISTIC_UUID_RX "6E400002-B5A3-F393-E0A9-E50E24DCCA9E"
#define CHARACTERISTIC_UUID_TX "6E400003-B5A3-F393-E0A9-E50E24DCCA9E"


class MyServerCallbacks: public BLEServerCallbacks {
    void onConnect(BLEServer* pServer) {
      deviceConnected = true;
    };

    void onDisconnect(BLEServer* pServer) {
      deviceConnected = false;
    }
};

class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string rxValue = pCharacteristic->getValue();

      if (rxValue.length() > 0) {
        Serial.println("*********");
        Serial.print("Received Value: ");
        for (int i = 0; i < rxValue.length(); i++)
          Serial.print(rxValue[i]);

        Serial.println();
        Serial.println("*********");
      }
    }
};


void setup() {
  Serial.begin(115200);

  // Create the BLE Device
  BLEDevice::init("BLE UART");

  // Create the BLE Server
  pServer = BLEDevice::createServer();
  pServer->setCallbacks(new MyServerCallbacks());

  // Create the BLE Service
  BLEService *pService = pServer->createService(SERVICE_UUID);

  // Create a BLE Characteristic
  pTxCharacteristic = pService->createCharacteristic(
										CHARACTERISTIC_UUID_TX,
										BLECharacteristic::PROPERTY_NOTIFY
									);
                      
  pTxCharacteristic->addDescriptor(new BLE2902());

  BLECharacteristic * pRxCharacteristic = pService->createCharacteristic(
											 CHARACTERISTIC_UUID_RX,
											BLECharacteristic::PROPERTY_WRITE
										);

  pRxCharacteristic->setCallbacks(new MyCallbacks());

  // Start the service
  pService->start();

  // Start advertising
  pServer->getAdvertising()->start();
  Serial.println("Waiting a client connection to notify...");
}

void loop() {

  //以下修正箇所 COMからデータを読み取り、BLEに送信
  if (deviceConnected == true)
  {
    if(Serial.available() != 0)
    {
      size_t bufSize = Serial.read(txValue, Serial.available());
      pTxCharacteristic->setValue(txValue, bufSize);
      pTxCharacteristic->notify();
    }

		delay(10); // bluetooth stack will go into congestion, if too many packets are sent
	}
  //ここまで

    // disconnecting
    if (!deviceConnected && oldDeviceConnected) {
        delay(500); // give the bluetooth stack the chance to get things ready
        pServer->startAdvertising(); // restart advertising
        Serial.println("start advertising");
        oldDeviceConnected = deviceConnected;
    }
    // connecting
    if (deviceConnected && !oldDeviceConnected) {
		// do stuff here on connecting
        oldDeviceConnected = deviceConnected;
    }
}
結果

スマートフォンからBLE接続を行いました。
スマートフォンアプリケーションにはSerial Bluetoothを使用します。

アプリケーションを起動し、画面左上のメニューから「Devices」を選択します。
「Bluetooth LE」を選択し、SCANを押します。
スケッチが正常に動作していれば「BLE UART」が表示されるので選択することで接続できます。

パソコン側からはArduinoIDEのシリアルモニタを使用します。
シリアルモニタから入力した文字がアプリケーション上に表示(水色の楕円)されます。
「Serial Bluetooth」アプリケーションから入力した文字が、シリアルモニタに表示(赤色の楕円)されます。

コメント

タイトルとURLをコピーしました