Android 6.0后蓝牙的开发,搜索,配对,连接发送数据等(二)
2017-12-07 09:51
621 查看
上一篇博客写了蓝牙的链接, 搜索, 配对等流程 , 这一篇我来说一说我在蓝牙开发时遇到的坑
第一个坑 Android 6.0以后为提供更高的数据保护需要获取定位权限
,
所以在开发中 targetSdkVersion 大于等于23(6.0) 需要在代码中进行权限获取
需要在配置文件中申请两个权限:
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
但是小米手机miui8系统
,会出现调不出定位权限,也没有弹出调用权限提示对话框,只有手动在设置里面手动打开。这相当于是小米手机的一个bug
, 目前还没有解决 , 只能手动在设置-->应用权限中打开 , 一下子就感觉小米很low了!
正常情况下在代码中调用时先进行权限判断,如果没有权限就去申请权限:
调用ActivityCompat.requestPermissions()之后会有一个回调
在网上有人说,当弹出权限确认框之后,用户点击确定或者拒绝时才会调用进行回调:onRequestPermissionsResult
但是在小米手机MIUI上并不是这样的。MIUI上是这样的:权限管理那里设置应用的定位权限为拒绝或者询问时checkAccessFinePermission != PackageManager.PERMISSION_GRANTED,说明没有定位权限 。如果设置为允许,checkAccessFinePermission
==PackageManager.PERMISSION_GRANTED,说明有定位权限。
当设置拒绝时去ActivityCompat.requestPermissions ,并没有弹出权限使用确认框,而是直接回调:没有权限
当设置询问时去ActivityCompat.requestPermissions
,并没有弹出权限使用确认框,而是直接回调:已有权限,然后在调用蓝牙代码的时候弹出确认框。当点击允许时权限管理那里变成了允许,当点击拒绝时,权限管理那里变成拒绝,但是下次再进行权限检查时返回 已有定位权限。权限管理那里明明是拒绝的啊,怎么就有定位权限了?这是MIUI的一个bug,我的系统是:MIUI
8 6.11.3开发版。
第二个坑
如何获取已经连接上的或是处于已连接状态的蓝牙设备 ? 这个问题我是通过博客找到的.利用反射的原理实现的.
BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter();
Class<BluetoothAdapter> bluetoothAdapterClass = BluetoothAdapter.class;//得到BluetoothAdapter的Class对象
try {//得到连接状态的方法
Method method = bluetoothAdapterClass.getDeclaredMethod("getConnectionState", (Class[]) null);
//打开权限
method.setAccessible(true);
int state = (int) method.invoke(adapter, (Object[]) null);
if(state == BluetoothAdapter.STATE_CONNECTED){
Log.i("BLUETOOTH","BluetoothAdapter.STATE_CONNECTED");
Set<BluetoothDevice> devices = adapter.getBondedDevices();
Log.i("BLUETOOTH","devices:"+devices.size());
for(BluetoothDevice device : devices){
Method isConnectedMethod = BluetoothDevice.class.getDeclaredMethod("isConnected", (Class[]) null);
method.setAccessible(true);
boolean isConnected = (boolean) isConnectedMethod.invoke(device, (Object[]) null);
if(isConnected){
Log.i("BLUETOOTH","connected:"+device.getName());
deviceList.add(device);
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
参考资料 http://blog.csdn.net/juesai2015/article/details/78737413
蓝牙开发的Demo: 蓝牙开发demo下载
第一个坑 Android 6.0以后为提供更高的数据保护需要获取定位权限
,
所以在开发中 targetSdkVersion 大于等于23(6.0) 需要在代码中进行权限获取
需要在配置文件中申请两个权限:
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
但是小米手机miui8系统
,会出现调不出定位权限,也没有弹出调用权限提示对话框,只有手动在设置里面手动打开。这相当于是小米手机的一个bug
, 目前还没有解决 , 只能手动在设置-->应用权限中打开 , 一下子就感觉小米很low了!
正常情况下在代码中调用时先进行权限判断,如果没有权限就去申请权限:
private void requestPermission() { if (Build.VERSION.SDK_INT >= 23) { int checkAccessFinePermission = ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION); if (checkAccessFinePermission != PackageManager.PERMISSION_GRANTED) { ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.ACCESS_FINE_LOCATION}, REQUEST_PERMISSION_ACCESS_LOCATION); Log.d(TAG, "没有权限,请求权限"); return; } Log.d(TAG, "已有定位权限"); } //做下面该做的事 }
调用ActivityCompat.requestPermissions()之后会有一个回调
@Override public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) { switch (requestCode) { case Common.REQUEST_PERMISSION_ACCESS_LOCATION: { if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) { Log.d(TAG, "开启权限permission granted!"); //做下面该做的事 } else { Log.d(TAG, "没有定位权限,请先开启!"); } } } super.onRequestPermissionsResult(requestCode, permissions, grantResults); }
在网上有人说,当弹出权限确认框之后,用户点击确定或者拒绝时才会调用进行回调:onRequestPermissionsResult
但是在小米手机MIUI上并不是这样的。MIUI上是这样的:权限管理那里设置应用的定位权限为拒绝或者询问时checkAccessFinePermission != PackageManager.PERMISSION_GRANTED,说明没有定位权限 。如果设置为允许,checkAccessFinePermission
==PackageManager.PERMISSION_GRANTED,说明有定位权限。
当设置拒绝时去ActivityCompat.requestPermissions ,并没有弹出权限使用确认框,而是直接回调:没有权限
当设置询问时去ActivityCompat.requestPermissions
,并没有弹出权限使用确认框,而是直接回调:已有权限,然后在调用蓝牙代码的时候弹出确认框。当点击允许时权限管理那里变成了允许,当点击拒绝时,权限管理那里变成拒绝,但是下次再进行权限检查时返回 已有定位权限。权限管理那里明明是拒绝的啊,怎么就有定位权限了?这是MIUI的一个bug,我的系统是:MIUI
8 6.11.3开发版。
第二个坑
如何获取已经连接上的或是处于已连接状态的蓝牙设备 ? 这个问题我是通过博客找到的.利用反射的原理实现的.
BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter();
Class<BluetoothAdapter> bluetoothAdapterClass = BluetoothAdapter.class;//得到BluetoothAdapter的Class对象
try {//得到连接状态的方法
Method method = bluetoothAdapterClass.getDeclaredMethod("getConnectionState", (Class[]) null);
//打开权限
method.setAccessible(true);
int state = (int) method.invoke(adapter, (Object[]) null);
if(state == BluetoothAdapter.STATE_CONNECTED){
Log.i("BLUETOOTH","BluetoothAdapter.STATE_CONNECTED");
Set<BluetoothDevice> devices = adapter.getBondedDevices();
Log.i("BLUETOOTH","devices:"+devices.size());
for(BluetoothDevice device : devices){
Method isConnectedMethod = BluetoothDevice.class.getDeclaredMethod("isConnected", (Class[]) null);
method.setAccessible(true);
boolean isConnected = (boolean) isConnectedMethod.invoke(device, (Object[]) null);
if(isConnected){
Log.i("BLUETOOTH","connected:"+device.getName());
deviceList.add(device);
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
参考资料 http://blog.csdn.net/juesai2015/article/details/78737413
蓝牙开发的Demo: 蓝牙开发demo下载
相关文章推荐
- Android 6.0后蓝牙的开发,搜索,配对,连接发送数据等(一)
- Android 蓝牙开发之搜索、配对、连接、通信大全
- Android 蓝牙开发之搜索、配对、连接、通信大全
- Android 蓝牙开发之搜索、配对、连接、通信大全
- [置顶] Android 蓝牙开发之搜索、配对、连接、通信大全
- Android开发蓝牙篇之蓝牙配对、连接与接收数据
- Android 蓝牙设备通讯的开发(配对/连接/传输数据)
- 如何实现android蓝牙开发 自动配对连接,并不弹出提示框
- 如何实现android蓝牙开发 自动配对连接,并不弹出提示框
- android开发之蓝牙初步 扫描已配对蓝牙、更改蓝牙可见性、搜索外部蓝牙设备
- android开发之蓝牙主动配对连接手机
- android开发之蓝牙主动配对连接手机
- android 蓝牙搜索、配对连接通信总结
- 求教Android蓝牙串口开发OutputStream发送数据失败的问题。
- Android蓝牙搜索设备,向其发送数据并接收
- Android开发之蓝牙连接与配对设备
- android开发之蓝牙配对连接的方法
- android bluetooth——蓝牙的开启、搜索、配对与连接
- Android蓝牙设备的配对,连接,搜索
- android开发之蓝牙主动配对连接手机