Using Bluetooth Low Energy
Go Up to Using Bluetooth
Because the Bluetooth Core Specification defines since version 4.0 different types of "Bluetooth" protocols, such as Bluetooth Low Energy, the original Bluetooth protocol is now known as " Classic Bluetooth".
Bluetooth Low Energy or Smart Bluetooth provides a new environment for devices with small amount of data to transfer and lower power consumption.
To implement BluetoothLE support for standard services in your applications:
- Place a TBluetoothLE component in your project
- Discover Bluetooth LE devices
- Discover and get the services for the device
- Discover and get the characteristics for the service
- Read, write or subscribe to a characteristic
- Subtract the information from the raw data
Contents
Platform Support
Platform | Bluetooth Low Energy | |
---|---|---|
Client | Server | |
Windows(*) |
10+ |
10+ (**) |
macOS |
10.7+ |
10.9+ |
iOS |
5+ |
6+ |
Android |
4.3+ |
5+ |
GATT (GENERIC ATTRIBUTE PROFILE) Profiles
Profiles are high level definitions that define how to use standard services in your applications. For example, there is a Heart Rate profile that is used for fitness or health applications. The server device with a Heart Rate Sensor exposes the standard Heart Rate Service so that the BluetoothLE client discovers the service and starts collecting data, for example the bpm (beats per minute).
The GATT profile is the combination of service + characteristics.
The official page with the GATT Profiles is GATT Specifications for Standard Profiles.
Place a TBluetoothLE Component
Use the new TBluetoothLE component to implement the RTL BluetoothLE feature for server and client applications.
TBluetoothLE includes the System.Bluetooth unit in your application and internally calls TBluetoothLEManager.Current to get an instance of TBluetoothLEManager. TBluetoothLEManager
is the main class for Bluetooth Low Energy communications.
TBluetoothLEManager.Current
always returns the same instance of TBluetoothLEManager
. You do not need more than one instance of TBluetoothLEManager
.Discovering Devices
BluetoothLE does not work as the Classic Bluetooth, you do not need to pair the devices. BluetoothLE clients need to discover BluetoothLE servers.
- Applications running on Windows platform lower than Windows 10 need to pair the devices before discovering BluetoothLE servers. For more information, see Windows Bluetooth FAQ.
- The WinRT API for Windows 10+ platforms allows to scan for devices without the need to pair them.
Use the DiscoverDevices method to discover BluetoothLE servers.
procedure DoScan;
const
HeartRateService: TBluetoothUUID = '{0000180D-0000-1000-8000-00805F9B34FB}';
begin
BluetoothLE1.DiscoverDevices(2500) // The parameter is the timeout in milliseconds.
BluetoothLE1.DiscoverDevices(2500, [HRService]) // It only exposes devices with the Heart Rate service to the BluetoothLE client.
end;
After this period of time, the OnEndDiscoverDevices event is fired. Once you discovered the device you can start getting the services and characteristics from the standard profile as outlined below.
Using Scan Filters
The RTL provides a BLE scan filter implementation that takes advantage of the new BLE low consumption chips.
You can scan for specific BLE devices using customized independent scan filters:
- Create your filter as a TBluetoothLEScanFilter.
- Specify the fields you want to filter your devices by.
- Optionally, for those devices that use ManufacturerSpecificData such as AltBeacons and iBeacons, you can use the TBeaconManufacturerDataHelper helper class, in order to filter by this data. Then pass the TBeaconManufacturerDataHelper content to the filter.
- Finally, add the filter to the filter list and start discovering devices with the new implementation of StartDiscovery.
procedure DoScanWithFilter;
const
HeartRateService: TGUID = '{0000180D-0000-1000-8000-00805F9B34FB}';
var
ABLEAdvertisedDataFilter: TBluetoothLEScanFilter;
ABLEAdvertisedDataFilterList: TBluetoothLEScanFilterList;
begin
ABLEAdvertisedDataFilter:= TBluetoothLEScanFilter.Create;
ABLEAdvertisedDataFilterList:= TBluetoothLEScanFilterList.Create;
ABLEAdvertisedDataFilter.ServiceUUID:= HeartRateService;
ABLEAdvertisedDataFilterList.Add(ABLEAdvertisedDataFilter);
BluetoothLE1.CurrentManager.StartDiscovery(2500,ABLEAdvertisedDataFilterList);
end;
Services and Characteristics
Discovering and Getting Services
Services are collections of characteristics and relationships to other services that encapsulate the behavior of part of a device.
A GATT profile includes one or more standard services that are identified by a number. For example, the Heart Rate service has an official number assigned: "0x180D".
The official page with Standard Services information is Standard BluetoothLE Services.
To get a service you need to use the complete UUID which is the assigned number for the standard service + the base bluetooth code, for example the complete code for the Heart Rate service is 0000180D-0000-1000-8000-00805F9B34FB
.
Use the DiscoverServices method to discover the services for a particular device. Once the services are discovered the OnServicesDiscovered event is triggered.
Once you discover the services, you need to get them. Use the GetServices method to get a list of services from a device or the GetService method to get a particular service from a device.
Discovering and Getting Characteristics
One service can contain one ore more characteristic that provide information for the particular service. Each characteristic is identified by an official number. For example, the Heart Rate service has a characteristic to measure the heart rate, Heart Rate Measurement with UUID 00002A37-0000-1000-8000-00805F9B34FB
and another characteristic to identify the location of the sensor, Body Sensor Location with UUID 00002A38-0000-1000-8000-00805F9B34FB
.
Use the GetCharacteristics method to get a list with the characteristics for a particular service, use the GetCharacteristic method to get the information of a particular characteristic.
Reading, Writing or Subscribing to a Characteristic
Once you get the characteristic using GetCharacteristic you can read or write (if available) the information contained. The OnCharacteristicRead event handler fires after reading the characteristic.
To get the current value of a characteristic use the ReadCharacteristic method. Use WriteCharacteristic to write if this option is available on the server.
You can also subscribe to a characteristic to get the information each time it changes. For example, to start monitoring the heart rate sensor you can read the current value with the GetCharacteristic and then use the SubscribeToCharacteristic method to get the information when it changes. To stop monitoring use the UnSubscribeToCharacteristic method.
Processing the Received Data
The client device receives an array of data from the server. To translate the data into readable information, follow the specification on the GATT profile. For example, you can find the data package details on the official page for the Heart Rate Measurement characteristic: Heart Rate Measurement Data Package Structure.
For example, for the Heart rate measurement characteristic, the first byte contains flags with information about the data transported on the Bluetooth LE package. The bit 0
of the Flags field defines the Heart Rate value format: UINT8 or UINT16. Depending on the format you need to extract the second byte of the data package or the second and the third package to get the bpm (beats per minute).
BluetoothLE Server
To create a server to expose or publish standard services:
- Place a TBluetoothLE component in your project.
- Use the GetGattServer method to publish Bluetooth Low Energy services.
- Use the CreateService method from the TBluetoothGattServer class to create the service using the standard UUID.
- Use the CreateCharacteristic method from the TBluetoothGattServer class to create the characteristics for the service using the standard UUIDs.
- Use the AddService method to add the service to the Gatt server.
- The OnCharacteristicReadRequest event handler fires when the server receives a reading request from the client device.
- The OnCharacteristicWriteRequest event handler fires when the server receives a writing request from the client device.
Non-Standard Profiles
You can create server and client applications using the BluetoothLE technology without using GATT profiles, which means that you can create your own services and characteristics for a private communication between server and client devices.
Using a non-standard profile requires a 128bit UUID and it must be generated randomly.
Every Bluetooth LE device acting as a GATT server must implement the official Generic Access service with the Device Name and Appearance characteristics. See the official web for more information: Generic Access service.
Adding Support for Background Execution on iOS
If your iOS application requires that some services continue running in the background, before you deploy your final application you should specify the values of the UIBackgroundModesProject
key in the Version Info page.
UIBackgroundModesProject
key:
bluetooth-central
: If your application assumes the central role.bluetooth-peripherical
: If your application assumes a peripheral role.
See Core Bluetooth Background Processing for iOS Apps for further information.