Blog Back to all posts View all authors

Xamarin Month #8: Bluetooth LE for Xamarin.Forms - How To Control Things From The Level Of Mobile App

by Tomasz Kuźniar
February 08. 2019

My first approach to programming was at primary school. During Computer Science classes, we were navigating a little turtle in Logo. It was the time when I got fascinated by IT. Controlling the turtle was fun. Who knew that one day I will be creating mobile applications that are going to control real things like robots via Bluetooth LE? I definitely didn’t.

Now I’m a Mobile Developer who wants to teach you how to get things moving via Bluetooth with the help of Xamarin.Forms.

 

 

Basics Of Bluetooth LE Protocole

Alright, that’s enough of nostalgia, let’s get down to business. We use Bluetooth LE Protocole to the communication between devices. Each of them can have one of the following roles:

GATT Client
- GATT Server


 

This construction is similar to the traditional Client – Server architecture.

 

 

Before we dig into the code, you must recognize some useful definitions:

Services - provided features and associated behaviors made to interact with the peripheral. Every service contains a collection of characteristics. Remember, first come services, then characteristics.

 

Characteristics - definition of the data divided into value and declaration. They occur in several modes: read, write, notify, indicate

 

Descriptor - an optional attribute that involves data on the specific value and ways of accessing it. It's located in characteristics.

 

UUID: Universally Unique ID that get transmitted over the air. This way, peripheral can pass the information to a central on services it provides.

 

Bluetooth LE: GATT Server Scheme; source: https://www.bignerdranch.com/blog/bluetooth-low-energy-part-1/

Bluetooth LE: Client-Service scheme

 

Attention! You can’t leave this page without remembering the following stuff:

- You can connect Bluetooth LE peripheral to only one central device at a time,
- Client must request the Server to send data – it won’t do it on its own,
- Server initiates operations of Notifications and Indications are whenever a value in the database changes.

 

Mental notes made? Great, let's move on to another part!

 

 

Xamarin.Forms App as a GATT Client

For the communication of cross-platform app with Bluetooth LE, use ACR Reactive BluetoothLE Plugin library, you can get it here. Install the package I've mentioned above to every project. (Core, Android, iOS).


Android project set up

In Android, we add permissions to AndroidManifest.xml. Remember that in the case of Android 6+ and other later versions, you should ask the user for the permissions with the pop-up. For this purpose, use PermissionPlugin available here

 

<uses-permission android:name="android.permission.BLUETOOTH"/>
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN"/>

 

<!--this is necessary for Android v6+ to get the device name and address-->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />

 

iOS project set up

In the case of iOS, add following keys to the Info.plist file:

<key>UIBackgroundModes</key>
<array>
    <!--for connecting to devices (client)-->
    <string>bluetooth-central</string>

    <!--for server configurations if needed-->
    <string>bluetooth-peripheral</string>
</array>

<!--To add a description to the Bluetooth request message (on iOS 10 this is required!)-->
<key>NSBluetoothPeripheralUsageDescription</key>
<string>YOUR CUSTOM MESSAGE</string>


Devices search

To find nearby devices, use the adapter from the plugin, which contains the following methods:

var _adapter = CrossBleAdapter.Current;

_adapter.Scan();

_adapter.ScanExtra();

_adapter.ScanInterval();

_adapter.ScanForUniqueDevices();
_adapter.ScanUntilDeviceFound();

_adapter.ScanForHeartRateSensors();


You can even attach an event that will inform you about finding a device:

 _adapter.ScanForUniqueDevices().Subscribe(device => DeviceDiscovered(device));
 

Connecting with a device

You can simply do this by calling a method on found device:

foundDevice.Connect();

 

Before connecting with a device, you can use events like:

foundDevice.WhenConnected().Subscribe(result => Connected(result));
foundDevice.WhenAnyCharacteristicDiscovered().Subscribe(result => CharacteristicsDiscovered(result));
foundDevice.WhenStatusChanged().Subscribe(status => StatusChanged(status));

 

They will help you with monitoring of the connection with the device and finding characteristics that are necessary for communication.

 

Disconnecting from the device occurs after you run the following code:

if (_connectedDevice.IsConnected())
    _connectedDevice.CancelConnection();

 

Communication

READ
var result = await characteristic.Read(); // use result.Data to see response

 

WRITE
await characteristic.Write(bytes);

 

NOTIFICATIONS
characteristic.EnableNotifications();
characteristic.WhenNotificationReceived().Subscribe( result => {
    //result.Data to get at response
}); 

If you have any questions, feel free to ask in the comments :)



SEE ALSO

 

Check out other awesome articles from Xamarin Month!

 

Configuration of Continuous Integration for Xamarin using GitLab

Dependency Injection in C# - how to make it?

contact us

Have an idea ? Let’s talk

Office in Rzeszow
Office in Warsaw
CONTACT US
CONTACT INFORMATION

GET IN TOUCH

Fill up the form and we will contact you shortly

Name
E-Mail
Message

Company information

Fill up the form and we will contact you shortly.

ServoCode Sp. z o.o.

Jasionka 954E, 36-002 Jasionka, Poland

NIP: 8133719852

REGON: 364182909

KRS: 0000611643

We are using cookies to provide statistics that help us give you the best experience of our site. You can find out more or switch them off if you prefer. However, by continuing to use the site without changing settings, you are agreeing to our use of cookies. Read more

close