Android BLE开发: BLE Peripheral开发流程

2024-06-03 17:58

本文主要是介绍Android BLE开发: BLE Peripheral开发流程,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Android从lolipop开始支持了BLE Peripheral开发。网上也有关于Framework的文章。真的关于应用开发的确不多,google官网也只给出了一个Central的Demo。之前做了一个BLE Peripheral的Demo,这里将Peripheral开发的一些流程简单整理一下。不多说,直接上代码。

初始化

//初始化BluetoothManager和BluetoothAdapter
if(mBluetoothManager == null)mBluetoothManager = (BluetoothManager) mActivity.getSystemService(Context.BLUETOOTH_SERVICE);if (mBluetoothManager != null && mBluetoothAdapter == null) {mBluetoothAdapter = mBluetoothManager.getAdapter();
}//打开蓝牙的套路
if ((mBluetoothAdapter == null) || (!mBluetoothAdapter.isEnabled())) {Toast.makeText(mActivity, R.string.bt_unavailable, Toast.LENGTH_SHORT).show();Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);mActivity.startActivityForResult(enableBtIntent, REQUEST_ENABLE_BT);
}

开始广播

//获取BluetoothLeAdvertiser,BLE发送BLE广播用的一个API
if (mBluetoothAdvertiser == null) {mBluetoothAdvertiser = mBluetoothAdapter.getBluetoothLeAdvertiser();
}
//创建BluetoothGattServerCallback,
//MockServerCallBack这个类继承自BluetoothGattServerCallback
//后面会贴出MockServerCallBack这个类的代码
//BluetoothGattServerCallback这个回调类主要是一些BLE读写的接口
//关于BLE读写的操作都在这个Callback中完成
if (mBluetoothAdvertiser != null) {mMockServerCallBack = new MockServerCallBack(mActivity);//打开BluetoothGattServermGattServer = mBluetoothManager.openGattServer(mActivity, mMockServerCallBack);if(mGattServer == null){Log.d(TAG , "gatt is null");}try{mMockServerCallBack.setupServices(mGattServer);//创建BLE Adevertising并且广播mBluetoothAdvertiser.startAdvertising(createAdvSettings(true, 0), createFMPAdvertiseData(),mAdvCallback);}catch(InterruptedException e){Log.v(TAG, "Fail to setup BleService");}
}

创建Advertising

public static AdvertiseSettings createAdvSettings(boolean connectable, int timeoutMillis) {AdvertiseSettings.Builder builder = new AdvertiseSettings.Builder();//设置广播的模式,应该是跟功耗相关builder.setAdvertiseMode(AdvertiseSettings.ADVERTISE_MODE_BALANCED);builder.setConnectable(connectable);builder.setTimeout(timeoutMillis);builder.setTxPowerLevel(AdvertiseSettings.ADVERTISE_TX_POWER_HIGH);return builder.build();
}//设置一下FMP广播数据
public static AdvertiseData createFMPAdvertiseData() {AdvertiseData.Builder builder = new AdvertiseData.Builder();builder.setIncludeDeviceName(true);AdvertiseData adv = builder.build();return adv;
}//发送广播的回调,onStartSuccess/onStartFailure很明显的两个Callback
private AdvertiseCallback mAdvCallback = new AdvertiseCallback() {public void onStartSuccess(android.bluetooth.le.AdvertiseSettings settingsInEffect) {if (settingsInEffect != null) {Log.d(TAG, "onStartSuccess TxPowerLv="+ settingsInEffect.getTxPowerLevel()+ " mode=" + settingsInEffect.getMode()+ " timeout=" + settingsInEffect.getTimeout());} else {Log.d(TAG, "onStartSuccess, settingInEffect is null");}}public void onStartFailure(int errorCode) {Log.d(TAG, "onStartFailure errorCode=" + errorCode);};
};

BLE需要的BluetoothGattServerCallback

