Android Open Source - twawm2 Bluetooth Helper






From Project

Back to project page twawm2.

License

The source code is released under:

Copyright (c) 2014, afnf All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: * Redistr...

If you think the Android project twawm2 listed in this page is inappropriate, such as containing malicious code/tools or violating the copyright, please email info at java2s dot com, thanks.

Java Source Code

package com.appspot.afnf4199ga.twawm;
//  w  ww  .java 2 s .co m
import java.lang.reflect.Method;
import java.util.Locale;

import net.afnf.and.twawm2.R;
import android.annotation.SuppressLint;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.Build;

import com.appspot.afnf4199ga.twawm.TwawmUtils.BT_RESUME_TYPE;
import com.appspot.afnf4199ga.twawm.app.BackgroundService;
import com.appspot.afnf4199ga.twawm.app.MainActivity;
import com.appspot.afnf4199ga.twawm.app.MainActivity.ACTIVITY_FLAG;
import com.appspot.afnf4199ga.twawm.app.UIAct;
import com.appspot.afnf4199ga.utils.AndroidUtils;
import com.appspot.afnf4199ga.utils.Logger;
import com.appspot.afnf4199ga.utils.MyStringUtlis;

public class BluetoothHelper {

    protected BackgroundService service;
    protected BluetoothAdapter bt = null;
    protected String bluetoothAddress = null;
    protected BluetoothDevice remoteDevice = null;
    protected boolean btAlreadyEnabled = false;
    protected boolean success = false;
    protected boolean executing = false;
    protected BluetoothSocket bluetoothSocket = null;
    protected BroadcastReceiver discoveryBcastReceiver = null;
    protected boolean discovering = false;

    public BluetoothHelper(BackgroundService service) {
        this.service = service;

        bluetoothAddress = Const.getPrefBluetoothAddress(service);
        btAlreadyEnabled = false;
        success = false;
        executing = true;
        bt = BluetoothAdapter.getDefaultAdapter();
    }

    public void disable() {
        if (isValidState() == false) {
            return;
        }

        if (bt.isEnabled()) {
            btAlreadyEnabled = true;

            // ?????
            Logger.i("Bluetooth enabled, disabling");
            bt.disable();
        }
        else {
            Logger.i("Bluetooth originally disabled");
            service.onBluetoothDisabled();
        }
    }

    public void enable() {
        if (isValidState() == false) {
            return;
        }

        if (bt.isEnabled()) {
            // Bluetooth??????????????????
            if (Const.isPrefBtRestartType(service) == false) {
                btAlreadyEnabled = true;
                Logger.i("Bluetooth originally enabled");
            }
            else {
                Logger.w("Bluetooth disabling failed?");
            }
            service.onBluetoothEnabled();
        }
        else {
            // Bluetooth??????????????????
            if (Const.isPrefBtRestartType(service) == false) {
                // BT????UI?????????????????????????????
                Logger.i("Bluetooth enabling");
                bt.enable();
            }
            else {
                // Bluetooth????????
                Logger.i("Bluetooth enabling manually");
                MainActivity.startActivity(service, ACTIVITY_FLAG.BT_ENABLING);
            }
        }
    }

    public void connect() {
        if (isValidState() == false) {
            return;
        }

        if (bt.isEnabled() == false) {
            Logger.w("Bluetooth enabling failed?");
            service.onBluetoothConnected(false);
            return;
        }

        // BT??
        startDiscoveringAndConnectingByThread();
    }

    protected void startDiscoveringAndConnectingByThread() {
        new Thread(new Runnable() {
            @Override
            public void run() {
                startDiscoveringAndConnecting();
            }
        }).start();
    }

