Не мога да дерегистрирам приемника си и все още получавам излъчвания

В моята дейност имам това:

protected void onStart() {
    super.onStart();
    blc = new BluetoothClient(this);
}

protected void onStop() {
    super.onStop();
    try {
        blc.close();
    } catch (IOException e) { }
    blc = null;
}

Това е класът, който има приемника: (Само важните части)

public class BluetoothClient implements Closeable {

    final BroadcastReceiver receiver;
    Context context;
    ...

    public BluetoothClient(Context context) {
        this.context = context.getApplicationContext();
        receiver = new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
            }
        };
        context.registerReceiver(receiver, new IntentFilter(BluetoothAdapter.ACTION_STATE_CHANGED));
        ...
    }

    ...

    public void close() throws IOException {
        try {
            context.unregisterReceiver(receiver); // Causes IllegalArgumentException
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

Получавам java.lang.IllegalArgumentException: Receiver not registered всеки път в BluetoothClient.close. Как мога да направя това правилно.

Редактиране: добавен е целият код (вероятно е твърде много, за да се прегледа с един поглед)

пълният код (с изключение на основната дейност, забравих за това) е тук: http://pastebin.com/aVit2L8M

основна дейност: http://pastebin.com/6Ww8sKwE


person gyozo kudor    schedule 29.09.2015    source източник
comment
Как се получава context в close() метод?   -  person ρяσѕρєя K    schedule 29.09.2015
comment
@ρяσѕρєя K Не го включих във въпроса, но го има.   -  person gyozo kudor    schedule 29.09.2015
comment
ако е възможно, моля, покажете кода на целия клас, като използвате сайт, подобен на pastebin   -  person ρяσѕρєя K    schedule 29.09.2015
comment
Добре, добавих pastebin, но мисля, че всички подходящи части са тук във въпроса.   -  person gyozo kudor    schedule 29.09.2015


Отговори (3)


Или използвате различен контекст, за да дерегистрирате излъчването, а не контекста, с който сте се регистрирали, ИЛИ дерегистрирате различен приемник.

person Khawar Raza    schedule 29.09.2015
comment
Контекстът е контекстът на приложението, актуализирах въпроса си. - person gyozo kudor; 29.09.2015

Трябва да зададете входящия контекст като поле в конструктора и да го използвате при отписване.

public class BluetoothClient {

    Context mContext;

    public BluetoothClient(Context context) {
        mContext = context;
        ...
    }

    public void close() {
        try {
           mContext.unregisterReceiver(receiver);
        }
    }
person loGi    schedule 29.09.2015
comment
Има го, просто не съм го включил тук. - person gyozo kudor; 29.09.2015

Регистрирайте и отменете регистрацията на приемника за излъчване съответно в onResume и onPause и използвайтеLocalBroadCastManger.getInstance(mContext).register(YourReceiver) и LocalBroadCastManger.getInstance(mContext).unregister(YourReceiver) Проверете и официалната документация

person Malik Umar    schedule 29.09.2015
comment
Използвам излъчващ приемник за Bluetooth STATE_ON събития. В този случай имам нужда от глобалния BroadcastManager, ако разбирам правилно. - person gyozo kudor; 29.09.2015
comment
Да, за bluetooth трябва да използвате BroadcastManager на системно ниво. LocalBroadcastManager е с цел ефективност, ако слушате собствено генерирани и локални предавания. - person Khawar Raza; 29.09.2015
comment
Моята грешка е, че трябва да регистрирате приемник в манифеста за Bluetooth, моля, проверете тази връзка. връзка - person Malik Umar; 30.09.2015