Download as pdf or txt
Download as pdf or txt
You are on page 1of 12

ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

..ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

enable notifications to receive updates when the battery level


changes.
microcontrollerslab.com

ESP32 BLE Server GATT Service


Battery Level Indication

16-20 minutes

In this tutorial, we will learn how to set up ESP32 as a BLE server


and use the GATT service to send battery levels to the Android
app. For demonstration, we will use the GATT service to send
battery percentage levels to our android smartphone from Bluetooth Low Energy (BLE)
ESP32. The ESP32 board will therefore act as a BLE server
Bluetooth Low Energy or simply BLE is designed as a low power
which is operated through a battery whose battery percentage is
consumption version of the generic classic Bluetooth connection.
being sent.
Instead of focusing on high data rates, BLE is optimized for
The Bluetooth Low Energy (BLE) Battery Service is a simple reduced energy consumption and is widely used in applications
GATT service that allows a device to expose the current battery such as fitness trackers, smartwatches, and battery-operated
level to other devices. The service consists of a single devices. That is why BLE has become one of the prominent
characteristic that contains the current battery level as a technologies in the internet of things.
percentage (0-100). The service also includes a notification
Although BLE is suitable for applications where we need to
property that allows the battery level to be updated automatically
transfer smaller amounts of data over a shorter distance. But its
when it changes.
power consumption is approximately 10 times lower than that of
To use the Battery Service, a device must first advertise the classic Bluetooth. This is because BLE activates radio only
service and its associated characteristic. Other devices can then whenever it is want to transmit or receive data to/from another
discover the service and read the battery level characteristic, or

1 of 24 1/14/2023, 11:01 PM2 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

device otherwise it is in standby mode. Low Power consumption

It is important to point out the major differences between BT Cost-Effective


classic and BLE in terms of electrical specifications. You can
Faster connection
view the table below to see some of the differences between the
two modes of Bluetooth connections. Compact size

Secure & reliable


Bluetooth Bluetooth Low
Classic Energy / BLE BLE Client and Server
Data Transfer Rate 2-3 Mbps 1 Mbps
In BLE, there are two types of devices known as the server
Range ~10-100m ~50m (Peripheral) and the client (Central). A client can have many

Operating 79 RF 40 RF simultaneous connections with multiple servers. But a server can

Frequency have only one connection at a time. Therefore, BLE


communication can be either one-to-one or one-to-many
Peak Current ~30mA <15mA communication.
Consumption
Apart from point-to-point communication, BLE also supports
Power 1W 0.01-0.5W mesh networks and broadcast modes. In broadcast mode,
Consumption multiple devices connect to a single server. It is a point to a
Total time to send 100ms 3ms multipoint data communication or one-to-many. Whereas in a
data mesh network, all the devices are connected so it acts as a
multipoint-to-multipoint or many-to-many communication.
Applications Audio straming or Sensor data, Control
files transfer commands, etc As shown in the figure below, one ESP32 acts as a client
(central), and the other ESP32 boards act as a server.
BLE operates at 2.4 GHz ISM (Industrial, Scientific, and Medical)
The BLE server announces its presence by sending radio
band and designed to target applications which need to run on
advertising packets and a ready-to-accept connection from a
batteries for longer periods of time—months, and even year.
client.
Key features

3 of 24 1/14/2023, 11:01 PM4 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

The BLE client discovers and listens to BLE devices that are A server advertises on the radio frequency by advertising
advertising. That means the BLE client initiates the process of connectable advertisement packets, its device name, and unique
establishing a connection to the BLE servers. UUID then on another in a process known as frequency hopping.
In doing so, it reduces radio interference created from reflected
signals or other devices.

Scanning

A client listens to incoming advertisements on the same radio


frequency and scans the nearby devices. An advertising event
from a server may consist of multiple events. When a client finds
a connectable event in an advertising packet, it sends a
connection request to a server with a CONNECT_IND packet.

Connecting

In the end, the BLE clients connect to a server by performing