    protected void startDiscoveringAndConnecting() {
        if (isValidState() == false) {
            return;
        }

        BackgroundService service = BackgroundService.getInstance();

        // Discovery????????????????
        if (Const.isPrefBtDiscoveringType(service) == false) {
            startConnecting();
        }

        // Discovery???????????
        else {
            // broadcastReceiver??
            discoveryBcastReceiver = new BroadcastReceiver() {
                @Override
                public void onReceive(final Context context, final Intent intent) {
                    // ??
                    if (AndroidUtils.isActionEquals(intent, BluetoothDevice.ACTION_FOUND)) {
                        try {
                            BluetoothDevice foundDevice = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
                            if (foundDevice != null) {
                                // ???????????????????
                                String addr = foundDevice.getAddress();
                                if (MyStringUtlis.isEmpty(addr) == false
                                        && MyStringUtlis.eqauls(addr.toUpperCase(Locale.US), bluetoothAddress)) {
                                    Logger.i("Bluetooth device found, discovery canceled");
                                    // ????????????
                                    remoteDevice = foundDevice;
                                    discovering = false;
                                    bt.cancelDiscovery();
                                    startConnectingByThread();
                                }
                            }
                        }
                        catch (Throwable e) {
                            Logger.w("Bluetooth BluetoothDevice.ACTION_FOUND failed", e);
                        }
                    }
                    // ??
                    else if (AndroidUtils.isActionEquals(intent, BluetoothAdapter.ACTION_DISCOVERY_FINISHED)) {
                        Logger.i("Bluetooth discovery finished");
                        if (discovering) {
                            discovering = false;
                            startConnectingByThread();
                        }
                    }
                }
            };

            // broadcastReceiver??
            IntentFilter filter = new IntentFilter();
            filter.addAction(BluetoothDevice.ACTION_FOUND);
            filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_FINISHED);
            service.registerReceiver(discoveryBcastReceiver, filter);

            // Discovery??
            try {
                bt.cancelDiscovery();
                discovering = bt.startDiscovery();
                if (discovering == false) {
                    Logger.w("Bluetooth startDiscovery failed");
                    startConnecting();
                }
            }
            catch (Throwable e) {
                Logger.w("Bluetooth startDiscovery failed, e=" + e.toString());
                startConnecting();
            }
        }
    }

    protected void startConnectingByThread() {
        new Thread(new Runnable() {
            @Override
            public void run() {
                startConnecting();
            }
        }).start();
    }

    @SuppressLint({ "DefaultLocale", "NewApi" })
    protected void startConnecting() {
        if (isValidState() == false) {
            return;
        }

        BackgroundService service = BackgroundService.getInstance();

        if (discoveryBcastReceiver != null) {
            try {
                service.unregisterReceiver(discoveryBcastReceiver);
                discoveryBcastReceiver = null;
            }
            catch (Throwable e) {
            }
        }

        // ????????
        BT_RESUME_TYPE btResumeType = Const.getPrefBtResumeType(service);
        int retry = TwawmUtils.getBtRetryCount(btResumeType);
        Logger.i("Bluetooth startConnecting, type=" + btResumeType.name() + ", retry=" + retry);

        for (int i = 0; i < retry; i++) {
            Logger.i("tring=" + i);

            try {
                // ?????????????remoteDevice????
                if (remoteDevice == null) {
                    remoteDevice = bt.getRemoteDevice(bluetoothAddress);
                }

                // ??????SSP
                if (i == 0) {
                    bluetoothSocket = remoteDevice.createRfcommSocketToServiceRecord(Const.BLUETOOTH_UUID);
                }

                // 2?????SDP lookup??????????????????
                else if (i == 1) {

                    // bluetoothSocket??????????????????????
                    int channel = 0;
                    try {
                        Method m = remoteDevice.getClass().getMethod("createRfcommSocket", new Class[] { int.class });
                        while (bluetoothSocket == null && channel < 10) {
                            bluetoothSocket = (BluetoothSocket) m.invoke(remoteDevice, ++channel);
                        }
                    }
                    catch (Throwable e) {
                        Logger.i(" error=" + e.toString());
                    }

                    if (bluetoothSocket != null) {
                        Logger.i(" channel=" + channel);
                    }
                    // ??????????????SSP?????
                    else {
                        Logger.i(" using SSP");
                        bluetoothSocket = remoteDevice.createRfcommSocketToServiceRecord(Const.BLUETOOTH_UUID);
                    }
                }

                // 3?????insecure
                else if (i == 2) {

                    // createInsecureRfcommSocketToServiceRecord???API10????
                    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.GINGERBREAD_MR1) {
                        bluetoothSocket = remoteDevice.createInsecureRfcommSocketToServiceRecord(Const.BLUETOOTH_UUID);
                    }
                    // API9??????createInsecureRfcommSocket?????
                    else {
                        // bluetoothSocket??????????????????????
                        Method m = remoteDevice.getClass().getMethod("createInsecureRfcommSocket", new Class[] { int.class });
                        int channel = 0;
                        while (bluetoothSocket == null && channel < 30) {
                            bluetoothSocket = (BluetoothSocket) m.invoke(remoteDevice, ++channel);
                        }
                        Logger.i(" channel=" + channel);
                    }
                }

                // ???????????????????????????????
                if (bluetoothSocket == null) {
                    Logger.w(" bluetoothSocket is null, continue");
                    continue;
                }
            }
            catch (Throwable e1) {
                Logger.w(" bluetoothSocket creation failed, e=" + e1.toString());
                // ????
                continue;
            }

            ClosingThread closingThread = new ClosingThread();
            try {

                // Discovery??
                // isDiscovering????????????????????(http://developer.android.com/intl/ja/guide/topics/connectivity/bluetooth.html)
                bt.cancelDiscovery();

                // ??????????
                closingThread.start();

                // ????
                bluetoothSocket.connect();

                Logger.i(" pairing succeeded, continue");
            }
            catch (Throwable e) {
                // unable to start??????
                String exception = e.toString().toLowerCase();
                if (exception.indexOf("unable to start service discovery") != -1) {
                    UIAct.toast(service.getString(R.string.bt_error_need_to_reboot));
                }
                Logger.i(" resume complete?, e=" + exception);
            }
            finally {
                try {
                    closingThread.interrupt();
                    synchronized (BluetoothHelper.class) {
                        if (bluetoothSocket != null) {
                            Logger.i(" closing bluetoothSocket on finally");
                            bluetoothSocket.close();
                            bluetoothSocket = null;
                        }
                    }
                }
                catch (Throwable e2) {
                    Logger.w(" finalize error", e2);
                }
            }
        }

        // ??????
        try {

            // ????????????????????????????????????????????
            success = true;

            long beforeDisabling = System.currentTimeMillis();

            // ???????????????
            service.onBluetoothConnectedBeforeDisabling();

            // ?????????????????????????
            if (btAlreadyEnabled) {
                Logger.i("Bluetooth keep enabled");
            }
            // ???
            else {
                // BT???
                Logger.i("Bluetooth disabling");
                bt.disable();
            }

            // NAD11????????????????
            long afterDisabling = System.currentTimeMillis();
            long diff = afterDisabling - beforeDisabling;
            long wait = Const.getPrefWaitAfterResumeMs(service);
            final long delay = Const.NOTIFY_DELAY_AFTER_BT_DISABLING + Math.max(0, wait - diff);

            // ???????????
            new Thread(new Runnable() {
                @Override
                public void run() {

                    // ????
                    AndroidUtils.sleep(delay);

                    // ????????
                    BackgroundService service = BackgroundService.getInstance();
                    if (service == null) {
                        Logger.e("service is null on BluetoothHelper.startConnecting().callback");
                        return;
                    }

                    // ???????
                    service.onBluetoothConnected(success);
                }
            }).start();
        }
        catch (Throwable e) {
            Logger.w("Bluetooth connecting failed", e);
        }
    }

    protected class ClosingThread extends Thread {
        public void run() {
            try {
                Thread.sleep(Const.getPrefBtConnectionTimeoutMs(service));

                synchronized (BluetoothHelper.class) {
                    if (bluetoothSocket != null) {
                        try {
                            Logger.i(" closing bluetoothSocket from thread");
                            // API?????????connect???? : "close() can be used to abort this call from another thread."
                            bluetoothSocket.close();
                            bluetoothSocket = null;
                        }
                        catch (Throwable e) {
                        }
                    }
                }
            }
            catch (InterruptedException t) {
                // interrupt?????????????
            }
        }
    }

    public void finish() {
        executing = false;

        if (btAlreadyEnabled == false) {
            BackgroundService service = BackgroundService.getInstance();
            if (service == null) {
                Logger.e("service is null on BluetoothHelper.finish");
                return;
            }
            // broadcastReceiver??
            if (discoveryBcastReceiver != null) {
                service.unregisterReceiver(discoveryBcastReceiver);
                discoveryBcastReceiver = null;
            }
        }
    }

    private boolean isValidState() {

        BackgroundService service = BackgroundService.getInstance();
        if (service == null) {
            Logger.e("service is null on BluetoothHelper");
            return false;
        }

        if (bt == null) {
            Logger.e("Bluetooth unnavigable");
            service.onBluetoothConnected(false);
            return false;
        }

        if (executing == false) {
            Logger.e("executing is false on BluetoothHelper");
            return false;
        }

        return true;
    }

    public static boolean isValidBluetoothAddress(String address) {
        if (MyStringUtlis.isEmpty(address) == false) {
            address = address.toUpperCase(Locale.US);
            if (BluetoothAdapter.checkBluetoothAddress(address)) {
                return true;
            }
        }
        return false;
    }
}




