移除处于无效状态的GKTurnBasedMatch

17

我正在进行一些实验,试图学习GameKit,并制作了一个简单的游戏和一个列出我的玩家比赛的界面。我正在尝试使用match上的removeWithCompletionHandler:方法来添加删除游戏的功能,但我无法删除似乎已进入无效状态的GKTurnBasedMatch

有关问题比赛的po如下:

$0 = 0x1d590d20 <GKTurnBasedMatch 0x1d590d20 id:858d8257-cc49-4060-b1d8-38c09a929e3c status:Ended message: taken:2013-03-08 18:08:47 +0000 created:2013-03-08 03:24:14 +0000
current:<GKTurnBasedParticipant 0x1d58c020 - id:G:1717956303 (local player) status:Invited outcome:None lastTurn:(null)>
participants:
    <GKTurnBasedParticipant 0x1d58bc90 - id:G:1717239488 status:Done outcome:Quit lastTurn:2013-03-08 18:08:47 +0000>
    <GKTurnBasedParticipant 0x1d58c020 - id:G:1717956303 (local player) status:Invited outcome:None lastTurn:(null)>
>
似乎表明比赛已经结束了,但其中一个参与者的结果是"None",根据文档,我认为这对于已结束的游戏无效。尝试简单删除游戏会显示:

由于一个或多个参数无效,因此无法完成所请求的操作。

在尝试设置结果并结束游戏时会显示:

由于会话处于无效状态,因此无法完成所请求的操作。

我以为可能不能删除游戏,因为本地玩家是活动参与者,但是participantQuitInTurnWithOutcome:...endTurnWithNextParticipants:...都会显示错误:

由于会话处于无效状态,因此无法完成所请求的操作。

我做错了什么还是我创建了一个无法删除的游戏?
P.S. 我也无法通过提供的界面从Game Center中删除游戏,在"Game Over"部分列出。
5个回答

7

这是我成功移除所有无效匹配的方法。

我检查了当前参与者的状态,如果它是被邀请的,我调用了declineInviteWithCompletionHandler,否则我调用了participantQuitInTurnWithOutcome。

在两个完成块中,我接着调用了removeWithCompletionHandler来移除匹配。

虽然这样可能会生成一些错误,但匹配仍然被移除了,所以我的列表很干净。

以下是一个解决方案,可以避免出现上述情况。这样做的额外好处是,如果邀请者在完成第一轮之前退出,则受邀者甚至不会收到通知。

在playerQuitForMatch中,首先结束回合,然后在完成处理程序中立即退出匹配。像这样:

[match endTurnWithNextParticipants:[NSArray arrayWithObject:nextParticipant]
                                          turnTimeout:GKTurnTimeoutDefault
                                            matchData:nil completionHandler:^(NSError *error) {
                                                if (error) {
                                                    NSLog(@"%@", error);
                                                }

                                                [match participantQuitOutOfTurnWithOutcome:GKTurnBasedMatchOutcomeQuit
                                                                     withCompletionHandler:^(NSError *error) {
                                                                         if (error) {
                                                                             NSLog(@"%@" ,error);
                                                                         }
                                                                     }];
                                            }];

