2016-04-16 22 views
-1

私は初めてiOS用のゲームを構築しています。私は非常に近いですが、私は衝突の検出を早くしてから何かを変えました。私は取り戻そうとしましたが、うまくいきませんでした。これは私がこれまで持っていたものですが、何も働いていません。私は、私がオンラインで見つけた衝突検出のさまざまなバージョンを試していますが、私はこれを動作させるために固執しています。私が間違ったところを理解していないだけです。衝突検出の問題swift 2.0 spritekit

ありがとうございます。

import SpriteKit 
enum ColliderType: UInt32 { 
    case Player = 1 
    case Traffic = 2 
} 


class GameScene: SKScene, SKPhysicsContactDelegate { 
    override func didMoveToView(view: SKView) { 

createWalls() 

    self.backgroundColor = SKColor.whiteColor() 
    self.physicsWorld.gravity = CGVectorMake(0, 0) 

    player.physicsBody = SKPhysicsBody(rectangleOfSize: player.size) 
    player.physicsBody?.dynamic = true 

    player.physicsBody!.categoryBitMask = ColliderType.Player.rawValue 
    player.physicsBody!.contactTestBitMask = ColliderType.Traffic.rawValue 

    player.zPosition = 3 
    player.name = "player" 
    player.position = CGPoint(x: self.frame.midX, y: (self.frame.midY)/3) 
    player.setScale(1.0) 

    self.addChild(player) 

    _ = NSTimer.scheduledTimerWithTimeInterval(2.5, target: self, selector: #selector(GameScene.makeTraffic), userInfo: nil, repeats: true) 
} 

func makeTraffic(){ 

    var aNumber = Int(arc4random_uniform(2)) 

    let Pos1 = Int(self.frame.midX/2)+30 
    let Pos2 = Int((self.frame.size.width)/2) 
    let Pos3 = Int(self.frame.size.width-300) 

    let array = [Pos1, Pos2, Pos3] 
    let randomIndex = Int(arc4random_uniform(UInt32(array.count))) 
    let randomPOS = CGPoint(x:Int(array[randomIndex]), y:Int(self.frame.height)) 

    if aNumber == 0 { 
     aNumber = aNumber + 1 
    } 

    switch aNumber { 
    case 1: 
     let car1 = SKSpriteNode(imageNamed: "Car_Green_Front") 
     car1.position = randomPOS 
     car1.zPosition = 3 
     car1.setScale(1.0) 

     car1.physicsBody = SKPhysicsBody(rectangleOfSize: car1.size) 
     car1.physicsBody?.dynamic = true 
     car1.physicsBody!.categoryBitMask = ColliderType.Player.rawValue 
     car1.physicsBody!.contactTestBitMask = ColliderType.Traffic.rawValue 

     self.addChild(car1) 
    case 2: 
     let car2 = SKSpriteNode(imageNamed: "Car_Purple_Front") 
     car2.position = randomPOS 
     car2.zPosition = 3 
     car2.setScale(1.0) 

     car2.physicsBody = SKPhysicsBody(rectangleOfSize: car2.size) 
     car2.physicsBody?.dynamic = true 
     car2.physicsBody!.categoryBitMask = ColliderType.Traffic.rawValue 
     car2.physicsBody!.contactTestBitMask = ColliderType.Player.rawValue 

     self.addChild(car2) 
    default: 
     return 
    } 
} 

func createWalls(){ 
    let wallSize = CGSize(width: 5, height: self.frame.size.height) 

    let rightwall = SKShapeNode(rectOfSize: wallSize) 
    rightwall.physicsBody = SKPhysicsBody(rectangleOfSize: wallSize) 
    rightwall.physicsBody!.dynamic = false 

    rightwall.position = CGPoint(x: self.frame.maxX-300, y: self.frame.size.height/2) 
    rightwall.fillColor = UIColor.clearColor() 
    self.addChild(rightwall) 

    let leftwall = SKShapeNode(rectOfSize: wallSize) 
    leftwall.physicsBody = SKPhysicsBody(rectangleOfSize: wallSize) 
    leftwall.physicsBody!.dynamic = false 

    leftwall.position = CGPoint(x: self.frame.minX+300, y: self.frame.size.height/2) 
    leftwall.fillColor = UIColor.clearColor() 
    self.addChild(leftwall) 
} 

func didBeginContact(contact: SKPhysicsContact) { 
print("Contact") 

if contact.bodyA.categoryBitMask == ColliderType.Traffic.rawValue && contact.bodyB.categoryBitMask == ColliderType.Player.rawValue { 

print("Hi") 

} else { 

print("Hello") } 

} 

}

+0

@ crashoverride777が彼の答えを指摘しているように、physicsWorldの代理人を設定していないので、didBeginContactはまったく起動されませんでした。それ以外にも、命名規則に従ってください。 variableName、methodName、ClassName、ProtocolName、StructNameなど... [Camel Case](https://en.wikipedia.org/wiki/CamelCase)を参照してください。それは必須ではありませんが、それはAppleのお勧めです(そして、StackOverflow上でコードが適切にフォーマットされるのに役立ちます)。 – Whirlwind

答えて

3

あなたのコードは、私はなるだろういくつかの小さな変更はあるものの、alriteようです。

1)この方法は、あなただけの1 あなたの方法で、最後の番号をインクリメントする必要があるので、私はあなたがより多くのカテゴリを追加することにした場合、次のいずれかを持っていますので、

struct ColliderType { 
    static let player: UInt32 = 0x1 << 0 
    static let traffic: UInt32 = 0x1 << 1 
} 

ように私のコライダーのタイプを記述します16など、より混乱している(あなたが32ビットの整数を扱っている)

それはそう

...categoryBitMask = ColliderType.player 

2のような使用より)それはよりも、8よりも、4であることをphysicsBodyを追加する前にスプライトの位置を指定することをお勧めします。あなたは予期せぬ問題を引き起こす可能性のある他の方法でそれをやっています。

3)あなたの衝突方法は、この

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 == ColliderType.player) && (secondBody.categoryBitMask == ColliderType.traffic) { 
     // player hit traffic, do something 
    } 
} 

4に変更します)最後に、最も重要な部分は、あなたが私はあなたのコードでは見ることができなかったデリゲートを設定する必要があるということです。 DidMoveToView

physicsWorld.contactDelegate = self 

コールこのそうDidBeginContact方法が起動することはありません。

また、リンゴの命名規則に従うとよいでしょう。したがって、クラス、プロトコル、列挙型、構造体だけが大文字で始まる必要があります。

希望これはdidBeginContactをコーディングする

+0

ありがとうございます、それは動作します。私は物理学を持たずにそれを見ることがわかっている世界のコードは私が一番欠けていたものだった。残りは素晴らしい作品です。 –

+0

あなたは大歓迎です。ハッピーコーディング – crashoverride777

0

きれいな方法があるのに役立ちます:

func didBeginContact(contact: SKPhysicsContact) { 
    let contactMask = contact.bodyA.categoryBitMask | contact.bodyB.categoryBitMask 

    switch contactMask { 

    case ColliderType.player | ColliderType.traffic: 
     // player and traffic have contacted 
     print("Collision between player and traffic") 

    default : 
     //Some other contact has occurred 
     print("Some other contact") 
    } 
} 

あなたが好きなようにあなたがcase ColliderType.object1 | ColliderType.object2:できるだけ多くを追加することができます。