Java Source Code List

com.appspot.afnf4199ga.twawm.BluetoothHelper.java
com.appspot.afnf4199ga.twawm.Const.java
com.appspot.afnf4199ga.twawm.Const.java
com.appspot.afnf4199ga.twawm.HostnameListTest.java
com.appspot.afnf4199ga.twawm.HostnameList.java
com.appspot.afnf4199ga.twawm.IconSelectorTest.java
com.appspot.afnf4199ga.twawm.IconSelector.java
com.appspot.afnf4199ga.twawm.OnlineChecker.java
com.appspot.afnf4199ga.twawm.StateMachineTest.java
com.appspot.afnf4199ga.twawm.StateMachine.java
com.appspot.afnf4199ga.twawm.TwawmUtils.java
com.appspot.afnf4199ga.twawm.app.BackgroundServiceTest.java
com.appspot.afnf4199ga.twawm.app.BackgroundService.java
com.appspot.afnf4199ga.twawm.app.DefaultWidgetProvider.java
com.appspot.afnf4199ga.twawm.app.InfoActivity.java
com.appspot.afnf4199ga.twawm.app.InitialConfigurationWizardActivity.java
com.appspot.afnf4199ga.twawm.app.LogSendActivity.java
com.appspot.afnf4199ga.twawm.app.MainActivity.java
com.appspot.afnf4199ga.twawm.app.MainApp.java
com.appspot.afnf4199ga.twawm.app.MyPreferenceActivity.java
com.appspot.afnf4199ga.twawm.app.NetworkSwitcher.java
com.appspot.afnf4199ga.twawm.app.StaticIntentListener.java
com.appspot.afnf4199ga.twawm.app.UIAct.java
com.appspot.afnf4199ga.twawm.ctl.CustomizeActionsActivityTest.java
com.appspot.afnf4199ga.twawm.ctl.CustomizeActionsActivity.java
com.appspot.afnf4199ga.twawm.ctl.CwacTouchListView.java
com.appspot.afnf4199ga.twawm.ctl.ListItem.java
com.appspot.afnf4199ga.twawm.router.EcoModeControlTest.java
com.appspot.afnf4199ga.twawm.router.EcoModeControl.java
com.appspot.afnf4199ga.twawm.router.InetLookupWrappter.java
com.appspot.afnf4199ga.twawm.router.InetLookupWrappter.java
com.appspot.afnf4199ga.twawm.router.MyHttpClientTest.java
com.appspot.afnf4199ga.twawm.router.MyHttpClient.java
com.appspot.afnf4199ga.twawm.router.MyHttpClient.java
com.appspot.afnf4199ga.twawm.router.RouterControlByHttpTest.java
com.appspot.afnf4199ga.twawm.router.RouterControlByHttp.java
com.appspot.afnf4199ga.twawm.router.RouterControlByHttp.java
com.appspot.afnf4199ga.twawm.router.RouterControl.java
com.appspot.afnf4199ga.twawm.router.RouterControl.java
com.appspot.afnf4199ga.twawm.router.RouterInfo.java
com.appspot.afnf4199ga.twawm.router.RouterInfo.java
com.appspot.afnf4199ga.utils.AndroidUtilsTest.java
com.appspot.afnf4199ga.utils.AndroidUtils.java
com.appspot.afnf4199ga.utils.AndroidUtils.java
com.appspot.afnf4199ga.utils.Logger.java
com.appspot.afnf4199ga.utils.Logger.java
com.appspot.afnf4199ga.utils.MyStringUtlisTest.java
com.appspot.afnf4199ga.utils.MyStringUtlis.java
com.appspot.afnf4199ga.utils.MyStringUtlis.java
com.appspot.afnf4199ga.utils.MyTestUtils.java
com.appspot.afnf4199ga.utils.MyUncaughtExceptionHandler.java
com.appspot.afnf4199ga.utils.MyUncaughtExceptionHandler.java
com.appspot.afnf4199ga.wmgraph.app.FetchThread.java
com.appspot.afnf4199ga.wmgraph.app.InetLookupThread.java
com.appspot.afnf4199ga.wmgraph.app.InfoActivity.java
com.appspot.afnf4199ga.wmgraph.app.MainActivity.java
com.appspot.afnf4199ga.wmgraph.app.MyPreferenceActivity.java
com.appspot.afnf4199ga.wmgraph.app.UIAct.java
net.afnf.and.twawm2.DexmakerInstrumentationTestCase.java
net.afnf.and.twawm2.MyInstrumentationTestRunner.java