import android.app.Activity;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothGatt;
import android.bluetooth.BluetoothGattCharacteristic;
import android.bluetooth.BluetoothGattDescriptor;
import android.bluetooth.BluetoothGattServer;
import android.bluetooth.BluetoothGattServerCallback;
import android.bluetooth.BluetoothGattService;
import android.util.Log;public class MockServerCallBack extends BluetoothGattServerCallback {private static final String TAG = "BleServer";private byte[] mAlertLevel = new byte[] {(byte) 0x00};private Activity mActivity;private HomePager mHomepager;private boolean mIsPushStatic = false;private BluetoothGattServer mGattServer;private BluetoothGattCharacteristic mDateChar;private BluetoothDevice btClient;private BluetoothGattCharacteristic mHeartRateChar;private BluetoothGattCharacteristic mTemperatureChar;private BluetoothGattCharacteristic mBatteryChar;private BluetoothGattCharacteristic mManufacturerNameChar;private BluetoothGattCharacteristic mModuleNumberChar;private BluetoothGattCharacteristic mSerialNumberChar;public void setupServices(BluetoothGattServer gattServer) throws InterruptedException{if (gattServer == null) {throw new IllegalArgumentException("gattServer is null");}mGattServer = gattServer;// 设置一个GattService以及BluetoothGattCharacteristic { //immediate alertBluetoothGattService ias = new BluetoothGattService( UUID.fromString(IMXUuid.SERVICE_IMMEDIATE_ALERT),BluetoothGattService.SERVICE_TYPE_PRIMARY);//alert level char.BluetoothGattCharacteristic alc = new BluetoothGattCharacteristic(UUID.fromString(IMXUuid.CHAR_ALERT_LEVEL),BluetoothGattCharacteristic.PROPERTY_READ |BluetoothGattCharacteristic.PROPERTY_WRITE | BluetoothGattCharacteristic.PROPERTY_NOTIFY ,BluetoothGattCharacteristic.PERMISSION_READ |BluetoothGattCharacteristic.PERMISSION_WRITE);alc.setValue("");ias.addCharacteristic(alc);if(mGattServer!=null && ias!=null)mGattServer.addService(ias);}}//当添加一个GattService成功后会回调改接口。public void onServiceAdded(int status, BluetoothGattService service) {if (status == BluetoothGatt.GATT_SUCCESS) {Log.d(TAG, "onServiceAdded status=GATT_SUCCESS service=" + service.getUuid().toString());} else {Log.d(TAG, "onServiceAdded status!=GATT_SUCCESS");}}//BLE连接状态改变后回调的接口public void onConnectionStateChange(android.bluetooth.BluetoothDevice device, int status,int newState) {Log.d(TAG, "onConnectionStateChange status=" + status + "->" + newState);}//当有客户端来读数据时回调的接口public void onCharacteristicReadRequest(android.bluetooth.BluetoothDevice device,int requestId, int offset, BluetoothGattCharacteristic characteristic) {Log.d(TAG, "onCharacteristicReadRequest requestId=" + requestId + " offset=" + offset);mGattServer.sendResponse(device, requestId, BluetoothGatt.GATT_SUCCESS, offset,characteristic.getValue());}//当有客户端来写数据时回调的接口@Overridepublic void onCharacteristicWriteRequest(android.bluetooth.BluetoothDevice device,int requestId, BluetoothGattCharacteristic characteristic, boolean preparedWrite,boolean responseNeeded, int offset, byte[] value) {mGattServer.sendResponse(device, requestId, BluetoothGatt.GATT_SUCCESS, offset, null);}//当有客户端来写Descriptor时回调的接口@Overridepublic void onDescriptorWriteRequest (BluetoothDevice device, int requestId, BluetoothGattDescriptor descriptor, boolean preparedWrite, boolean responseNeeded, int offset, byte[] value) {btClient = device;Log.d(TAG, "onDescriptorWriteRequest");// now tell the connected device that this was all successfullmGattServer.sendResponse(device, requestId, BluetoothGatt.GATT_SUCCESS, offset, value);}
}

至此,BLE Peripheral发送广播所需要的工作都完成了,并且当有Central设备读写该Peripheral设备时候也能通过BluetoothGattServerCallback回调到。

停止广播

//关闭BluetoothLeAdvertiser,BluetoothAdapter,BluetoothGattServer 
if (mBluetoothAdvertiser != null) {mBluetoothAdvertiser.stopAdvertising(mAdvCallback);mBluetoothAdvertiser = null;
}if(mBluetoothAdapter != null){mBluetoothAdapter = null;
}if (mGattServer != null) {mGattServer.clearServices();mGattServer.close();
}       

这样,Android设备就停止了BLE的广播,外部的Central设备就搜索不到该设备并且连接上它了。
BLE Peripheral的API乍一看有些多,其实仔细理一理非常简单,工作重点在于那个Callback的编写。

这篇关于Android BLE开发: BLE Peripheral开发流程的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1027704

相关文章

redis-sentinel基础概念及部署流程

《redis-sentinel基础概念及部署流程》RedisSentinel是Redis的高可用解决方案,通过监控主从节点、自动故障转移、通知机制及配置提供,实现集群故障恢复与服务持续可用,核心组件包... 目录一. 引言二. 核心功能三. 核心组件四. 故障转移流程五. 服务部署六. sentinel部署

SpringBoot集成XXL-JOB实现任务管理全流程

《SpringBoot集成XXL-JOB实现任务管理全流程》XXL-JOB是一款轻量级分布式任务调度平台,功能丰富、界面简洁、易于扩展,本文介绍如何通过SpringBoot项目,使用RestTempl... 目录一、前言二、项目结构简述三、Maven 依赖四、Controller 代码详解五、Service

Android协程高级用法大全

《Android协程高级用法大全》这篇文章给大家介绍Android协程高级用法大全,本文结合实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友跟随小编一起学习吧... 目录1️⃣ 协程作用域(CoroutineScope)与生命周期绑定Activity/Fragment 中手

Python实战之SEO优化自动化工具开发指南

《Python实战之SEO优化自动化工具开发指南》在数字化营销时代,搜索引擎优化(SEO)已成为网站获取流量的重要手段,本文将带您使用Python开发一套完整的SEO自动化工具,需要的可以了解下... 目录前言项目概述技术栈选择核心模块实现1. 关键词研究模块2. 网站技术seo检测模块3. 内容优化分析模

基于Java开发一个极简版敏感词检测工具

《基于Java开发一个极简版敏感词检测工具》这篇文章主要为大家详细介绍了如何基于Java开发一个极简版敏感词检测工具,文中的示例代码简洁易懂,感兴趣的小伙伴可以跟随小编一起学习一下... 目录你是否还在为敏感词检测头疼一、极简版Java敏感词检测工具的3大核心优势1.1 优势1:DFA算法驱动,效率提升10

MySQL 临时表与复制表操作全流程案例

《MySQL临时表与复制表操作全流程案例》本文介绍MySQL临时表与复制表的区别与使用,涵盖生命周期、存储机制、操作限制、创建方法及常见问题,本文结合实例代码给大家介绍的非常详细,感兴趣的朋友跟随小... 目录一、mysql 临时表(一)核心特性拓展(二)操作全流程案例1. 复杂查询中的临时表应用2. 临时

Python开发简易网络服务器的示例详解(新手入门)

《Python开发简易网络服务器的示例详解(新手入门)》网络服务器是互联网基础设施的核心组件,它本质上是一个持续运行的程序,负责监听特定端口,本文将使用Python开发一个简单的网络服务器,感兴趣的小... 目录网络服务器基础概念python内置服务器模块1. HTTP服务器模块2. Socket服务器模块

Android 缓存日志Logcat导出与分析最佳实践

《Android缓存日志Logcat导出与分析最佳实践》本文全面介绍AndroidLogcat缓存日志的导出与分析方法,涵盖按进程、缓冲区类型及日志级别过滤,自动化工具使用,常见问题解决方案和最佳实... 目录android 缓存日志(Logcat)导出与分析全攻略为什么要导出缓存日志?按需过滤导出1. 按

Java 与 LibreOffice 集成开发指南(环境搭建及代码示例)

《Java与LibreOffice集成开发指南(环境搭建及代码示例)》本文介绍Java与LibreOffice的集成方法,涵盖环境配置、API调用、文档转换、UNO桥接及REST接口等技术,提供... 目录1. 引言2. 环境搭建2.1 安装 LibreOffice2.2 配置 Java 开发环境2.3 配

MySQL 升级到8.4版本的完整流程及操作方法

《MySQL升级到8.4版本的完整流程及操作方法》本文详细说明了MySQL升级至8.4的完整流程,涵盖升级前准备(备份、兼容性检查)、支持路径(原地、逻辑导出、复制)、关键变更(空间索引、保留关键字... 目录一、升级前准备 (3.1 Before You Begin)二、升级路径 (3.2 Upgrade