several types of handshaking steps.
Note: ESP32 can act both as a server or client. Most importantly, Note: While connected to a client, the server may not connect to
the BLE client can hold connections with multiple servers at the any other device.
same time.
Communication
The client has two modes such as scanning and connected.
Similarly, the server also has two modes such as advertising and A client can request data from a server through something called
connected.about:blank a “Characteristic.” Characteristics are provided by the server for
Now let’s see how the BLE server and client establised a the client to read and write data. A Characteristic may have one
connection through advertising, scanning and conneting steps. or more properties, for example, READ or WRITE. Each
Characteristic belongs to a Service, which is like a container for
Advertising Characteristics. This paradigm is called the Bluetooth Generic

5 of 24 1/14/2023, 11:01 PM6 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

Attribute Profile (GATT) At the top of the hierarchy, you can find the Profile which
consists of one or more Services. These are the set of Services
BLE GATT Profile that are defined by the designers or by Bluetooth Special Interest
Group (SIG).
BLE clients and servers devices transmit and receive data
through Generic Attribute Profile (GATT). In this protocol, the GATT Services
central devices act as clients and any peripheral device is the
server. The server has Characteristics, Services, and a particular These are sets of simple data for example readings from a
ATT table that is used in the transmission and reception of data. sensor and are divided into subcategories known
The GATT protocol consists of a hierarchy in which there are as Characteristics. Pre-defined Services by Bluetooth SIG are
different sections known as Profiles, Services, and available such as reading heart rate, Weight Scale, Blood
Characteristics. The figure below shows these different sections pressure, etc. To view all the official services, click here.
in their particular order and positions. UUID or Universally Unique Identifier is the unique ID code of a
particular Service. It can be 16 or 128 bits depending on the
service. We can use the preset UUIDs or customize our own for
a particular service. To obtain a unique UUID go to the online
website UUIDGenerator.

An example of a UUID obtained from this generator is: c31cb7af-


34e2-42eb-8e7e-198230848b4a

Characteristics

Every service has its own Characteristics. These are broken


down into a single Characteristic or several Characteristics. They
also have unique UUIDs consisting of 16/128 bits. These contain
all the useful information in its ‘value’ section and declaration
GATT Protocol which supplies metadata.about:blank

Profile The descriptor is optional and is used in describing the

7 of 24 1/14/2023, 11:01 PM8 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

Characteristic value. They contain a different type of metadata #define BatteryService BLEUUID((uint16_t)0x180F)
through which they expand the Characteristic. The Properties
exercise the role of permitting operations including read, notify, BLECharacteristic
write, indicate, or broadcast. These are the functions of a BatteryLevelCharacteristic(BLEUUID((uint16_t)0x2A19),
particular value that is defined by property. This property is then BLECharacteristic::PROPERTY_READ |
linked with a particular Characteristic. BLECharacteristic::PROPERTY_NOTIFY);
BLEDescriptor
After getting to know about the necessary BLE terminologies, let
BatteryLevelDescriptor(BLEUUID((uint16_t)0x2901));
us move ahead and program our ESP32 module as a BLE
server. We will create a battery level indicator using the GATT
service. For this we will require the nRF android application on
class MyServerCallbacks : public BLEServerCallbacks {
our smartphone. Moreover, we will need a phone which supports
void onConnect(BLEServer* pServer) {
BLE connection.
_BLEClientConnected = true;
We will use Arduino IDE to program our ESP32 development
};
board. Thus, you should have the latest version of Arduino IDE.
Additionally, you also need to install the ESP32 plugin. If your
IDE does not have the plugin installed you can visit the link
void onDisconnect(BLEServer* pServer) {
below:
_BLEClientConnected = false;
Installing ESP32 library in Arduino IDE and upload code. }

Open your Arduino IDE and go to File > New. Copy the following };

code and save it.


