1

問題:私のプレーヤーにコインと衝突させ、衝突時にコインラベルに+1を追加するのに少し問題があるようです。プレイヤーはコインと接触した後も移動を続ける必要があります。PhysicsBodysを使った基本的なSwift SpriteKitの衝突

私が今持っているコード:プレイヤーはコインを通って移動しますが、衝突は発生せず、+1はコインのラベルに追加されません。

私はまだ素早い言語を学んでいますので、私は与えられた助けを感謝します。

コード:

struct ColliderType { 

static let playerCategory: UInt32 = 0x1 << 0 

static let boundary: UInt32 = 0x1 << 1 
​ 
​static let coinCategory: UInt32 = 0x1 << 2 
​ 
​static let bodyA: UInt32 = 0x1 << 4 
​ 
​static let bodyB: UInt32 = 0x1 << 8 

} 

​override func didMoveToView(view: SKView) { 
​ 
var coinInt = 0 
​ 
​ 
​ 
​self.physicsWorld.gravity = CGVectorMake(0.0, -7.0) 
physicsWorld.contactDelegate = self 

player = SKSpriteNode(imageNamed: "player") 
player.zPosition = 1 
player.position = CGPoint(x: CGRectGetMidX(self.frame), y: CGRectGetMidY(self.frame)) 
player.physicsBody = SKPhysicsBody(circleOfRadius: player.size.width/5.12) 
player.physicsBody?.dynamic = true 
player.physicsBody?.allowsRotation = false 

self.addChild(player) 

generateCoins() 

​ 
​ 
coin = SKSpriteNode(imageNamed: "coin") 
coin.physicsBody? = SKPhysicsBody(circleOfRadius: coin.size.height/10) 
coin.physicsBody?.dynamic = false 
coin.physicsBody?.allowsRotation = false 
coin.zPosition = 1 
​self.addChild(coin) 
​ 
player.physicsBody?.categoryBitMask = ColliderType.playerCategory 
​player.physicsBody?.contactTestBitMask = ColliderType.boundary 
player.physicsBody?.collisionBitMask = ColliderType.coinCategory | ColliderType.boundary 

coin.physicsBody?.categoryBitMask = ColliderType.coinCategory 
coin.physicsBody?.contactTestBitMask = ColliderType.playerCategory 
coin.physicsBody?.collisionBitMask = ColliderType.playerCategory 

func didPlayerCollideWithCoin(player: SKSpriteNode, coin: SKSpriteNode) { 



self.coin.removeFromParent() 

self.coin += 1 

coinLabel.text = "\(coinInt)" 

} 

​ 
​  
​ 
​func generateCoins() { 

if(self.actionForKey("spawning") != nil){return} 

let coinTimer = SKAction.waitForDuration(7, withRange: 2) 

let spawnCoin = SKAction.runBlock { 

self.coin = SKSpriteNode(imageNamed: "coin") 

self.coin.physicsBody = SKPhysicsBody(circleOfRadius: self.coin.size.height/10) 

self.coin.name = "coin" 

self.coin.physicsBody?.dynamic = false 

self.coin.physicsBody?.allowsRotation = false 

var coinPosition = Array<CGPoint>() 

coinPosition.append((CGPoint(x:340, y:103))) 

coinPosition.append((CGPoint(x:340, y:148))) 

coinPosition.append((CGPoint(x:340, y:218))) 

coinPosition.append((CGPoint(x: 340, y:343))) 

let spawnLocation =  coinPosition[Int(arc4random_uniform(UInt32(coinPosition.count)))] 

let action = SKAction.repeatActionForever(SKAction.moveToX(+self.xScale, duration: 4.4)) 

self.coin.runAction(action) 

self.coin.position = spawnLocation 

self.addChild(self.coin) 

print(spawnLocation) 

} 

let sequence = SKAction.sequence([coinTimer, spawnCoin]) 

self.runAction(SKAction.repeatActionForever(sequence), withKey: "spawning") 

} 
​​ 
func didBeginContact(contact:SKPhysicsContact) { 

let bodyA: SKPhysicsBody = contact.bodyA 

let bodyB: SKPhysicsBody = contact.bodyB 

if ((bodyA.categoryBitMask == ColliderType.playerCategory) &&  (bodyB.categoryBitMask == ColliderType.coinCategory)){ 

didPlayerCollideWithCoin(bodyA.node as! SKSpriteNode, coin: bodyB.node as! SKSpriteNode) 

} 
    ​   
​} 
+0

なぜ '(circleOfRadius:coinOne.size.height/10 ) '(circleOfRadius:coinOne.size.height/2)'ではないでしょうか? –

+0

「/」の後ろにある数字は、物理学の物理的な大きさを制御していると思いましたか?/2、または/ 3を使用した場合と同様に、より大きな数値を使用する場合に比べてphysicsBodyが大きくなります。私は間違っている可能性がある。 –

+0

半径(あなたの後ろにあるもの)は直径/ 2です。あなたのコインの高さ==コインの直径(これはおそらく)である場合、この値を2で割った値はおそらくあなたの後のサイズになります。 –

答えて

2

あなたは同じあなたcontactTestBitmasksを残してみたがプレーヤーとコインの間collisionBitmasks削除できます。プレイヤーは、それは意志のコインと衝突したとき、この道を

player.physicsBody?.categoryBitMask = ColliderType.playerCategory 
​player.physicsBody?.contactTestBitMask = ColliderType.boundary 
player.physicsBody?.collisionBitMask = ColliderType.boundary 


coin.physicsBody?.categoryBitMask = ColliderType.coinCategory 
coin.physicsBody?.contactTestBitMask = ColliderType.playerCategory 

をしかし、それは "跳ね返る"ことはなく、同じ方向に動いていきます。

*注:これを使用するには、代わりに

func didPlayerCollideWithCoin(player: SKSpriteNode, coin: SKSpriteNode) { 

func didBeginContact(contact: SKPhysicsContact) { 

メソッドを使用する必要かもしれませんが、私が最初にdidPlayerCollideWithCoin()メソッドでそれをしようとお勧めします。

あなたがそれを必要とする場合には、それは次のように実装されています。詳細については

func didBeginContact(contact: SKPhysicsContact) { 

var firstBody: SKPhysicsBody 
var secondBody: SKPhysicsBody 

if contact.bodyA.categoryBitMask < contact.bodyB.categoryBitMask { 
    firstBody = contact.bodyA 
    secondBody = contact.bodyB 
} else { 
firstBody = contact.bodyB 
secondBody = contact.bodyA 
} 

if firstBody.categoryBitMask == playerCategory && secondBody.categoryBitMask == coinCategory { 
print("Your player passes through the coin") 
score = score + 1 
} 
} 

はレイWenderlichからこのチュートリアルを参照してください。 https://www.raywenderlich.com/123393/how-to-create-a-breakout-game-with-sprite-kit-and-swift

+0

こんにちはhb22、あなたの答えをありがとう!あなたの回答に書いた内容と一致するようにコードを編集しました(didPlayerCollideWithCoinで最初に試してからdidBeginContactを試しました)が、何も変わっていませんでした。だから私は 'view.showsPhysics = true'を使ってphysicsBodysを確認しました。そして、私は、プレーヤーphysicsBodyが見えますが、物理学に気付きました。物理ノードを持っているにもかかわらず、 ' 自分の。私はそれが衝突が適切に機能するのを妨げる問題かもしれないと思う。 –

関連する問題