我的手机正在连接到蓝牙设备,并且可以正常工作。它连接并保持连接。我可以更改方向,在后台运行我的应用程序,可以关闭应用程序,当我重新打开它时,它将自动连接。但是从应用程序用户那里,我得到一些报告,指出一段时间后连接丢失(未检测到任何模式)。我试图重新创建它,但是没有运气。因此,为避免此问题,如果连接断开,我想实现与先前选择的设备的自动重新连接。
我做了一些研究,可以通过实现一个可以检测到以下内容的广播接收器来做到这一点: android.bluetooth.device.action.ACL_DISCONNECTED
我的问题是:
感谢您的回答。
蓝牙服务代码:
public class BluetoothService
{
// Debugging
private static final String TAG = "BluetoothService";
private static final UUID MY_UUID = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");
// Member fields
private final BluetoothAdapter mAdapter;
private final Handler mHandler;
private final Context mContext;
private ConnectThread mConnectThread;
private ConnectedThread mConnectedThread;
private int mState;
// Constants that indicate the current connection state
public static final int STATE_NONE = 0; // we're doing nothing
public static final int STATE_CONNECTING = 1; // now initiating an outgoing connection
public static final int STATE_CONNECTED = 2; // now connected to a remote device
public BluetoothService(Context context, Handler handler)
{
mAdapter = BluetoothAdapter.getDefaultAdapter();
mState = STATE_NONE;
mHandler = handler;
mContext = context;
}
private synchronized void setState(int state)
{
mState = state;
mHandler.obtainMessage(MainActivity.MESSAGE_STATE_CHANGE, state, -1).sendToTarget();
}
public synchronized int getState()
{
return mState;
}
public synchronized void start()
{
if (mConnectThread != null)
{
mConnectThread.cancel();
mConnectThread = null;
}
if (mConnectedThread != null)
{
mConnectedThread.cancel();
mConnectedThread = null;
}
}
public synchronized void connect(BluetoothDevice device)
{
if (mState == STATE_CONNECTING)
{
if (mConnectThread != null)
{
mConnectThread.cancel();
mConnectThread = null;
}
}
if (mConnectedThread != null)
{
mConnectedThread.cancel();
mConnectedThread = null;
}
mConnectThread = new ConnectThread(device);
mConnectThread.start();
setState(STATE_CONNECTING);
}
public synchronized void connected(BluetoothSocket socket, BluetoothDevice device, final String socketType)
{
if (mConnectThread != null)
{
mConnectThread.cancel();
mConnectThread = null;
}
if (mConnectedThread != null)
{
mConnectedThread.cancel();
mConnectedThread = null;
}
mConnectedThread = new ConnectedThread(socket, socketType);
mConnectedThread.start();
Message msg = mHandler.obtainMessage(MainActivity.MESSAGE_DEVICE_NAME);
Bundle bundle = new Bundle();
bundle.putString(MainActivity.DEVICE_NAME, device.getName());
msg.setData(bundle);
mHandler.sendMessage(msg);
setState(STATE_CONNECTED);
}
public synchronized void stop()
{
if (mConnectThread != null)
{
mConnectThread.cancel();
mConnectThread = null;
}
if (mConnectedThread != null)
{
mConnectedThread.cancel();
mConnectedThread = null;
}
setState(STATE_NONE);
}
public void write(byte[] out)
{
ConnectedThread r;
synchronized (this)
{
if (mState != STATE_CONNECTED) return;
r = mConnectedThread;
}
r.write(out);
}
private void connectionFailed()
{
Message msg = mHandler.obtainMessage(MainActivity.MESSAGE_TOAST);
Bundle bundle = new Bundle();
bundle.putString(MainActivity.TOAST, mContext.getResources().getString(R.string.cant_connect));
msg.setData(bundle);
mHandler.sendMessage(msg);
BluetoothService.this.start();
}
private class ConnectThread extends Thread
{
private final BluetoothSocket mmSocket;
private final BluetoothDevice mmDevice;
private String mSocketType;
public ConnectThread(BluetoothDevice device)
{
mmDevice = device;
BluetoothSocket tmp = null;
mSocketType = "Secure";
// another option createInsecureRfcommSocketToServiceRecord
try
{
tmp = device.createRfcommSocketToServiceRecord(MY_UUID);
}
catch (IOException e)
{
Log.e(TAG, "Socket Type: " + mSocketType + "create() failed", e);
}
/*
Method m = null;
try {
m = mmDevice.getClass().getMethod("createRfcommSocket", new Class[] {int.class});
tmp = (BluetoothSocket) m.invoke(mmDevice, 1);
} catch (Exception e) {
e.printStackTrace();
}*/
mmSocket = tmp;
}
public void run()
{
Log.i(TAG, "BEGIN mConnectThread SocketType:" + mSocketType);
setName("ConnectThread" + mSocketType);
mAdapter.cancelDiscovery();
try
{
mmSocket.connect();
Log.i(TAG, "ConnectThread running");
}
catch (IOException e)
{
try
{
mmSocket.close();
}
catch (IOException e2)
{
Log.e(TAG, "unable to close() " + mSocketType + " socket during connection failure", e2);
}
connectionFailed();
return;
}
synchronized (BluetoothService.this)
{
mConnectThread = null;
}
connected(mmSocket, mmDevice, mSocketType);
}
public void cancel()
{
try
{
mmSocket.close();
}
catch (IOException e)
{
Log.e(TAG, "close() of connect " + mSocketType + " socket failed", e);
}
}
}
private class ConnectedThread extends Thread
{
private final BluetoothSocket mmSocket;
private final OutputStream mmOutStream;
public ConnectedThread(BluetoothSocket socket, String socketType)
{
mmSocket = socket;
OutputStream tmpOut = null;
try
{
tmpOut = socket.getOutputStream();
}
catch (IOException e)
{
Log.e(TAG, "temp sockets not created", e);
}
mmOutStream = tmpOut;
}
public void run()
{
}
public void write(byte[] buffer)
{
try
{
mmOutStream.write(buffer);
try
{
sleep(2000);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
}
catch (IOException e)
{
Log.e(TAG, "Exception during write", e);
}
}
public void cancel()
{
try
{
mmSocket.close();
}
catch (IOException e)
{
Log.e(TAG, "close() of connect socket failed", e);
}
}
}
}
我分两个阶段解决了这个问题。首先,我创建了一个新的广播接收器,因为我现有的接收器用于ACTION_BOOT_COMPLETED,并且必须在android清单中声明。我创建的一个必须动态,因为我需要一个MainActivity实例:
if (bluetoothLostReceiver == null)
{
bluetoothLostReceiver = new BluetoothLostReceiver();
bluetoothLostReceiver.setMainActivity(this);
IntentFilter filter = new IntentFilter("android.bluetooth.device.action.ACL_DISCONNECTED");
registerReceiver(bluetoothLostReceiver, filter);
}
在接收者中,我尝试了与打印机的新连接。我添加了一个附加的paramenter tryBluetoothReconnect,这样,如果我想关闭连接,则不会尝试重新连接。
public class BluetoothLostReceiver extends BroadcastReceiver {
MainActivity main = null;
public void setMainActivity(MainActivity main)
{
this.main = main;
}
@Override
public void onReceive(Context context, Intent intent) {
if(BluetoothDevice.ACTION_ACL_DISCONNECTED.equals(intent.getAction()) && Global.tryBluetoothReconnect)
{
if(Global.PosPrinterDeviceName != null && !Global.PosPrinterDeviceName.equals(""))
main.connectPrinter(Global.PosPrinterDeviceName);
}else
{
Global.tryBluetoothReconnect = true;
}
}
}
我还升级了我的蓝牙服务,以便如果连接不成功(connectionFailed()方法),它将再尝试4次:
if(tryCount >= 4)
{
tryCount = 0;
Message msg = mHandler.obtainMessage(MainActivity.MESSAGE_TOAST);
Bundle bundle = new Bundle();
bundle.putString(MainActivity.TOAST, mContext.getResources().getString(R.string.cant_connect));
msg.setData(bundle);
mHandler.sendMessage(msg);
BluetoothService.this.start();
}
else
{
tryCount++;
connect(bluetoothDevice);
}
希望这对遇到同样问题的人有所帮助。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句