我知道这个问题已被问及" here但它没有帮助,也没有涵盖我的要求。
话虽如此,我想知道如何实现以下目标:
node
,它有2个物理体:1)一个较小的体(200x200)代表节点的框架,2)一个较大的体(500x500)代表一个外围的周边一个将作为&#34;检测&#34;边界。外部物体不会物理地撞击碰撞物体,它只需要记录物体遇到该边界线。以下是我所描述的简单概念:我最初的方法是使用SKPhysicsBody bodyWithBodies:<NSArray>
,但这只会将重叠体创建为较小的矩形。
所以我想我必须为较小的身体(黑色方块)创建SKSpriteNode
,为较大的身体(蓝色方块)创建另一个SKSpriteNode
,并将其添加为孩子到较小的方块(反之亦然)。
我的问题是,在注册该交互时,我似乎无法获得外部边界以允许另一个对象通过。我最接近的是让一个可移动的节点到达边界,然后只要我试图通过边界,就会不断地沿着500x500边界的线来回推动。我已经能够使移动节点UNABLE通过500x500,但这与我需要的完全相反。
以下是我正在使用的代码,也许有人可以看到我做错的事情:
/// TESTING
// Detection body - 500x500
SKSpriteNode *dbody = [SKSpriteNode spriteNodeWithImageNamed:@"object500"];
dbody.position = CGPointMake(500, 100);
dbody.physicsBody = [SKPhysicsBody bodyWithEdgeLoopFromRect:dbody.frame];
dbody.physicsBody.categoryBitMask = detection;
dbody.physicsBody.collisionBitMask = 0;
dbody.physicsBody.contactTestBitMask = player;
// Node body - 200x200
SKSpriteNode *testBoundary = [SKSpriteNode spriteNodeWithImageNamed:@"object"];
testBoundary.physicsBody = [SKPhysicsBody bodyWithEdgeLoopFromRect:testBoundary.frame];
testBoundary.physicsBody.categoryBitMask = object;
testBoundary.physicsBody.contactTestBitMask = player;
testBoundary.position = dbody.position;
// Add boundary as child to main node
[testBoundary addChild:dbody];
// Add to scene
[chapterScene addChild:dbody];
所有这些都在 LevelScene.m 中,SKScene
在标题中设置了<SKPhysicsContactDelegate>
。另外,我已经定义了chapterScene
:
// Set up main chapter scene
self.anchorPoint = CGPointMake(0.5, 0.5); //0,0 to 1,1
chapterScene = [SKNode node];
[self addChild:chapterScene];
, LevelScene顶部定义chapterScene
。
@interface LevelScene () {
#pragma 1 Scene objects
SKNode *chapterScene;
}
如果有人可以帮助我弄清楚我做错了什么,或者可能采用另一种方法来解决我想要的问题,我会很感激。
注意:我的备份解决方案在CPU和内存方面似乎很昂贵,但我相信它仍会有效。如果移动的玩家节点在500x500区域内,我会有BOOL isDetected
来表示,然后在update
我将监视到500x500节点中心的较小200x200矩形边界的距离。但我更愿意使用2 SKPhysicsBody
,因为我相信它可以完成并且更容易实现。
更新
这是我的移动角色(一个名为 Character.m 的单独的SKNode
类)
- (void)createCharacterWithName:(NSString *)charName {
character = [SKSpriteNode spriteNodeWithImageNamed:charName];
[self addChild:character];
self.physicsBody = [SKPhysicsBody bodyWithCircleOfRadius:character.frame.size.width/2.0];
self.physicsBody.dynamic = YES;
self.physicsBody.allowsRotation = YES;
// Define physics body relationships
self.physicsBody.categoryBitMask = player;
self.physicsBody.collisionBitMask = player;
self.physicsBody.contactTestBitMask = detection;
}
答案 0 :(得分:2)
这对我有用。抱歉,我没有在obj c上写。对我来说快速的快速
import SpriteKit
let CategoryOuter:UInt32 = 1 << 0
let CategoryInner:UInt32 = 1 << 1
let CategoryTester:UInt32 = 1 << 2
class GameScene: SKScene, SKPhysicsContactDelegate {
let outerSprite = SKSpriteNode(color: SKColor.redColor(), size: CGSizeMake(100, 100))
let innerSprite = SKSpriteNode(color: SKColor.blueColor(), size: CGSizeMake(40, 40))
let tester = SKSpriteNode(color: SKColor.greenColor(), size: CGSizeMake(10, 10))
override init(size: CGSize) {
super.init(size: size)
physicsWorld.contactDelegate = self
physicsWorld.gravity = CGVectorMake(0, 0)
outerSprite.position = CGPointMake(size.width/2, size.height/2)
outerSprite.physicsBody = SKPhysicsBody(rectangleOfSize: outerSprite.size)
outerSprite.physicsBody!.dynamic = false
outerSprite.physicsBody!.categoryBitMask = CategoryOuter
outerSprite.physicsBody!.collisionBitMask = 0
outerSprite.physicsBody!.contactTestBitMask = CategoryTester
innerSprite.physicsBody = SKPhysicsBody(rectangleOfSize: innerSprite.size)
innerSprite.physicsBody!.dynamic = false
innerSprite.physicsBody!.categoryBitMask = CategoryInner
innerSprite.physicsBody!.collisionBitMask = CategoryTester
innerSprite.physicsBody!.contactTestBitMask = CategoryTester
outerSprite.addChild(innerSprite)
addChild(outerSprite)
tester.physicsBody = SKPhysicsBody(rectangleOfSize: tester.size)
tester.physicsBody!.categoryBitMask = CategoryTester
tester.physicsBody!.collisionBitMask = CategoryInner
addChild(tester)
}
func didBeginContact(contact: SKPhysicsContact) {
let collision:UInt32 = (contact.bodyA.categoryBitMask | contact.bodyB.categoryBitMask)
if collision == (CategoryOuter | CategoryTester) {
print("outer collision")
}
else if collision == (CategoryInner | CategoryTester) {
print("inner collision")
}
}
override func touchesMoved(touches: Set<UITouch>, withEvent event: UIEvent?) {
if let touch = touches.first {
let location = touch.locationInNode(self)
tester.position = location
}
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}