Home > Back-end >  .net Maui Bluetooth LE - Run-time permissions check and set on Android device
.net Maui Bluetooth LE - Run-time permissions check and set on Android device

Time:06-12

Since Microsoft has decided that Bluetooth (and apparently Wi-fi) are not worthy of being on their Maui roadmap I guess we have to do it ourselves :sigh. https://github.com/dotnet/maui/discussions/277 see David Ortinau comment

I admit that even after programming computers on and off since 1977 with paper tape on a PDP-8 I am struggling with getting the proper structure for my code and even understanding how it works, so please forgive me if I get things wrong and feel free to put me on the right track.

Since this will be of benefit to newbies of the future - all hail! I'll try to be as detailed as I can.

I have a Maui app, it has a shell flyout menu and some ViewModels and I'm using the CommunityToolkit.Mvvm (via NuGet) to make my coding life easier with bindings.

The folder structure is Pages>BluetoothPage.xaml and it's corresponding code behind file BluetoothPage.xaml.cs and other pages. There is a Models folder for the classes which contains a BluetoothPeripheral.cs class which holds the class for the properties I will need for remembering peripherals I've connected to and a ViewModels folder in which I have a BluetoothPeripheralsViewModel.cs which is used for binding to my BluetoothPage.

When I start I can select Bluetooth from the shell and go to that BluetoothPage.xaml and it's in the code behind for that file that I start my work.

I managed to use plugin.ble to make a start, but when when I wanted to scan I immediately got the issue that on Android (since version23 (Marshamallow?)) that the app needs to prompt the user to accept permission to use bluetooth.

I have also added the following lines to the Platforms>Android>Resources>AndroidManifest.xml file


  <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" />

  <uses-permission android:name="android.permission.BLUETOOTH_SCAN" />
  <uses-permission android:name="android.permission.BLUETOOTH_CONNECT" />
  <uses-permission android:name="android.permission.BLUETOOTH_ADVERTISE" />

    <uses-feature android:name="android.hardware.bluetooth_le" android:required="true"/>
</manifest>

Here is my basic code and comments - (I'm guessing there is a more sophisticated way of doing this, but for now this is what my brain can handle.)

BluetoothPage.xaml.cs - code behind

//other imports are in a GlobalUsing.cs file
using Android;
using Android.OS;

namespace TSDZ2Monitor.Pages;

public partial class BluetoothPage : ContentPage
{
    public BluetoothPage()
    {
        InitializeComponent();

        *//so I start my code here, but I suspect that I should be using some kind of page displayed, on startup event?*

    Console.WriteLine("Bluetooth here");

    getBLEPermission();
    startScan();
    
    *//Need to get user to accept bluetooth permissions in Android 6.0 ,v23 that is the Run-time Permissions check - should this be in the constructor?*
    async void getBLEPermission()
    {
      bool blePermissionGranted = false;

      int sdk = (int)Build.VERSION.SdkInt; //<-- if you want to check > 23


      //Do the check to see if permission already granted - how?


      if (!blePermissionGranted)  //so go and get permission, display an alert
      {  

        blePermissionGranted = await App.Current.MainPage.DisplayAlert("Alert", "Allow use of bluetooth for scanning for your peripheral devices such as heart rate monitor etc?", "Allow", "Deny");
        if (blePermissionGranted)
        {
          //Set the permission on android - how

        }
        //Console.WriteLine($"SDK version {sdk}");
        //Console.WriteLine($"BLE permission granted: {blePermissionGranted}");

      }

    }

    async void startScan()
    {
       //TODO 
    }
  }

}

Q1 how do I test if Bluetooth permission is set?

Q2 if not how do I set it?

Many thanks for any advice etc.

EDIT (Added): So I've worked out how to use the permission supplied with .net Maui. Here for example is the example using location in the docs https://docs.microsoft.com/en-us/dotnet/maui/platform-integration/appmodel/permissions?tabs=android

//using InTheHand.Bluetooth;

namespace TSDZ2Monitor.Pages;

public partial class BluetoothPage : ContentPage
{
    public BluetoothPage()
    {
        InitializeComponent();

        Console.WriteLine("Bluetooth here");

    getBLEPermission();

    static async void getBLEPermission()
    {
      PermissionStatus status = await Permissions.CheckStatusAsync<Permissions.LocationWhenInUse>();
      if (status != PermissionStatus.Granted)
      {
        status = await Permissions.RequestAsync<Permissions.LocationWhenInUse>();
        if (status != PermissionStatus.Granted)
        {
          //well kill the app because it's no use if bluetooth not enabled
        }
      }
    }


  }

}

Note that I don't need to do an alert, Android does that for me.

Of course the Bluetooth permission is not part of this scenario. How hard can it be to add this? If you are MS please do so.

Any ideas anyone?

CodePudding user response:

Permissions as you've noted need to be entered in the info.plist and appmanifests. Then check their granted or not status as per https://docs.microsoft.com/en-us/xamarin/essentials/permissions?context=xamarin/android&tabs=android

The preview nuget of BLE in Shiny is working in Maui for Maccatalyst, iOS, and Android https://shinylib.net/mobile/ble/index.html

CodePudding user response:

For a working solution please see discussion here https://github.com/dotnet/maui/discussions/277

and full code solution here https://gist.github.com/salarcode/da8ad2b993e67c602db88a62259d0456#gistcomment-4197943

I am so grateful to all who have contributed, but particularly salarcode on github. Cheers.

(I'll leave it to someone else to mark answer :) )

  • Related