java android开发,小计一个断开BLE连接的方式

本文深入解析了Android蓝牙Gatt连接的断开与资源释放方法,包括BluetoothGatt.disconnect()和BluetoothGatt.close()的源码分析,以及如何优雅地处理连接断开,避免空指针异常。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、断开连接的调用方法

  • android.bluetooth.BluetoothGatt.disconnect()  断开连接
  • android.bluetooth.BluetoothGatt.close()  释放连接资源

二、源码分析

  • android.bluetooth.BluetoothGatt.disconnect()的源码分析
private IBluetoothGatt mService;//对象中的属性

BluetoothGatt(Context context, IBluetoothGatt iGatt, BluetoothDevice device,
                                int transport) {
        mContext = context;
        mService = iGatt; //创建对象的时候,将gatt对象赋值给mService
        mDevice = device;
        mTransport = transport;
        mServices = new ArrayList<BluetoothGattService>();

        mConnState = CONN_STATE_IDLE;
}

public void disconnect() {
        if (DBG) Log.d(TAG, "cancelOpen() - device: " + mDevice.getAddress());
        if (mService == null || mClientIf == 0) return;

        try {
            mService.clientDisconnect(mClientIf, mDevice.getAddress());
        } catch (RemoteException e) {
            Log.e(TAG,"",e);
        }
}
  • android.bluetooth.BluetoothGatt.close()的源码分析
public void close() {
        if (DBG) Log.d(TAG, "close()");

        unregisterApp();
        mConnState = CONN_STATE_CLOSED;
}

private void unregisterApp() {
        if (DBG) Log.d(TAG, "unregisterApp() - mClientIf=" + mClientIf);
        if (mService == null || mClientIf == 0) return;

        try {
            mCallback = null;
            mService.unregisterClient(mClientIf);
            mClientIf = 0;
        } catch (RemoteException e) {
            Log.e(TAG,"",e);
        }
}

三、断开连接小计

  • 网上看到的大部分处理方式

监听页面的生命周期,再页面需要执行销毁处理,判断gatt连接对象是否存在,如果存在,则同时调用上述的两种方式进行关闭连接操作处理。

但这样处理有个问题:

看上述的两段源码,close其实算得上是将callback置空处理,有点类似GC机制,如果同时使用,则在disconnect操作后,会触发android.bluetooth.BluetoothGattCallback().onConnectionStateChange(BluetoothGatt, int, int)的处理监听(这个是异步的,毕竟蓝牙底层处理需要时间),如果在调用disconnect后直接调用close(),将百分百出现空指针问题,切断开操作不够优雅!

  • 自己的处理方式

检测连接是否真正的断开,函数封装

public int getConnectedState() {
		int state = 100;
		if (lock_bluetoothManager != null && (lock_mac != null | lock_mac == "") && mBluetoothAdapter != null
				&& mBluetoothAdapter.isEnabled()) {
			BluetoothDevice bdevice = mBluetoothAdapter.getRemoteDevice(lock_mac);
			// 蓝牙连接状态为0,1,2,3 为了避免出问题初始化为100
			/**
			 * STATE_DISCONNECTED 0 STATE_CONNECTING 1 STATE_CONNECTED 2 STATE_DISCONNECTING
			 * 3
			 */
			state = lock_bluetoothManager.getConnectionState(bdevice, BluetoothProfile.GATT);
		}
		Log.i("getConnectedState()方法调用,返回数据为-->", String.valueOf(state));
		return state;
	}

具体断开操作思路: 

  1. 在需要断开连接的地方,调用  mBluetoothGatt.disconnect(); 进行尝试断开处理操作;
  2. 等待 onConnectionStateChange(BluetoothGatt, int, int) 状态监听函数的触发;
  3. 为了避免信号的变化导致的连接不稳定,需要对连接失败做一个处理,getConntectState();
  4. 在连接状态回调处,进行判断
  5. if (newState == BluetoothProfile.STATE_DISCONNECTED) {// 连接失败 或者连接断开都会调用此方法
    				Log.i("连接回调-->", "getConnectedState()");
    				if (getConnectedState() == BluetoothProfile.STATE_CONNECTED) {
    					Log.i("onConnectionStateChange-->", "连接伪失败");
    					return;
    				}
    				Log.i("onConnectionStateChange-->", "连接失败");
    				Message message = new Message();
    				message.what = CONNECT_FAIL;
    				AppSendMesg(message);
    }

    在CONNECT_FAIL中实现处理(此时的状态是真正的断开了连接了),此时需要对连接对象进行资源释放操作

  6. if(mBluetoothGatt != null) {
    	//释放资源
    	mBluetoothGatt.close();
    }

     

  7.  

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值