Как правильно настроить GKSession (Bluetooth) на iOS 6.1

У меня возникла проблема с запуском GKSession. Ниже приведен мой код, который выполняется при нажатии определенной кнопки.

GKSession *session;
if (connectButtonHasBeenPressed == false) {
    NSLog(@"connectToBluetoothDevice has been called");
    connectButtonHasBeenPressed = true;
    GKSession *session = [[GKSession alloc] initWithSessionID:@"Unicorn" displayName:nil sessionMode:GKSessionModePeer];
    [session setDataReceiveHandler:self withContext:nil];
    [session setDelegate:self];
    [session setAvailable:YES];
    NSLog(@"Session ID: %@", [session sessionID]);
    NSLog(@"Currently Available Peers: %i", [[session peersWithConnectionState:GKPeerStateAvailable] count]);
    if ([session isAvailable]) {
        NSLog(@"The Session Is Available");
    }
    [connectToDeviceButton setTitle:@"Searching..." forState:UIControlStateNormal];

}
else {
    NSLog(@"Currently Available Peers: %i", [[session peersWithConnectionState:GKPeerStateAvailable] count]);
}

После первого нажатия кнопки все работает нормально. И каждый раз, когда я нажимаю кнопку после этого, он печатает «Доступные в настоящее время одноранговые узлы: 0». Это был бы ожидаемый результат, если бы у меня не было двух устройств, расположенных рядом друг с другом, запускающих программу с нажатой кнопкой. У меня также есть все методы GKSessionDelegate, реализованные в этом классе, и все они выводят сообщение на консоль. Ни один из этих методов никогда не запускается. Все это указывало бы мне на то, что устройства не могут найти друг друга.

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

Какие-либо предложения?


person Andrew    schedule 03.06.2013    source источник


Ответы (1)


Кажется, у вас есть два экземпляра GKSession. Один снаружи, а другой внутри оператора if.

Это означает, что если connectButtonHasBeenPressed равно false, он создаст собственную версию GKSession, которую сохранит. но если это true, то session будет равно nil.

Также я бы рекомендовал использовать nil в качестве идентификатора сеанса, поскольку затем он устанавливается для вас с использованием идентификатора пакета. Хотя это могут быть личные предпочтения.

Попробуйте использовать что-то вроде этого:

if (session == nil)
{
    NSLog(@"connectToBluetoothDevice has been called");
    session = [[GKSession alloc] initWithSessionID:nil displayName:nil sessionMode:GKSessionModePeer];
    [session setDataReceiveHandler:self withContext:nil];
    [session setDelegate:self];
    [session setAvailable:YES];

    NSLog(@"Session ID: %@", [session sessionID]);
    if ([session isAvailable])
    {
        NSLog(@"The Session Is Available");
    }
    [connectToDeviceButton setTitle:@"Searching..." forState:UIControlStateNormal];

    connectButtonHasBeenPressed = true;
}

NSLog(@"Currently Available Peers: %i", [[session peersWithConnectionState:GKPeerStateAvailable] count]);

Вам действительно не нужно иметь переменную connectButtonHasBeenPressed, так как вы можете просто проверить, равна ли GKSession нулю, что всегда должно быть, если нет соединения. Когда ваш сеанс заканчивается, вы всегда должны отменить все действия сеанса и установить session = nil;.

Переменная session действительно должна быть объявлена ​​в вашем файле .h, чтобы вы могли использовать ее во всем классе. Так что GKSession *session; уже не нужен.

Примечание. Просто примечание из вашего журнала connectToBluetoothDevice has been called. По моему опыту, GKSession будет использовать Wi-Fi или Bluetooth, в зависимости от того, что доступно. Настолько, что у вас может быть 3 устройства, 1 с включенным только Bluetooth, 1 с включенным только WiFi и последнее с обоими включенными, и все они будут подключаться и разговаривать друг с другом абсолютно нормально.

Надеюсь это поможет.

Изменить: из примера кода удалена ненужная переменная connectButtonHasBeenPressed и добавлены дополнительные пояснения.

person Baza207    schedule 03.06.2013
comment
Кроме того, иногда у вас могут возникать проблемы с подключением между устройствами на iOS 5 и iOS 6. Похоже, это проблема Apple, и не похоже, что будет исправлена ​​ошибка. - person Baza207; 03.06.2013
comment
Большое спасибо! Я не видел, чтобы у меня было два экземпляра GKSession. - person Andrew; 03.06.2013