Android bluetooth: список сопряженных устройств

У меня есть устройство bluetooth с профилем SPP и bluetooth версии 2.1.
У меня есть приложение, которое подключается к этому устройству и общается с ним. Устройство использует технику сопряжения "просто работает".

Я сталкиваюсь с проблемой на некоторых телефонах, таких как Samsung Galaxy tablet, Galaxy S.

проблема заключается в том, что после выхода пользователя из приложения я закрываю сокеты и отключаюсь от устройства. После успешного разъединения, замечено что прибор запись удаляется из списка сопряженных устройств.

3 ответов


Я не работал с планшетами, но я написал приложение, которое использовало SPP для телефонов Android. Я обнаружил, что для того, чтобы Bluetooth был стабильным, я должен вручную подключиться к устройству, с которым я хочу общаться. Мы использовали код ниже, чтобы инициировать склеивание из приложения, и он должен сохранить склеивание так же, как если бы вы вручную сопряжены через меню настроек.

вот общий поток: 1) зарегистрировать приемник BroadcastReceiver для прослушивания BluetoothDevice.ACTION_BOND_STATE_CHANGED
2) после обнаружения устройства у вас должен быть объект BluetoothDevice.
3) Используйте отражение для вызова метода "createBond" на BluetoothDeviceObject
3a) дождитесь событий изменения состояния облигаций перед открытием сокетов

BluetoothDevice device = {obtained from device discovery};
Method m = device.getClass().getMethod("createBond", (Class[])null);
m.invoke(device, (Object[])null);

int bondState = device.getBondState();
if (bondState == BluetoothDevice.BOND_NONE || bondState == BluetoothDevice.BOND_BONDING)
{
    waitingForBonding = true; // Class variable used later in the broadcast receiver

    // Also...I have the whole bluetooth session running on a thread.  This was a key point for me.  If the bond state is not BOND_BONDED, I wait here.  Then see the snippets below
    synchronized(this)
    {
        wait();
    }
}

4) подождите, пока состояние облигации изменится с BOND_BONDING на BOND_BONDED

внутри BroadcastReciever:

public void onReceive(Context context, Intent intent)
{
    if (BluetoothDevice.ACTION_BOND_STATE_CHANGED.equals(intent.getAction()))
    {
        int prevBondState = intent.getIntExtra(BluetoothDevice.EXTRA_PREVIOUS_BOND_STATE, -1);
        int bondState = intent.getIntExtra(BluetoothDevice.EXTRA_BOND_STATE, -1);

        if (waitingForBonding)
        {
            if (prevBondState == BluetoothDevice.BOND_BONDING)
            {
                // check for both BONDED and NONE here because in some error cases the bonding fails and we need to fail gracefully.
                if (bondState == BluetoothDevice.BOND_BONDED || bondState == BluetoothDevice.BOND_NONE)
                {
                    // safely notify your thread to continue
                }
            }
        }
    }
}

5) раскройте гнезда и общаться

вы также можете использовать метод "removeBond" через отражение, чтобы удалить устройство из списка сопряжения.

надеюсь, что это помогает!


Если сопряжение происходит вследствие подключения вашего приложения, я предполагаю, что некоторые устройства будут рассматривать его как временное сопряжение и не будут держать устройство в парном списке после отключения соединения. Чтобы сохранить устройство в парном списке, вы должны вручную выполнить сопряжение через меню настроек Bluetooth. После сопряжения ваша программа может подключаться / отключаться, и устройство сохранит себя в сопряженном списке.


Я также испытал ту же проблему с Sony Xperia X10. Мне удалось "запомнить" сопряжение, изменив настройки уровня безопасности на стороне устройства bluetooth (поскольку я также разрабатываю устройство).

Я не уверен в объяснении "временного сопряжения", которое зависело бы от производителя, не имеет смысла, что разные телефоны будут по-разному реагировать на соединение с одним и тем же устройством.

однако это неограниченная часть это проблема для меня. Обычно стек Bluetooth, кажется, сбой, когда пользователь отключает устройство, пока приложение подключено в фоновом режиме. Я все еще не понял, как правильно управлять событием ACTION_BOND_STATE_CHANGED.