关于监听蓝牙断开的问题

努力de俺 发布于 2014/07/03 16:18
阅读 7K+
收藏 0

我有一个设备和手机蓝牙连接,它们的连接方式是通过手机的APP,但是当设备关机以后,由于数据已经不透传了,怎么在手机的APP其中一个界面上给一个提示例如:蓝牙已断开的提示。怎么调用?我是菜鸟希望大神详细解释一下。

BluetoothService.java文件

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.UUID;


import com.dvb.detector.constant.Constant;
import com.dvb.detector.util.StringUtil;
import com.dvb.detector.activity.DeviceConnectActivity;


import android.app.Service;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log;
import android.widget.Toast;
/**
 * 
 *蓝牙服务
 */
public class BluetoothService extends Service {
    private static final String NAME_SECURE = "BluetoothSecure";


    private static final UUID MY_UUID_SECURE = UUID
            .fromString("00001101-0000-1000-8000-00805F9B34FB");


    private BluetoothAdapter mAdapter;
    /**
     * 正在连接的线程,连接成功以后切至ConnectedThread
     */
    private ConnectThread mConnectThread;
    /**
     * 用于连接后的读写操作线程
     */
    private ConnectedThread mConnectedThread;
    /**
     * 当前连接的状态值,分别为以下三个状态值
     */
    private int mState;


    // 当前连接状态
    /**
     * 无连接
     */
    public static final int STATE_NONE = 0;
    /**
     * 正在连接
     */
    public static final int STATE_CONNECTING = 2;
    /**
     * 连接成功
     */
    public static final int STATE_CONNECTED = 3;
    
    private final IBinder binder = new BluetoothBinder();
    /**
     * 单片机mac地址
     */
    private String address;
    /**
     * 重连次数设定
     */
    private int reConnectCount;
    /**
     * 最大重连次数
     */
    private static final int MAX_RECONNECT_TIMES = 2;


    public class BluetoothBinder extends Binder {
        public BluetoothService getService() {
            return BluetoothService.this;
        }
    }


    @Override
    public IBinder onBind(Intent intent) {
        return binder;
    }


    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        mAdapter = BluetoothAdapter.getDefaultAdapter();
        connectDevice(intent);
        mState = STATE_NONE;
        return START_REDELIVER_INTENT;
    }


    /**
     * 连接机器
     * 
     * @param data
     */
    private void connectDevice(Intent data) {
        address = data.getStringExtra("MAC");
        // 根据Mac地址获取device
        BluetoothDevice device = mAdapter.getRemoteDevice(address);
        // 尝试连接该机器
        connect(device);
    }
    /**
     * 发起重连
     */
    private void reConnectDevice() {
    /**
    * 最大重连次数之内直接重连,否则跳回至设备选择界面
    */
        if (reConnectCount <= MAX_RECONNECT_TIMES) {
//            Toast.makeText(this, "正在进行蓝牙重连", Toast.LENGTH_LONG).show();
            // 根据Mac地址获取device
            BluetoothDevice device = mAdapter.getRemoteDevice(address);
            // 尝试连接该机器
            connect(device);
            reConnectCount++;
        } else {
            Intent intent = new Intent(this, DeviceConnectActivity.class);
            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
            intent.putExtra("flag", 1);
          /*  startActivity(intent);*/
        }
    }


    /**
     * 和机器连接
     */
    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) {
        if (mConnectThread != null) {
            mConnectThread.cancel();
            mConnectThread = null;
        }


        if (mConnectedThread != null) {
            mConnectedThread.cancel();
            mConnectedThread = null;
        }
        // 开启连接对话管理线程
        mConnectedThread = new ConnectedThread(socket);
        mConnectedThread.start();
        reConnectCount = 0;
        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() {
        BluetoothService.this.reConnectDevice();
        Toast.makeText(this,"蓝牙断开正在重新连接", Toast.LENGTH_LONG).show();
    }


    /**
     * 连接丢失
     */
    private void connectionLost() {
        BluetoothService.this.reConnectDevice();
    }


    private synchronized void setState(int state) {
        Log.i("xth", "state = " + state);
        mState = state;
    }


    public synchronized int getState() {
        return mState;
    }


    /**
     * 连接线程
     */
    private class ConnectThread extends Thread {
        private final BluetoothSocket mmSocket;


        private final BluetoothDevice mmDevice;


        public ConnectThread(BluetoothDevice device) {
            mmDevice = device;
            BluetoothSocket tmp = null;
            try {
                tmp = device.createRfcommSocketToServiceRecord(MY_UUID_SECURE);
            } catch (IOException e) {
            }
            mmSocket = tmp;
        }


        public void run() {
            // 连接前把耗费资源的搜索功能关闭
            mAdapter.cancelDiscovery();


            try {
                mmSocket.connect();
            } catch (IOException e) {
                try {
                    mmSocket.close();
                } catch (IOException e2) {
                }
                connectionFailed();
                return;
            }


            // 完成连接,重置连接线程
            synchronized (BluetoothService.this) {
                mConnectThread = null;
            }


            connected(mmSocket, mmDevice);
        }


        public void cancel() {
            try {
                mmSocket.close();
            } catch (IOException e) {
            }
        }
    }


    /**
     * 已完成配对,处理所有读写消息
     */
    private class ConnectedThread extends Thread {
        private final BluetoothSocket mmSocket;


        private final InputStream mmInStream;


        private final OutputStream mmOutStream;


        public ConnectedThread(BluetoothSocket socket) {
            mmSocket = socket;
            InputStream tmpIn = null;
            OutputStream tmpOut = null;


            try {
                tmpIn = socket.getInputStream();
                tmpOut = socket.getOutputStream();
            } catch (IOException e) {
            }


            mmInStream = tmpIn;
            mmOutStream = tmpOut;
        }


        public void run() {
            byte[] buffer = new byte[Constant.BYTES];
            int bytes;


            byte[] result = new byte[Constant.BYTES];
            int resultLenth = 0;
            // 持续监听是否收到消息
            while (true) {
                try {
                //每次接收到20个字节则转换成本地数据结构FPItem存储
                    bytes = mmInStream.read(buffer);
                    if (resultLenth < Constant.BYTES && bytes + resultLenth <= Constant.BYTES) {
                        System.arraycopy(buffer, 0, result, resultLenth, bytes);
                        resultLenth += bytes;
                    }


                    if (resultLenth >= Constant.BYTES) {
                        resultLenth = 0;
                        StringUtil.list.add(result);
                    }
                } catch (Exception e) {
                    connectionLost();
                    break;
                }
            }
        }


        /**
         * 写数据,向单片机输出数据
         */
        public void write(byte[] buffer) {
            try {
                mmOutStream.write(buffer);
            } catch (IOException e) {
            }
        }


        public void cancel() {
            try {
                mmSocket.close();
            } catch (IOException e) {
            }
        }
    }
}

