游戏中心沙盒环境:无法创建游戏问题

4

我目前正在开发一款回合制游戏,使用Game Center来处理在线功能(匹配和回合处理)。

我使用了两个沙盒账户——一个在我的3gs上,另一个在iOS模拟器上。我一直在使用GKTurnBasedMatchMakerViewController进行匹配测试而没有任何问题,但现在我遇到了一个问题:

每次我想邀请另一个玩家加入新的游戏(与任意一个或另一个玩家),GKTurnBasedMatchMakerViewController都会显示一个UIAlertView,其中写着:

无法创建游戏-请删除现有游戏并重试。

问题是,我已经为每个玩家删除了所有比赛(他们的列表中没有任何比赛(甚至没有关闭的比赛)。所以目前没有任何用户处于任何比赛中。

在我的GKTurnBaseMatchMakerViewControllerDelegate中,turnBasedMatchmakerViewController:didFailWithError:没有被调用。当我点击UIAlertView上的OK按钮时,委托中唯一被调用的函数是turnBasedMatchmakerViewControllerWasCancelled:

我唯一能想到的就是我的游戏实际上没有从GameCenter中删除,但由于我使用的是GKMatchMakerViewController UI进行删除,所以我几乎不认为会出现这种情况。


当退出回合制比赛时,我实现了turnBasedMatchmakerViewController:playerQuitForMatch:,如下所示:

- (void)turnBasedMatchmakerViewController:(GKTurnBasedMatchmakerViewController *)viewController playerQuitForMatch:(GKTurnBasedMatch *)match
{
  if ( [self isLocalPlayerCurrentPlayerForMatch:match] ) {

    NSData* endData = match.matchData;

    for (GKTurnBasedParticipant* participant in match.participants) {
      participant.matchOutcome = GKTurnBasedMatchOutcomeWon;
    }
    match.currentParticipant.matchOutcome = GKTurnBasedMatchOutcomeLost;

    [match endMatchInTurnWithMatchData:endData 
                     completionHandler:^(NSError *error) {
                       if (error) {
                         NSLog(@"%@",error.description);
                       }
                     }];
  }  

}

(注意:该游戏只有两名玩家)

isLocalPlayerCurrentPlayerForMatch的含义是:

- (BOOL) isLocalPlayerCurrentPlayerForMatch:(GKTurnBasedMatch*)match
{
  return [[[GKLocalPlayer localPlayer] playerID] isEqualToString:match.currentParticipant.playerID];
}

有人遇到过这个问题并找到解决方法吗?我是做错了什么,还是这个问题很明显我只是看不见?
非常感谢任何能帮助我找到问题根源的评论。
更新
感谢@kaan-dedeoglu的帮助,我知道两个用户都有一个空的匹配列表(与显示状态一致)。
我还创建了第三个沙盒帐户。将前两个帐户命名为A和B,第三个帐户为C。
状态1:
1. A和B都没有链接到任何比赛。 2. A和B在创建任何游戏时都会收到“无法创建游戏”的错误(A邀请B,A || B邀请其他玩家,A || B创建新的自动匹配)。
状态2:
1. C(工作帐户)可以邀请B并正常与B玩派对。 2. C(工作)可以邀请B进行另一个同时进行的聚会 3. C(工作)邀请A玩耍。 4. A无法玩耍(无法访问当前匹配列表,GKTurnBasedMatchMakerViewController直接进入新游戏的创建)。 5. C不再工作。 6. A、B和C现在都卡在“无法创建游戏”的错误中。
此外,这是我如何初始化我的GKTurnBasedMatchMakerViewController,但我认为这没有错。
- (void) displayMatchMakerVC
{

  if (! [[GKLocalPlayer localPlayer] isAuthenticated] ) return;

  GKMatchRequest* request = [[[GKMatchRequest alloc] init] autorelease];
  int nbPlayers = 2;
  request.minPlayers = nbPlayers;
  request.maxPlayers = nbPlayers;


  GKTurnBasedMatchmakerViewController*  matchMakerVC = [[[GKTurnBasedMatchmakerViewController alloc] initWithMatchRequest:request] autorelease];
  matchMakerVC.turnBasedMatchmakerDelegate = self;
  matchMakerVC.showExistingMatches = YES;

  [[CCDirector sharedDirector] presentModalViewController:matchMakerVC animated:YES];
}

注意:我没有使用ARC,这是否与内存问题有关?虽然我不是内存管理专家,但根据我的理解,它似乎是正确的。
你有什么想法,这可能与我的代码有关,而不是游戏中心?非常感谢任何能帮助我进一步的答案。
更新2:turnbasedMatchmakerViewController:didFindMatchMethod:
下面是我的turnbasedMatchmakerViewController:didFindMatchMethod:方法。
- (void)turnBasedMatchmakerViewController:(GKTurnBasedMatchmakerViewController *)viewController didFindMatch:(GKTurnBasedMatch *)match
{
  BLTheme* theme = [[[BLGameConfig sharedConfig] localPlayer] userTheme];
  GameSceneRemoteGCLoader* loader = [[GameSceneRemoteGCLoader alloc] initWithGKMatch:match andTheme:theme];
  [viewController dismissViewControllerAnimated:NO completion:^{}];
  [[CCDirector sharedDirector] replaceScene:loader];

}

当我启动自动匹配时,它会显示相同的错误信息:“无法创建游戏 - 请删除现有游戏并重试。”。


当我开始自动匹配时,我会收到相同的“无法创建游戏错误”。 我再次更新了我的帖子,以显示turnBasedMatchmakerViewController:didFindMatch。 感谢您的帮助,非常感激。 - thib_b
在你的第二次编辑之后,我也感到非常困惑。你分享的代码部分看起来很不错,我不知道为什么会出现错误。我猜测 turnBasedMatchmakerViewControllerDidFindMatch 方法甚至没有被调用。沙盒模式有时可能会表现得很奇怪。我的最后建议是注销并重新登录,并尝试使用我的答案删除所有游戏。希望我能提供更多帮助! - Kaan Dedeoglu
你说得对,它甚至没有被调用。 我使用了你的答案来移除它们,但是它并没有解决我的问题。 我也倾向于认为这可能与沙盒相关,因为它似乎只与我的前两个帐户有关,但我没有任何正式证据支持这一点。 如果我得到答案或更多元素,我会回来发帖的。 非常感谢您所提供的帮助和花费的时间! :) - thib_b
@thib_b,你有没有找到解决方法?我也遇到了同样的问题,但一直没有找到解决方法。我怀疑当我更新构建时,旧的匹配项会从新构建中隐藏,但它们实际上并没有被删除,在某个地方有太多的匹配项导致出现错误消息。 - Tim Arnold
@TimArnold,那个项目已经结束了,但我记得我从未真正找到解决方法(只是使用新账户当一些被封锁...)。话虽如此,你的观点很引人入胜并且有趣,但是我很抱歉无法提供更多帮助。如果你找到答案,请发布一下。干杯! - thib_b
显示剩余2条评论
4个回答

