首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >初始化EASession失败-- EAAccessory没有协议

初始化EASession失败-- EAAccessory没有协议
EN

Stack Overflow用户
提问于 2013-08-15 20:55:29
回答 4查看 4.1K关注 0票数 1

我正在开发一个与蓝牙2.1通信的iOS应用程序。当应用程序变得活跃时,它就会连接到BT。如果应用程序转到后台,并再次活跃起来,它就可以正常工作了。

但我注意到了一个问题:

如果我关闭BT模块电源,应用程序将收到通知,其中我执行以下操作:

代码语言:javascript
复制
  - (void)accessoryDidDisconnect:(EAAccessory *)accessory
    {
        NSLog(@"EAController::accessoryDidDisconnect:");
        _selectedAccessory = nil;
        UIAlertView *alert = [[UIAlertView alloc]initWithTitle:@"Alert" message:@"Lost connection. " delegate:nil cancelButtonTitle:@"OK" otherButtonTitles: nil];
        [alert show];
        NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
        [defaults setBool:YES forKey:@"Lost Communication"];
        [self closeSession];
    }

然后我打开模块电源,转到设置->蓝牙,将BT模块连接到iPhone,激活应用程序(从后台返回),EASession无法启动:

代码语言:javascript
复制
if (_session == nil)
    {
        NSLog(@"EAController::openSession");
        [_selectedAccessory setDelegate:self];
        _session = [[EASession alloc] initWithAccessory:[self selectedAccessory] forProtocol:_protocolString];

        if (_session)
        {
                    // Set up delegate........
        }
        else
        {
            NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
            [defaults setBool:NO forKey:Unit_Has_Connection_UserDefault_Key];
            NSLog(@"creating session failed");
        }
    }

启动_accessoryList和_selectedAccessory:

代码语言:javascript
复制
_accessoryList = [[NSMutableArray alloc] initWithArray:[[EAAccessoryManager sharedAccessoryManager] connectedAccessories]];
_selectedAccessory = [_accessoryList objectAtIndex:0];

我发现_accessoryList有我正在使用的附件,但它的“协议”是空的。

代码语言:javascript
复制
$12 = 0x1dd58050 <__NSArrayI 0x1dd58050>(
<EAAccessory: 0x1dd1dce0> {
  connected:YES
  connectionID:XXX
  name: XXX
  manufacturer: XXX
  modelNumber: XXX
  serialNumber: 
  firmwareRevision: XXX
  hardwareRevision: XXX
  macAddress: XXX
  protocols: (
)
  delegate: (null)
}
)

如果我关掉这个应用程序并重新启动,它就能正常工作。

有人知道怎么解决这个问题吗?

这个问题类似于this one,但是发生在不同的情况下,这个问题的答案似乎不能解决我的问题。

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2013-08-19 20:12:56

经过几天的寻找解决,我终于解决了这个问题(或者我希望我解决了这个问题。)我在这里张贴我的答案,所以如果任何人有同样的问题,可以有一个想法。

你永远不能相信EAAccessoryManager,它可能有鬼配件。因此,使用以下命令启动_accessoryList并不总是有效的。

代码语言:javascript
复制
_accessoryList = [[NSMutableArray alloc] initWithArray:[[EAAccessoryManager sharedAccessoryManager] connectedAccessories]];

如果您启动带有鬼附件的accessoryList,则肯定无法成功启动EASession。

正确的方法是使用EAAccessory通知,它在this answer中进行了描述,但没有详细说明如何做到这一点。

首先,您需要创建post 2通知:

代码语言:javascript
复制
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(accessoryConnected:) name:EAAccessoryDidConnectNotification object:nil];
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(accessoryDisconnected:) name:EAAccessoryDidConnectNotification object:nil];

[[EAAccessoryManager sharedAccessoryManager]registerForLocalNotifications];

然后在accessoryConnected和accessoryDisconnected中,您可以执行以下操作。

代码语言:javascript
复制
- (void)accessoryConnected:(NSNotification *)notification
{
    NSLog(@"EAController::accessoryConnected");

    EAAccessory *connectedAccessory = [[notification userInfo] objectForKey:EAAccessoryKey];
    [[self accessoryList] addObject:connectedAccessory];
    if ([_accessoryList count])
    {
        _selectedAccessory = [_accessoryList objectAtIndex:0];
        NSArray *protocolStrings = [_selectedAccessory protocolStrings];
        if ([protocolStrings count]) {
            self.protocolString = [protocolStrings objectAtIndex:0];
            [self openSession];
        }
    }
}


- (void)accessoryDisconnected:(NSNotification *)notification
{
    EAAccessory *disconnectedAccessory = [[notification userInfo] objectForKey:EAAccessoryKey];

    int disconnectedAccessoryIndex = 0;
    for(EAAccessory *accessory in [self accessoryList]) {
        if ([disconnectedAccessory connectionID] == [accessory connectionID]) {
            break;
        }
        disconnectedAccessoryIndex++;
    }

    if (disconnectedAccessoryIndex < [[self accessoryList] count]) {
        [[self accessoryList ] removeObjectAtIndex:disconnectedAccessoryIndex];
    } else {
        NSLog(@"could not find disconnected accessory in accessory list");
    }
    NSLog(@"_accessory did disconnect: %@",_accessoryList);

}
票数 1
EN

Stack Overflow用户

发布于 2014-10-13 07:36:03

当我从后台返回时,我也遇到了重新连接到我的附件的问题,特别是在我们假设8h+空闲之后。仅依赖EAAccessoryDidConnectNotification/Disconnect (而不是可以给出鬼设备的EAAccessoryManager )进行详细说明,大多数时间看起来都很好。

然而,如果两个应用程序正在使用我们的附件,它可能会出现故障,一旦手机/垫被唤醒。到前台的第一个应用程序最终将收到连接通知。但是在第二个应用程序中交换时,它只会收到断开连接的通知,而不是连接。在这里,我很难确定我们是否有一个连接的附件,因为我不能相信EAAccessoryManager。

票数 1
EN

Stack Overflow用户

发布于 2016-04-12 21:14:11

我发现当一个EAAccessory重新连接时,您会看到附件对象的两个刷新。第一个没有协议字符串,几秒钟后,相同的附件(具有相同的连接ID)将与协议字符串一起重新出现。构造了我的代码。它忽略了苹果推荐的技术中没有协议字符串的任何附件。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18261670

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档