Android 蓝牙 与 BLE 低功耗蓝牙的最佳实践

本文深入探讨了Android平台上的低功耗蓝牙(BLE)技术,从蓝牙的工作原理、基本概念到蓝牙3.0和蓝牙4.0(BLE)的实践。详细介绍了蓝牙的初始化、搜索、配对、连接、数据传输以及BLE库的使用,帮助开发者从零开始掌握BLE技术。
摘要由CSDN通过智能技术生成

本文较长,阅读需要十分钟


640?wx_fmt=jpeg


鉴于星球的很多同学比较期望此类文章,本文我们好好的来聊聊低功耗蓝牙,相信有小部分同学正在从事的就是此行业了,这篇文章算是从零开始吧,带领你从新认识BLE,所以前面会有一些长篇大论,耐心读写去,收获满满。


一.蓝牙的工作原理

蓝牙的设备关系处于C/S架构,也就是说,一个是Client,一个是Server,两端连接成功之后将建立数据链,建立成功之后就能进行双向的数据或语音通讯,并且两端都是可以发起断链操作,也就是说只有在设备连接的时候才会有身份关系,之后双向的可操作性都是一样的,而搜索配对这个过程,我们可以理解为呼叫:主端发起呼叫首先是查找,然后根据蓝牙地址进行配对,配对成功后进行建链,蓝牙在手机上的应用,一般都是无线传输,但是应用最广泛的,还是基于蓝牙模块的串口通信。


二.蓝牙的基本概念

先来了解一下UUID,UUID被用于唯一标识的一个服务,主设备通过UUID访问从设备提供相同UUID的服务,从而建立C/S模式,再来了解一下基础的概念知识,一般我们使用的无外乎蓝牙3.0(传统蓝牙) 和 蓝牙4.0(低功耗蓝牙),他们之前的使用有一些共性也有一些区别的,所以我们虽然是以BLE为主,但是我们还是要先从传统蓝牙了解,这样也能更好的平移过去,我们先来了解传统蓝牙


三.蓝牙3.0的实践

我们就来基础的使用一下传统蓝牙,先了解传统蓝牙的两个关键类


  • BluetoothAdapter

  • BluetoothDevice


BluetoothAdapter位于源码中frameworks/base/core/java/android/bluetooth/目录下,作为本地适配器的存在,他有一系列的可操作本地功能的方法,我们再来看下BluetoothDevice,本地蓝牙设备,记录了机身相关蓝牙信息和同步蓝牙状态信息的一个类,通过实例,我们就可以使用了。


1.初始化

首先是添加权限,在传统蓝牙中,我们的权限需要添加如下两个:


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

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


然后就可以操作我们的蓝牙设备获取本地适配器来打开蓝牙了:

640?wx_fmt=jpeg      

这里我们可以看到,我通过getDefaultAdapter获取到BluetoothAdapter对象,这里要判断是否为空,因为模拟器是获取不到对象的,我们看下他的实现就知道了:

640?wx_fmt=jpeg    

这是一个单例的写法,我们通过ServiceManager.getService去获取与framework通讯的IBinder,如果能获取到,说明系统蓝牙层是运行状态的,我们就可以初始化BluetoothAdapter并且返回了,否则会打印:Bluetooth binder is null


这里还要看下,我们可以通过两种方式来打开蓝牙,实际上是一种方式,另外一种知识Setting对外的接口而已,我们可以调用enable来打开,也可以通过disable来关闭蓝牙,这些方法包括适配器中的方法无外乎都是外包装了一层,最终的实现还是BluetoothManager通过IBluetoothManager接口实现的,这里还可以看到我们的第二种方法就是Intent跳转,这里可以传入一个requestCode来接收返回结果是否开启蓝牙。


2.已配对列表

到这里蓝牙是打开了,我们紧接着就可以实现搜索等功能并且展示蓝牙列表了,首先我们可以通过适配器去获取已配对的列表:

640?wx_fmt=jpeg      

这里通过getBondedDevices获得一个Set集合,只要遍历就能得到已配对的列表,我们来看下这个方法的实现:

640?wx_fmt=jpeg      

他首先判断了当前的状态是否是开启的,如果不是则返回一个空的集合,然后再判断mService是否为空,我们在getDefaultAdapter的源码中看到,mService实际上就是绑BluetoothManager的服务,所以如果调用getDefaultAdapter或者设备不支持蓝牙,则调用getBondedDevices获取为空。


这里用到了一个mServiceLock,也就是ReentrantReadWriteLock,这是一个线程锁,同一时间只能允许一个线程访问,确保binder的通信,后面会有很多地方用到这个锁的。


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值