5
很不幸,我遇到了完全相同的错误。为了帮助其他人理解这个问题,并希望能够研究出解决方案,您可以通过邀请朋友参加比赛,但在提交回合给被邀请的玩家之前退出比赛来重新创建此问题。然后,托管玩家从Game Center中删除比赛。在被邀请的玩家设备上,他们将拥有一个看起来像上面引用的那样无法删除的比赛。我尝试了所有类型的解决方法。
目前我还没有什么好的办法,但如果我找到解决方案,我会更新我的答案。我正在尝试发布一个Game Center游戏,因此必须找到某种解决方法。我将在接下来的一两天内得出结论。
更新: 我检查了我的不可删除的比赛,它们几乎与您的相同,除了我的拥有受邀状态的玩家还赢得了比赛。似乎把比赛置于无效状态的关键是让一个玩家的状态为已受邀而非已完成,但是比赛状态为已结束。这是我们两种情况的共同点,在苹果复杂的Game Center代码中属于边缘情况。如果他们慢慢地阅读他们的文档,他们可能会把这些拼凑在一起最终发现这个问题。如果苹果真的没能解决这个边缘情况,而期望你“仅仅知道”你不应该把玩家放在那种状态下,那也并不奇怪。
我的结论是,苹果遇到了一个边缘情况,很容易被忽略,因为只有在退出新比赛时才会发生,并且只有在邀请朋友时才会发生。如果您没有错误地设置比赛结果,我猜它永远不会发生,所以他们就从未发现这一点。
由于我还没有发布,我将配置我的应用程序来检测处于这种状态的比赛并忽略它们。我会向控制台报告处于此状态的比赛数量,以确保其不会超出此点。然后,我将分析我的退出代码,并确保在这种边缘情况下,我永远不会再次将比赛置于此状态。考虑到我们所知道的,我们必须积极主动,并且只是接受一些比赛会溜过去的事实。
希望您还没有发布,所以错误案例匹配将局限于Game Center Sandbox环境。实际上,错误的比赛只局限于沙盒中的测试用户,因此一旦您解决了问题,就可以丢弃该用户并从新用户开始。如果您实施了我的上述建议,您应该能够在执行此步骤之前确认您的应用程序正常工作。
如果有人真的找到了删除这些错误比赛的方法,请告诉我们,但我希望我的建议和实际原因的鉴定足以帮助您继续进行项目。

我通过将所有参与者的participant.matchOutcome设置为GKTurnBasedMatchOutcomeTied,然后调用[matchremoveWithCompletionHandler...]成功清除了这些错误匹配。虽然我不会在我的代码中保留它,但它有效地解决了无效游戏的问题。 - Jon

5

我找到了解决方案。对于无效匹配,只需使用-participantQuitOutOfTurn方法,然后使用-removeWithCompletionHandler方法。这将完全删除它。


4

我有一个类似的情况,但稍有不同。我开始匹配游戏,邀请第二个沙盒账户参与,然后第一位玩家在第二位玩家回应前退出并删除了游戏。当第二位玩家试图退出游戏时,他们会收到以下错误提示:

Error quitting match in turn: Error Domain=GKErrorDomain Code=22 "The requested operation could not be completed because the specified participant is invalid." 
UserInfo=0x1f5de800 {
    GKServerStatusCode=5097, 
    NSUnderlyingError=0x1f58b610 "The operation couldn’t be completed. 
    status = 5097, 
    Invalid state: turn sent to playerId:1952436619 in slotIndex: 0 for sessionId: 698b074b-fa0b-4505-834f-1b4305b7eecb : expected slot state: Active but found: Inactive", 
    NSLocalizedDescription=The requested operation could not be completed because the specified participant is invalid.
}

据我所知,这是因为下一个参与者已经被标记为“完成”,我猜测这是因为他们已经退出了。
<GKTurnBasedMatch 0x1f532b20    id:698b074b-fa0b-4505-834f-1b4305b7eecb status:Open message: taken:2013-03-30 19:53:47 +0000 created:2013-03-30 18:29:09 +0000
current:<GKTurnBasedParticipant 0x1f532b80 - id:G:1952433332 (local player) status:Active outcome:None lastTurn:2013-03-30 19:53:47 +0000>
participants:
        <GKTurnBasedParticipant 0x1f532b70 - id:G:1952436619 status:Done outcome:Lost lastTurn:2013-03-30 18:29:10 +0000>
        <GKTurnBasedParticipant 0x1f532b80 - id:G:1952433332 (local player) status:Active outcome:None lastTurn:2013-03-30 19:53:47 +0000>
    >

希望这能帮助其他人进行诊断,即使没有解决方案。很想听取其他人对解决方法的见解。如果这是苹果的错误,似乎值得报告。


2

苹果技术开发支持确认了这个问题。已提交错误报告。我们会随时与您保持联系。


1
这个问题有更新了吗?您能否发布一个问题跟踪链接? - Drux

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