【问题标题】:How do we wait for a while before detecting next action? [closed]我们如何在检测下一个动作之前等待一段时间? [关闭]
【发布时间】:2014-05-11 13:35:27
【问题描述】:

基本上这是我喜欢做的事情:

-(void)didBeginContact:(SKPhysicsContact *)contact
{
     uint32_t collision = (contact.bodyA.categoryBitMask | contact.bodyB.categoryBitMask);
     if (collision == (CNPhysicsCategoryCat|CNPhysicsCategoryBed)) {
         _catNode.userData = [@{@"catOnBed":@(YES)} mutableCopy];
         //Code here can let me wait for 3 seconds or something.
         (_catNode.userData[@"catOnBed"])?[self win]:[self lose];
     }
     if (collision == (CNPhysicsCategoryCat|CNPhysicsCategoryEdge)) {
         [self lose];
     }
}

所以我希望在接触发生 3 秒后进行检测。

我尝试了 dispatch_time 方法,它返回“断点 2.1”给我。截图如下:

然后我也尝试了 performSelector 方法,它告诉我未声明的“detectContact...”

我也创建了方法,这是证据。

然后我尝试了SKAction序列方法(我认为这是关闭的)。它也失败了:

这是堆栈跟踪:

【问题讨论】:

  • 看完后我觉得不是同一个问题,因为我在这里调用了一个方法,而这个问题是关于通过原始方法创建延迟。
  • 我感觉你甚至不确定你在问什么。除了返回正确的错误和堆栈跟踪之外,您发布的断点图像基本上是无用的。
  • 这里是堆栈跟踪:i.stack.imgur.com/9B9Tt.png
  • 好的,越来越近了。左边的是堆栈跟踪,右边的是普通的汇编,除非你是魔术师,否则这是没用的。转到底部的控制台,并粘贴控制台输出,具体错误应该在那里。

标签: ios objective-c sprite-kit


【解决方案1】:

您可以使用延迟任务!

int64_t delay = 3;
dispatch_time_t time = dispatch_time(DISPATCH_TIME_NOW, delay * NSEC_PER_SEC);
dispatch_after(time, dispatch_get_main_queue(), ^(void){
    // do whatever you want to do after 3 seconds.
});

【讨论】:

【解决方案2】:

您可以使用-[NSObject performSelector:withObject:afterDelay]。有关更多信息,请查看documentation。基本上你的代码应该是这样的:

-(void)didBeginContact:(SKPhysicsContact *)contact {
    // Other code
    [self performSelector:@selector(detectContact) withObject:nil afterDelay:3];
}

- (void)detectContact {
    // Code to be execute after 3 second delay
}

方法detectContact将在3秒后被调用。

【讨论】:

  • 它表示未声明的标识符。截图:i.stack.imgur.com/zbYWm.png
  • 您必须定义“detectContact”方法。这只是一个示例方法名称。该方法将保存您想要在延迟后执行的任何代码。
  • 在哪里定义这个方法以及如何在调用上面显示的原始方法时定义它?
  • 您可以像任何其他方法一样声明和实现它。我在答案中添加了一个示例。
  • 谢谢哥们。它仍然显示相同的信息:i.stack.imgur.com/4VuMA.png
【解决方案3】:

延迟引入一个新的SKAction

SKAction *delayedBlock = [SKAction sequence:@[[SKAction waitForDuration:2.0], 
                                              [SKAction runBlock:
^{
    // Perform action here.
}]]];

然后在任何相关的节点上运行它,可能是SKScene

// Assuming that self is the SKScene
[self runAction:delayedBlock];

我建议使用SKActions 而不是其他建议的替代方案,以限制在SpriteKit 的运行循环内。

【讨论】:

  • 我认为这是解决方案(或至少非常封闭)。我仍然遇到断点 1.1 tho:i.stack.imgur.com/b3kby.png
  • A breakpoint isn't an error, @AeroWindwalker.
  • 由于某种原因,如果使用此方法,它似乎会运行两次所需的操作,而不是只运行一次。
  • 可能是因为多次发生碰撞?确保只开火一次。
  • 这很奇怪,因为其他方法不会导致这种现象。
【解决方案4】:

像这样使用 dispatch_time_t...

double delaySeconds = 2.0;
dispatch_time_t time = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(delaySeconds * NSEC_PER_SEC));
dispatch_after(time, dispatch_get_main_queue(), ^(void){
    (_catNode.userData[@"catOnBed"])?[self win]:[self lose];
});

【讨论】:

猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-05-25
  • 2013-01-17
  • 1970-01-01
  • 2016-04-06
  • 1970-01-01
  • 2014-10-21
  • 2019-06-07
相关资源
最近更新 更多