DeviceConnectThread.java文件

import android.app.Activity;
import android.os.Handler;
import android.os.Message;
import android.util.Log;


import com.dvb.detector.constant.Constant;
import com.dvb.detector.service.BluetoothService;
import com.dvb.detector.util.StringUtil;
/**
 * 设备连接线程,向单片机发起连接请求 
 * 我方发送474消息,当接收到单片机返回的“lock=3”消息,表明连接成功
 *
 */
public class DeviceConnectThread extends Thread {


private Handler handler;


private BluetoothService bluetoothService;


private int readCount;


private boolean stop;


public DeviceConnectThread(Activity activity, Handler handler, BluetoothService bluetoothService) {
this.handler = handler;
this.bluetoothService = bluetoothService;
}


@Override
public void run() {
for (int i = 0; i < Constant.DEVICE_ACTIVITY_LIMIT; i++) {
bluetoothService.write(StringUtil.getSendData("474"));
readCount = 0;
Log.i("xth","Wait write ");
while (readCount <= Constant.DEVICE_ACTIVITY_EACH_LIMIT) {
while (!StringUtil.list.isEmpty()) {
Log.i("xth","notEmpty");
Message msg = handler.obtainMessage();
msg.obj = StringUtil.list.poll();
msg.what = Constant.CONNECT;
handler.sendMessage(msg);
readCount = Constant.DEVICE_ACTIVITY_EACH_LIMIT + 1;
}
try {
sleep(Constant.DEVICE_ACTIVITY_SLEEP_TIME);
} catch (InterruptedException e) {
e.printStackTrace();
}
if (readCount++ > Constant.DEVICE_ACTIVITY_EACH_LIMIT) {
return;
}
}
}


if (!stop) {
Message msg1 = handler.obtainMessage();
msg1.what = Constant.CONNECT_FAIL;
handler.sendMessage(msg1);
}
}


public void cancel() {
stop = true;
}
}

如有高手知道 应该在别的界面怎么调用里面的方法??

加载中
0
oldfeel
oldfeel
蓝牙是通过socket连接的,socket断开时会报异常,可以在异常处理的时候发送一个广播,更新ui.
返回顶部
顶部