void InitBLE() {
#include <BLEDevice.h>
BLEDevice::init("BLE Battery");
#include <BLEUtils.h>
// Create the BLE Server
#include <BLEServer.h>
BLEServer *pServer = BLEDevice::createServer();
#include <BLE2902.h>

pServer->setCallbacks(new MyServerCallbacks());
bool _BLEClientConnected = false;

9 of 24 1/14/2023, 11:01 PM10 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

uint8_t battery_level = 0;
// Create the BLE Service
BLEService *pBattery = void loop() {
pServer->createService(BatteryService); BatteryLevelCharacteristic.setValue(&battery_level,
1);
pBattery->addCharacteristic(&BatteryLevelCharacteristic BatteryLevelCharacteristic.notify();
BatteryLevelDescriptor.setValue("Percentage 0 - delay(5000);
100"); battery_level++;
Serial.println(int(battery_level));
BatteryLevelCharacteristic.addDescriptor(&BatteryLevelDescriptor if (int(battery_level) == 100)
BatteryLevelCharacteristic.addDescriptor(new battery_level = 0;
BLE2902()); }

Working of the Code


pServer->getAdvertising()->addServiceUUID(BatteryService
pBattery->start();
The code starts off by including all the libraries which are
necessary for the BLE server
// Start advertising
communication, connection and advertisement.
pServer->getAdvertising()->start();
#include <BLEDevice.h>
}
#include <BLEUtils.h>
#include <BLEServer.h>
#include <BLE2902.h>
void setup() {
Serial.begin(115200); Next, we define the server callback function. This function will
Serial.println("BLE Battery Level Indicator"); make sure that a successful connection is established between
InitBLE(); the server and client. The bool variable ‘_BLEClientConnected’
} is initially set as false. Inside the onConnect() function, it is set as
true and inside the onDisconnect() function it is set as false.

11 of 24 1/14/2023, 11:01 PM12 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

bool _BLEClientConnected = false; BLECharacteristic::PROPERTY_READ |


BLECharacteristic::PROPERTY_NOTIFY);
class MyServerCallbacks : public BLEServerCallbacks { BLEDescriptor
void onConnect(BLEServer* pServer) { BatteryLevelDescriptor(BLEUUID((uint16_t)0x2901));
_BLEClientConnected = true;
}; InitBLE()

The InitBLE() function is called inside the setup() function which


initializes the Bluetooth device.
void onDisconnect(BLEServer* pServer) {
_BLEClientConnected = false; void InitBLE() {
} BLEDevice::init("BLE Battery");
}; // Create the BLE Server
BLEServer *pServer = BLEDevice::createServer();
Next, we define the UUID, characteristic, and descriptor for the
Battery Level Service. As we are using Battery Service hence its
pServer->setCallbacks(new MyServerCallbacks());
UUID is 0x108F. You can get the UUIDs from this link.

#define BatteryService BLEUUID((uint16_t)0x180F)


// Create the BLE Service
Next, we set the characteristic for the Battery Service which is BLEService *pBattery =
Battery Level. This characteristic is read using the GATT Read pServer->createService(BatteryService);
characteristic value sub-procedure and outputs the current
battery level as a percentage from 0% to 100%. Its UUID is pBattery->addCharacteristic(&BatteryLevelCharacteristic
0x2A19. This characteristic has two properties, Read which is BatteryLevelDescriptor.setValue("Percentage 0 -
mandatory, and Notify which is optional. Moreover, the 100");
descriptor’s value is given as 0X2901 as the size of the value is
8-bit. BatteryLevelCharacteristic.addDescriptor(&BatteryLevelDescriptor
BatteryLevelCharacteristic.addDescriptor(new
BLECharacteristic
BLE2902());
BatteryLevelCharacteristic(BLEUUID((uint16_t)0x2A19),

13 of 24 1/14/2023, 11:01 PM14 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

pBattery->addCharacteristic(&BatteryLevelCharacteristic
pServer->getAdvertising()->addServiceUUID(BatteryService BatteryLevelDescriptor.setValue("Percentage 0 -
pBattery->start(); 100");

// Start advertising BatteryLevelCharacteristic.addDescriptor(&BatteryLevelDescriptor


pServer->getAdvertising()->start(); BatteryLevelCharacteristic.addDescriptor(new
} BLE2902());

First, define your BLE device by specifying the name of your After the service has started, we will use getAdvertising() to
choice in the init command. In our case, we our device name is initiate the advertising process so that nearby devices would be
‘BLE Battery.’ able to spot our server and connect with it. After a connection
had been made, the Battery Service is started. We will then
BLEDevice::init("BLE Battery");
launch the server, using the start() command.
Next, we create the BLE server by using
pServer->getAdvertising()->addServiceUUID(BatteryService
the createServer() function and set the server callback.
pBattery->start();
BLEServer *pServer = BLEDevice::createServer();
pServer->setCallbacks(new MyServerCallbacks()); setup()
Then, the BLE GATT service is created. After that, we will add
Inside the setup() function, we open the serial communication at
the Characteristic on our server. By using the setValue() method,
we will set the ‘Value’ of the characteristic with the a baud rate of 115200 and print “BLE Battery Level Indicator” on
the serial monitor. Then InitBLE() function is called which
text: “Percentage 0-100.” You can change this value according to
initializes our BLE device.
your liking. After we start the BLE GATT service, the descriptor
along with the characteristics is joined and the values are set. void setup() {
Additionally, BLE2902 service is also included. Serial.begin(115200);
Serial.println("BLE Battery Level Indicator");
BLEService *pBattery =
InitBLE();
pServer->createService(BatteryService);
}

15 of 24 1/14/2023, 11:01 PM16 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

loop()

Inside the loop() function, we set the value of the characteristic


with the hard coded battery level which is 0. This will be sent to
the client. Note that this characteristic can take values from 0% to
100%. Hence we increment the battery level after every 5
seconds and when the level reaches 100, the value is set back to
0.

uint8_t battery_level = 0;

void loop() {
BatteryLevelCharacteristic.setValue(&battery_level,
1);
BatteryLevelCharacteristic.notify();
delay(5000);
battery_level++;
Serial.println(int(battery_level));
if (int(battery_level) == 100)
battery_level = 0;
}
Then, go to Tools > Port and select the appropriate port through
Demonstration which your board is connected.

Choose the correct board and COM port before uploading your
code to the board. Therefore go to Tools > Board and
select ESP32 Dev Module.

Select the ESP32 Dev module as follows:

17 of 24 1/14/2023, 11:01 PM18 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

In your Arduino IDE, open up the serial monitor and set the baud
rate to 115200. You will be able to view the battery value. It will
increment after every 5 seconds.

Click on the upload button to upload the code to ESP32


development board. Testing BLE Server GATT Service Battery Level
After you have uploaded your code to the ESP32, press its Indication
ENABLE button.about:blank
To perform the testing functionality of the ESP32 BLE server on a
cell phone we will need a phone which supports a BLE
connection. After you have got your hands on one, open the Play
Store and search for ‘nRF Connect for Mobile.’ This is a free app
that will help us to check for the connection. Install the app on
your cell phone.

19 of 24 1/14/2023, 11:01 PM20 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

Before proceeding further, enable the Bluetooth on your Now, open the nRF Connect for Mobile application and tap the
smartphone and pair it with “BLE Battery” which is the name of Scan button. This will scan for all the devices which are close to
our BLE device. the cell phone. Thus, our BLE device will also get scanned and
you will be able to see ‘BLE Battery’ written among the scanned
devices as shown below. Connect with it.

21 of 24 1/14/2023, 11:01 PM22 of 24 1/14/2023, 11:01 PM


ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...ESP32 BLE Server GATT Service Battery Level Indication about:reader?url=https%3A%2F%2Fmicrocontrollerslab.com%2Fesp...

Now, tap the Connect button and the following appears on the
cell phone screen.

The Service (Battery Service) and the Characteristic (Battery


Level) which we had defined in the program code can be viewed
here. It displays “Percentage 0-100” which we set as our
characteristic value and both the service and the characteristic
You may also like to read:
UUIDs are also visible with the properties: Read and notify. The
Send Sensor Readings to Android Phone using Arduino and
current battery value is 61% which gets incremented after every
NRF24L01 via BLE
5 seconds.
ESP32 Bluetooth Low Energy (BLE) using Arduino IDE

ESP32 BLE Server Client Communication using Arduino IDE

23 of 24 1/14/2023, 11:01 PM24 of 24 1/14/2023, 11:01 PM

You might also like