检测精灵套件中的碰撞

Posted

技术标签:

【中文标题】检测精灵套件中的碰撞【英文标题】:Detecting collisions in sprite kit 【发布时间】:2013-12-13 17:19:24 【问题描述】:

我正在尝试使用 sprite kit 制作一个简单的游戏。 基本思想是有一名玩家可以跳跃以避免阻挡。 但是我有一个问题,我不知道如何制作,当玩家击中方块时,玩家会消失并且血液动画开始。 首先,我不明白我在苹果网站上找到的这段代码的作用。

static const uint32_t blockCategory = 0x1 <<0;
static const uint32_t  playerCategory = 0x1 <<1;

比我调用 didBeginContact 函数并在其中放入一个 NSLOG("did call function") 。 但我从未在调试器中收到输出。

这是我的 _player 和 _block 代码: -(SKSpriteNode *)字符

_player = [SKSpriteNode spriteNodeWithImageNamed:@"soldier_run1"];
_player.physicsBody = [SKPhysicsBody bodyWithCircleOfRadius:_player.size.width /2 -5];
_player.physicsBody.dynamic = YES;
_player.physicsBody.usesPreciseCollisionDetection = YES;
_player.physicsBody.friction = 0;
_player.physicsBody.categoryBitMask = playerCategory;
_player.physicsBody.collisionBitMask = blokCategory;
_player.name = @"player";
SKAction *animAction = [SKAction animateWithTextures:playerTextures timePerFrame:0.1      resize:YES restore:YES];

我的 _player 代码:

[_player runAction:[SKAction repeatActionForever:animAction]];

return _player;

-(SKSpriteNode *)block 
_blok = [[SKSpriteNode alloc] initWithColor:[SKColor blackColor] size:CGSizeMake(15, 40)];

//physics
_blok.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:_blok.size];
_blok.physicsBody.dynamic = NO;
_blok.name = @"block";
_blok.physicsBody.categoryBitMask = blokCategory;
_blok.physicsBody.collisionBitMask = playerCategory;
SKAction *moveBlock = [SKAction sequence:@[
                                          [SKAction moveToX:-20 duration:2] ]];
[_blok runAction:moveBlock ];
return _blok;

我也不太明白 categoryBitMask 和 collisionBitMask 的作用。 在我完成这项工作后,我想让角色从屏幕上消失并开始播放血液动画,但我不知道如何让这种情况发生。我认为您必须执行以下操作: 如果(_player && _block didcollide) 但我不知道具体怎么做。

【问题讨论】:

看到这个答案***.com/questions/22495285/… 【参考方案1】:

categoryBitMask 设置精灵所属的类别,而 collisionBitMask 设置精灵可以与之发生碰撞但不能通过它们的类别。

对于碰撞检测,您需要设置contactTestBitMask。在这里,您可以设置希望在联系时调用联系代表的精灵类别。

你已经做的是正确的。以下是您需要做的一些补充:

_player.physicsBody.contactTestBitMask = blockCategory;
_blok.physicsBody.contactTestBitMask = playerCategory;

然后,按如下方式实现联系人委托:

-(void)didBeginContact:(SKPhysicsContact *)contact`

NSLog(@"contact detected");

SKPhysicsBody *firstBody;
SKPhysicsBody *secondBody;

if (contact.bodyA.categoryBitMask < contact.bodyB.categoryBitMask)

    firstBody = contact.bodyA;
    secondBody = contact.bodyB;

else

    firstBody = contact.bodyB;
    secondBody = contact.bodyA;


//Your first body is the block, secondbody is the player.
//Implement relevant code here.


有关实现碰撞检测的详细说明,请查看 this 教程。

【讨论】:

【参考方案2】:

处理碰撞有点混乱。 :) 有很多方法,但您应该从一个地方开始,this 来自 Apple 的相当简单的示例。自述文件提供了很好的介绍,然后您就可以开始研究代码了。

另一种方法(Apple 在其指南中提到)是使用 Double Dispatching(请参阅 wikipedia 了解详细说明)。然而,我不会一开始就尝试摸索这种方法。这是一种有点先进的方法,因为它依赖于动态选择器和类似的技术来实现魔法。然而,即使有这个警告,你也可以找到一个简单的例子来说明如何做到这一点,以及大量的支持描述here。

【讨论】:

以上是关于检测精灵套件中的碰撞的主要内容,如果未能解决你的问题,请参考以下文章

子精灵的精灵套件碰撞检测

在精灵套件中发生碰撞时停止对象

Python进阶篇十一Pygame的精灵和碰撞检测

pygame之精灵碰撞检测

如何检测pygame中的碰撞?

动画精灵与碰撞检测