我遵循了How to get the status of bluetooth (ON/OFF) in iphone programatically的代码来获取蓝牙的状态。

但是,当我通过后退导航按钮弹出viewController时,应用程序崩溃并出现以下错误。

[CoreBluetooth] XPC connection invalid



  ***由于未捕获的异常'NSInternalInconsistencyException'而终止应用程序,原因:'释放了CBCentralManager类的实例0x170261c80,同时仍向其注册了键值观察器。当前观察信息:(上下文:0x1aa9c3710,属性:0x170056b90>上下文:0x1aa9c3710,属性:0x170056b00>上下文:0x1aa9c3710,属性:0x170056b90>上下文:0x1aa9c3710,属性:0x170056b00>)'


我在尝试调用viewWillDisappear时试图删除上述观察者,但是仍然出现错误。

[self.bluetoothManager removeObserver:self forKeyPath:@"state"];
[self.bluetoothManager removeObserver:self forKeyPath:@"delegate"];


我试过了

self.bluetoothManager.delegate = nil;




self.bluetoothManager = nil;


可悲的是,他们都没有作品。

请给予帮助。

更新:

我想在调用-(void)detectBluetooth时未打开蓝牙的情况下显示系统弹出警报。所以我加

[self.bluetoothManager init];


在-(void)detectBluetooth。

我发现造成了错误。

但是我想不出另一种方法来显示默认弹出窗口(带有SETTING按钮)。

最佳答案

我找到了发生此错误的根本原因。

我对蓝牙管理器进行了多次初始化,因此它本身分配了多个观察者。

根据我的目的,在蓝牙未打开时显示系统警报弹出窗口。由于init将弹出警报,因此我需要先将nil设置为蓝牙管理器,然后再设置init。这没有错误。

这是我的最终代码:

if(!self.bluetoothManager)
{
    // Put on main queue so we can call UIAlertView from delegate callbacks.
    self.bluetoothManager = [[CBCentralManager alloc] initWithDelegate:self queue:dispatch_get_main_queue()];
} else{
    if (self.bluetoothManager.state != CBManagerStatePoweredOn) {
        self.bluetoothManager = nil;
        self.bluetoothManager = [[CBCentralManager alloc] initWithDelegate:self queue:dispatch_get_main_queue()];
    }
}
[self centralManagerDidUpdateState:self.bluetoothManager];


- (void)centralManagerDidUpdateState:(CBCentralManager *)central
{
    switch(self.bluetoothManager.state)
    {
        case CBCentralManagerStatePoweredOn: [self pushViewController]; break;
        case CBCentralManagerStateResetting:
        case CBCentralManagerStateUnsupported:
        case CBCentralManagerStateUnauthorized:
        case CBCentralManagerStatePoweredOff:
        default: break;
    }
}

10-08 04:25