1
这可能或可能不是解决您问题的方法,但我遇到类似问题并通过以下方式解决了它。
似乎默认情况下游戏中心将具有不同CFBundleVersion(构建号而不是版本号或CFBundleShortVersionString)值的应用视为彼此不兼容,因此不会显示具有增加构建号的应用之间的匹配。 (通常,在开发期间分发新的自定构建或稳定版本时,开发人员会增加此数字,因此这非常不幸)。
为了找到并删除“丢失”的游戏,我减少了我的CFBundleVersion值(这揭示了游戏),然后删除了有问题的匹配项。
另外,在iTunes Connect中调整一些设置似乎已经去除了这种CFBundleVersion不兼容性。 它需要一段时间才能传播,但我认为它的方法是点击我的应用程序,点击查看详细信息,确保Game Center开关设置为“启用”,并确保“多人兼容性”表中有一个项目。 您还可以在原始应用程序屏幕上使用“管理Game Center”按钮中的各种可能性,但我认为“多人兼容性”设置最终使我看到了以前隐藏的所有旧匹配项。

祝你好运!


我无法再测试您的解决方案了,但既然它解决了您的特定问题,我将把它标记为解决方案。谢谢! - thib_b

1

只是为了确保:在这两个设备中,将这些行添加到您的身份验证完成处理程序中,并运行一次。(然后您可以将其注释掉)。

