I'm still a beginner in Swift and I'm having some trouble with collision detections in SpriteKit. I used this question from StackOverFlow which was great in showing my how to construct things neatly. But I'm having problems with my didBegin
function, which does not even get called to at all. I'm hoping I missed something simple out that you guys can take a look at for me.
Thanks in advance.
Here is my PhysicsCatagoies struct:
import Foundation
import SpriteKit
struct PhysicsCatagories: OptionSet {
let rawValue: UInt32
init(rawValue: UInt32) { self.rawValue = rawValue }
static let None = PhysicsCatagories(rawValue: 0b00000) // Binary for 0
static let Player = PhysicsCatagories(rawValue: 0b00001) // Binary for 1
static let EnemyBullet = PhysicsCatagories(rawValue: 0b00010) // Binary for 2
static let PlayerBullet = PhysicsCatagories(rawValue: 0b00100) // Binary for 4
static let Enemy = PhysicsCatagories(rawValue: 0b01000) // Binary for 8
static let Boss = PhysicsCatagories(rawValue: 0b10000) // Binary for 16
}
extension SKPhysicsBody {
var category: PhysicsCatagories {
get {
return PhysicsCatagories(rawValue: self.categoryBitMask)
}
set(newValue) {
self.categoryBitMask = newValue.rawValue
}
}
}
And here is how I assigned my nodes in GameScene:
player.physicsBody = SKPhysicsBody(rectangleOf: player.size)
player.physicsBody!.affectedByGravity = false
player.physicsBody!.categoryBitMask = PhysicsCatagories.Player.rawValue
player.physicsBody!.collisionBitMask = PhysicsCatagories.None.rawValue
player.physicsBody!.category = [.Enemy, .EnemyBullet, .Boss]
bullet.physicsBody = SKPhysicsBody(rectangleOf: bullet.size)
bullet.physicsBody!.affectedByGravity = false
bullet.physicsBody!.categoryBitMask = PhysicsCatagories.PlayerBullet.rawValue
bullet.physicsBody!.collisionBitMask = PhysicsCatagories.None.rawValue
bullet.physicsBody!.category = [.Enemy, .Boss]
enemy.physicsBody = SKPhysicsBody(rectangleOf: enemy.size)
enemy.physicsBody!.affectedByGravity = false
enemy.physicsBody!.categoryBitMask = PhysicsCatagories.Enemy.rawValue
enemy.physicsBody!.collisionBitMask = PhysicsCatagories.None.rawValue
enemy.physicsBody!.category = [.Player, .PlayerBullet]
enemyBullet.physicsBody = SKPhysicsBody(rectangleOf: enemyBullet.size)
enemyBullet.physicsBody!.affectedByGravity = false
enemyBullet.physicsBody!.categoryBitMask = PhysicsCatagories.EnemyBullet.rawValue
enemyBullet.physicsBody!.collisionBitMask = PhysicsCatagories.None.rawValue
enemyBullet.physicsBody!.category = [.Player]
boss.physicsBody = SKPhysicsBody(rectangleOf: boss.size)
boss.physicsBody!.affectedByGravity = false
boss.physicsBody!.categoryBitMask = PhysicsCatagories.Boss.rawValue
boss.physicsBody!.collisionBitMask = PhysicsCatagories.None.rawValue
boss.physicsBody!.category = [.Player, .PlayerBullet]
bulletSpecial.physicsBody = SKPhysicsBody(rectangleOf: bulletSpecial.size)
bulletSpecial.physicsBody!.affectedByGravity = false
bulletSpecial.physicsBody!.categoryBitMask = PhysicsCatagories.PlayerBullet.rawValue
bulletSpecial.physicsBody!.collisionBitMask = PhysicsCatagories.None.rawValue
bulletSpecial.physicsBody!.category = [.Enemy, .Boss]
Finally, this is my didBegin
function, which does not seem to work at all:
func didBegin(_ contact: SKPhysicsContact) {
let contactCategory: PhysicsCatagories = [contact.bodyA.category, contact.bodyB.category]
switch contactCategory {
case [.Player, .Enemy]:
print("player has hit enemy")
case [.PlayerBullet, .Enemy]:
print("player bullet has hit enemy")
case [.PlayerBullet, .Boss]:
print("player bullet has hit boss")
case [.Player, .Boss]:
print("player has hit boss")
case [.Player, .EnemyBullet]:
print("player has hit enemy bullet")
default:
preconditionFailure("Unexpected collision type: \(contactCategory)")
}
}