![]() |
VOOZH | about |
dotnet add package Plugin.BLE --version 3.2.1
NuGet\Install-Package Plugin.BLE -Version 3.2.1
<PackageReference Include="Plugin.BLE" Version="3.2.1" />
<PackageVersion Include="Plugin.BLE" Version="3.2.1" />Directory.Packages.props
<PackageReference Include="Plugin.BLE" />Project file
paket add Plugin.BLE --version 3.2.1
#r "nuget: Plugin.BLE, 3.2.1"
#:package Plugin.BLE@3.2.1
#addin nuget:?package=Plugin.BLE&version=3.2.1Install as a Cake Addin
#tool nuget:?package=Plugin.BLE&version=3.2.1Install as a Cake Tool
Build status: 👁 Build status
Xamarin, MAUI and MvvMCross plugin for accessing the bluetooth functionality. The plugin is loosely based on the BLE implementation of Monkey Robotics.
Important Note: With the term "vanilla" we mean the non-MvvmCross version, i.e. the pure Xamarin or MAUI plugin. You can use it without MvvmCross, if you download the vanilla package.
| Platform | Version | Limitations |
|---|---|---|
| Xamarin.Android | 4.3 | |
| Xamarin.iOS | 7.0 | |
| Xamarin.Mac | 10.9 (Mavericks) | >= 2.1.0 |
| Xamarin.UWP | 1709 - 10.0.16299 | >= 2.2.0 |
| MAUI (Android, iOS, Mac, WinUI) | >= 3.0.0 |
| package | stable | beta | downloads |
|---|---|---|---|
| Plugin.BLE | 👁 NuGet |
👁 NuGet Beta |
👁 Downloads |
| MvvmCross.Plugin.BLE | 👁 NuGet MvvMCross |
👁 NuGet MvvMCross Beta |
👁 Downloads |
Vanilla
// stable
Install-Package Plugin.BLE
// or pre-release
Install-Package Plugin.BLE -Pre
MvvmCross
Install-Package MvvmCross.Plugin.BLE
// or
Install-Package MvvmCross.Plugin.BLE -Pre
Add these permissions to AndroidManifest.xml. For Marshmallow and above, please follow Requesting Runtime Permissions in Android Marshmallow and don't forget to prompt the user for the location permission.
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.BLUETOOTH" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
Android 12 and above may require one or more of the following additional runtime permissions, depending on which features of the library you are using (see the android Bluetooth permissions documentation)
<uses-permission android:name="android.permission.BLUETOOTH_SCAN" />
<uses-permission android:name="android.permission.BLUETOOTH_CONNECT" />
<uses-permission android:name="android.permission.BLUETOOTH_ADVERTISE" />
Add this line to your manifest if you want to declare that your app is available to BLE-capable devices only:
<uses-feature android:name="android.hardware.bluetooth_le" android:required="true"/>
On iOS you must add the following keys to your Info.plist
<key>UIBackgroundModes</key>
<array>
<string>bluetooth-central</string>
<string>bluetooth-peripheral</string>
</array>
<key>NSBluetoothPeripheralUsageDescription</key>
<string>YOUR CUSTOM MESSAGE</string>
<key>NSBluetoothAlwaysUsageDescription</key>
<string>YOUR CUSTOM MESSAGE</string>
On MacOS (version 11 and above) you must add the following keys to your Info.plist:
<key>NSBluetoothAlwaysUsageDescription</key>
<string>YOUR CUSTOM MESSAGE</string>
Add this line to the Package Manifest (.appxmanifest):
<DeviceCapability Name="bluetooth" />
We provide a sample Xamarin.Forms app, that is a basic bluetooth LE scanner. With this app, it's possible to
Have a look at the code and use it as starting point to learn about the plugin and play around with it.
Vanilla
var ble = CrossBluetoothLE.Current;
var adapter = CrossBluetoothLE.Current.Adapter;
MvvmCross
The MvvmCross plugin registers IBluetoothLE and IAdapter as lazy initialized singletons. You can resolve/inject them as any other MvvmCross service. You don't have to resolve/inject both. It depends on your use case.
var ble = Mvx.Resolve<IBluetoothLE>();
var adapter = Mvx.Resolve<IAdapter>();
or
MyViewModel(IBluetoothLE ble, IAdapter adapter)
{
this.ble = ble;
this.adapter = adapter;
}
Please make sure you have this code in your LinkerPleaseLink.cs file
public void Include(MvvmCross.Plugins.BLE.Plugin plugin)
{
plugin.Load();
}
var state = ble.State;
You can also listen for State changes. So you can react if the user turns on/off bluetooth on your smartphone.
ble.StateChanged += (s, e) =>
{
Debug.WriteLine($"The bluetooth state changed to {e.NewState}");
};
adapter.DeviceDiscovered += (s,a) => deviceList.Add(a.Device);
await adapter.StartScanningForDevicesAsync();
var scanFilterOptions = new ScanFilterOptions();
scanFilterOptions.ServiceUuids = new [] {guid1, guid2, etc}; // cross platform filter
scanFilterOptions.ManufacturerDataFilters = new [] { new ManufacturerDataFilter(1), new ManufacturerDataFilter(2) }; // android only filter
scanFilterOptions.DeviceAddresses = new [] {"80:6F:B0:43:8D:3B","80:6F:B0:25:C3:15",etc}; // android only filter
await adapter.StartScanningForDevicesAsync(scanFilterOptions);
Set adapter.ScanTimeout to specify the maximum duration of the scan.
Set adapter.ScanMode to specify scan mode. It must be set before calling StartScanningForDevicesAsync(). Changing it while scanning, will not affect the current scan.
ConnectToDeviceAsync returns a Task that finishes if the device has been connected successful. Otherwise a DeviceConnectionException gets thrown.
try
{
await _adapter.ConnectToDeviceAsync(device);
}
catch(DeviceConnectionException e)
{
// ... could not connect to device
}
ConnectToKnownDeviceAsync can connect to a device with a given GUID. This means that if the device GUID is known, no scan is necessary to connect to a device. This can be very useful for a fast background reconnect.
Always use a cancellation token with this method.
try
{
await _adapter.ConnectToKnownDeviceAsync(guid, cancellationToken);
}
catch(DeviceConnectionException e)
{
// ... could not connect to device
}
var services = await connectedDevice.GetServicesAsync();
or get a specific service:
var service = await connectedDevice.GetServiceAsync(Guid.Parse("ffe0ecd2-3d16-4f8d-90de-e89e7fc396a5"));
var characteristics = await service.GetCharacteristicsAsync();
or get a specific characteristic:
var characteristic = await service.GetCharacteristicAsync(Guid.Parse("d8de624e-140f-4a22-8594-e2216b84a5f2"));
var bytes = await characteristic.ReadAsync();
await characteristic.WriteAsync(bytes);
characteristic.ValueUpdated += (o, args) =>
{
var bytes = args.Characteristic.Value;
};
await characteristic.StartUpdatesAsync();
var descriptors = await characteristic.GetDescriptorsAsync();
var bytes = await descriptor.ReadAsync();
await descriptor.WriteAsync(bytes);
Returns all BLE devices connected or bonded (only Android) to the system. In order to use the device in the app you have to first call ConnectAsync.
var systemDevices = adapter.GetSystemConnectedOrPairedDevices();
foreach(var device in systemDevices)
{
await _adapter.ConnectToDeviceAsync(device);
}
The BLE API implementation (especially on Android) has the following limitations:
try
{
await _adapter.ConnectToDeviceAsync(device);
}
catch(DeviceConnectionException ex)
{
//specific
}
catch(Exception ex)
{
//generic
}
Build
Open a console, change to the folder "dotnet-bluetooth-le/.build" and run cake.
pack the nuget
nuget pack ../Source/Plugin.BLE/Plugin.BLE.csproj
nuget pack ../Source/MvvmCross.Plugins.BLE/MvvmCross.Plugins.BLE.csproj
We usually do our development work on a branch with the name of the milestone. So please base your pull requests on the currently open development branch.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net5.0 net5.0 was computed. net5.0-windows net5.0-windows was computed. net6.0 net6.0 was computed. net6.0-android net6.0-android was computed. net6.0-ios net6.0-ios was computed. net6.0-maccatalyst net6.0-maccatalyst was computed. net6.0-macos net6.0-macos was computed. net6.0-tvos net6.0-tvos was computed. net6.0-windows net6.0-windows was computed. net7.0 net7.0 was computed. net7.0-android net7.0-android was computed. net7.0-ios net7.0-ios was computed. net7.0-maccatalyst net7.0-maccatalyst was computed. net7.0-macos net7.0-macos was computed. net7.0-tvos net7.0-tvos was computed. net7.0-windows net7.0-windows was computed. net8.0 net8.0 was computed. net8.0-android net8.0-android was computed. net8.0-android34.0 net8.0-android34.0 is compatible. net8.0-browser net8.0-browser was computed. net8.0-ios net8.0-ios was computed. net8.0-ios18.0 net8.0-ios18.0 is compatible. net8.0-maccatalyst net8.0-maccatalyst was computed. net8.0-maccatalyst18.0 net8.0-maccatalyst18.0 is compatible. net8.0-macos net8.0-macos was computed. net8.0-tvos net8.0-tvos was computed. net8.0-windows net8.0-windows was computed. net8.0-windows10.0.19041 net8.0-windows10.0.19041 is compatible. net8.0-windows10.0.22000 net8.0-windows10.0.22000 is compatible. net9.0 net9.0 was computed. net9.0-android net9.0-android was computed. net9.0-android35.0 net9.0-android35.0 is compatible. net9.0-browser net9.0-browser was computed. net9.0-ios net9.0-ios was computed. net9.0-ios18.0 net9.0-ios18.0 is compatible. net9.0-maccatalyst net9.0-maccatalyst was computed. net9.0-maccatalyst18.0 net9.0-maccatalyst18.0 is compatible. net9.0-macos net9.0-macos was computed. net9.0-tvos net9.0-tvos was computed. net9.0-windows net9.0-windows was computed. net9.0-windows10.0.19041 net9.0-windows10.0.19041 is compatible. net10.0 net10.0 was computed. net10.0-android net10.0-android was computed. net10.0-browser net10.0-browser was computed. net10.0-ios net10.0-ios was computed. net10.0-maccatalyst net10.0-maccatalyst was computed. net10.0-macos net10.0-macos was computed. net10.0-tvos net10.0-tvos was computed. net10.0-windows net10.0-windows was computed. |
| .NET Core | netcoreapp2.0 netcoreapp2.0 was computed. netcoreapp2.1 netcoreapp2.1 was computed. netcoreapp2.2 netcoreapp2.2 was computed. netcoreapp3.0 netcoreapp3.0 was computed. netcoreapp3.1 netcoreapp3.1 was computed. |
| .NET Standard | netstandard2.0 netstandard2.0 is compatible. netstandard2.1 netstandard2.1 was computed. |
| .NET Framework | net461 net461 was computed. net462 net462 was computed. net463 net463 was computed. net47 net47 was computed. net471 net471 was computed. net472 net472 was computed. net48 net48 was computed. net481 net481 was computed. |
| MonoAndroid | monoandroid monoandroid was computed. monoandroid13.0 monoandroid13.0 is compatible. |
| MonoMac | monomac monomac was computed. |
| MonoTouch | monotouch monotouch was computed. |
| Tizen | tizen40 tizen40 was computed. tizen60 tizen60 was computed. |
| Universal Windows Platform | uap10.0.17763 uap10.0.17763 is compatible. |
| Xamarin.iOS | xamarinios xamarinios was computed. xamarinios10 xamarinios10 is compatible. |
| Xamarin.Mac | xamarinmac xamarinmac was computed. xamarinmac20 xamarinmac20 is compatible. |
| Xamarin.TVOS | xamarintvos xamarintvos was computed. |
| Xamarin.WatchOS | xamarinwatchos xamarinwatchos was computed. |
Showing the top 5 NuGet packages that depend on Plugin.BLE:
| Package | Downloads |
|---|---|
|
MvvmCross.Plugin.BLE
MVVMCross Plugin to access Bluetooth Low Energy functionality on Android, iOS, macOS, and Windows. Read the full documentation on the projects page. |
|
|
Buttplug.Server.Managers.XamarinBluetoothManager
Xamarin Bluetooth LE (Android/iOS) device support for Buttplug Servers, using Plugin.BLE. (.Net Standard 2.0) |
|
|
Plugin.BLE.FTMS
Package Description |
|
|
XBeeLibrary.Xamarin
C# library for Xamarin to interact with Digi International's XBee radio frequency modules from mobile devices. |
|
|
Moduware.Platform.Core
Library to work with Moduware modular platform. |
Showing the top 4 popular GitHub repositories that depend on Plugin.BLE:
| Repository | Stars |
|---|---|
|
VladislavAntonyuk/MauiSamples
.NET MAUI Samples
|
|
|
lswiderski/mi-scale-exporter
Mobile App to export data from Mi Body Composition Scale and upload it to Garmin Connect Cloud
|
|
|
densen2014/BlazorHybrid
关于BlazorHybrid的一切研究. 用 c # 和 Razor 创建本机移动应用和桌面应用。快速开发共享代码库运行于 Windows (Winforms/WPF/UWP)、Android、iOS、macOS、Linux 的应用。
|
|
|
sharpbrick/powered-up
.NET implementation of the LEGO PoweredUp Protocol
|
| Version | Downloads | Last Updated |
|---|---|---|
| 3.3.0-beta.2 | 252 | 5/11/2026 |
| 3.3.0-beta.1 | 2,354 | 1/27/2026 |
| 3.2.1 | 4,453 | 5/14/2026 |
| 3.2.0 | 86,572 | 10/26/2025 |
| 3.2.0-beta.2 | 1,528 | 10/12/2025 |
| 3.2.0-beta.1 | 7,043 | 3/30/2025 |
| 3.1.1 | 134 | 5/16/2026 |
| 3.1.0 | 503,473 | 5/20/2024 |
| 3.1.0-rc.1 | 6,099 | 5/3/2024 |
| 3.1.0-beta.3 | 3,170 | 3/25/2024 |
| 3.1.0-beta.2 | 4,630 | 2/12/2024 |
| 3.1.0-beta.1 | 20,628 | 11/17/2023 |
| 3.0.0 | 163,449 | 10/8/2023 |
| 3.0.0-rc.1 | 4,993 | 9/21/2023 |
| 3.0.0-beta.6 | 3,168 | 9/5/2023 |
| 3.0.0-beta.5 | 11,695 | 8/5/2023 |
| 3.0.0-beta.4 | 16,343 | 5/21/2023 |
| 3.0.0-beta.3 | 25,824 | 4/17/2023 |
| 3.0.0-beta.2 | 19,247 | 11/24/2022 |
| 3.0.0-beta.1 | 8,513 | 11/17/2022 |