[GKTurnBasedMatch loadMatchesWithCompletionHandler:(^)(NSArray *matches, NSError *error) {

   for (GKTurnbasedMatch *match in matches) {

       [match removeWithCompletionHandler:NULL];

    }
}];

这将确保从您的playerID中删除所有游戏。


非常感谢您的代码,它让我检查到没有匹配项(空列表,也没有错误检索它们)。如果您想进一步了解,请查看我的帖子更新。无论如何,非常感谢! :) - thib_b
此调用不会从本地玩家ID中删除所有游戏。请参阅GKTurnBasedMatch类参考中的removeWithCompletionHandler方法 -->“在将本地玩家作为活动参与者的比赛上调用此方法是编程错误。” - Jay Haase
@JayHaase 是的,在发布版本中,您应该先将轮次传递给下一个玩家,然后再移除比赛(否则比赛会卡住)。但是在调试时,可以在所有设备上运行此代码-这样比赛就会从游戏中心服务器中删除(因为每个参与者都会删除比赛)。 - Kaan Dedeoglu
如何在iOS6中删除退出匹配?请注意,本文仅为翻译内容,不涉及解释。 - Vineesh TP

0

这太荒谬了。你不必删除现有的匹配项来创建新的匹配项。我正在开发一个类似的游戏,它确实能正常运行。


似乎在Game Center上,一个应用程序允许的GKTurnBasedMatch数量是有限制的。 - Tim Arnold
是的,这是正在进行中比赛的30个。但是对于未进行中的比赛可能会有更多。 - Salih Ozdemir

0
以下方法对我起作用。首先,我在每个玩家的设备上运行了应用程序,调用了quitAllMatches函数。然后,我再次在每个设备上运行了应用程序,调用了removeAllMatches函数。
从长远来看,随着进程的进行逐步清理可能会更好一些。但是这种方法解决了立即面临的问题。
-(void) quitAllMatches {
    [GKTurnBasedMatch loadMatchesWithCompletionHandler:^(NSArray* matches, NSError* error)  {
        for (GKTurnBasedMatch* match in matches) {
            GKTurnBasedParticipant* participant = match.currentParticipant;
            NSString* playerID = participant.playerID;
            NSString* localPlayerID = [GKLocalPlayer localPlayer].playerID;
            if ([playerID isEqualToString: localPlayerID]) {
                NSArray* participants = match.participants;
                for (GKTurnBasedParticipant* participant in participants) {
                    participant.matchOutcome = GKTurnBasedMatchOutcomeTied;
                }
                NSData* data = [NSData data];
                [match endMatchInTurnWithMatchData: data completionHandler:^(NSError* error) {
                    if (error) {
                        WJLog(@"did not end -- error %@", [error localizedDescription]);
                    }
                    else {
                        WJLog(@"match ended!");
                    }
                }];
            }
        }
    }];
}

-(void) removeAllMatches {
    [GKTurnBasedMatch loadMatchesWithCompletionHandler:^(NSArray* matches, NSError* error)  {
        for (GKTurnBasedMatch* match in matches) {
            [match removeWithCompletionHandler:^(NSError* error) {
                if (error) {
                    WJLog(@"error: %@", [error localizedDescription]);
                }
                else {
                    WJLog(@"removed match");
                }
            }];
        }
    }];
}

它没有移除完全匹配项。你能说一下如何在iOS6中移除完全匹配项吗? - Vineesh TP

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接