我想在SpriteKit中检测两种冲突类型:
当ballOne击中goalOne而ballTwo击中goalTwo:
到目前为止,我已经添加了不同的物理类别:
struct physicsCategory {
static let ballOne :UInt32 = 0x1 << 0
static let goalOne :UInt32 = 0x1 << 1
static let ballTwo :UInt32 = 0x1 << 2
static let goalTwo :UInt32 = 0x1 << 3
}
这是我班上的相关部分:
class gameScene: SKScene, SKPhysicsContactDelegate {
var borderBody:SKPhysicsBody!
var myscore:Int = 0
var opponentScore:Int = 10
override func sceneDidLoad() {
super.sceneDidLoad()
physicsWorld.contactDelegate = self
}
func didBegin(_ contact: SKPhysicsContact) {
let firstBody = contact.bodyA.node as! SKSpriteNode
let secondBody = contact.bodyB.node as! SKSpriteNode
if ((firstBody.name == "ballOne") && (secondBody.name == "goalOne")) {
collisionGoalOne(BallOne: firstBody, GoalOne: secondBody)
}
else {
}
}
func collisionGoalOne(BallOne: SKSpriteNode, GoalOne: SKSpriteNode) {
addScore()
}
override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent?) {
let touch = touches.first
let touchLocation = touch!.location(in: self)
let ballOne = childNode(withName: "ballOne") as! SKSpriteNode
ballOne.physicsBody?.categoryBitMask = physicsCategory.ballOne
ballOne.physicsBody?.collisionBitMask = physicsCategory.goalOne
ballOne.physicsBody?.contactTestBitMask = physicsCategory.goalOne
ballOne.physicsBody?.isDynamic = true
let goalOne = childNode(withName: "goalOne") as! SKSpriteNode
goalOne.physicsBody?.categoryBitMask = physicsCategory.goalOne
goalOne.physicsBody?.collisionBitMask = physicsCategory.ballOne
goalOne.physicsBody?.contactTestBitMask = physicsCategory.ballOne
goalOne.physicsBody?.isDynamic = false
}
}
现在,当球与墙壁碰撞时,应用程序崩溃
let firstBody = contact.bodyA.node as! SKSpriteNode
“无法将类型'appName.gameScene'(0x105320)的值强制转换为'SKSpriteNode'(0x1877b5c)。”
很想了解为什么会发生此崩溃,以及这是否是处理冲突的好方法。谢谢。
最佳答案
FirstBody可能无法转换为SKSpriteNode,因此仅在检查哪些节点发生碰撞后才创建该变量。
请注意,ballOne可以是bodyA或bodyB,因此请更改代码以检查这两种可能性。
我对您的代码做了一些更改。希望这可以帮助
if ((contact.bodyA.node?.name == "ballOne") && (contact.bodyB.node?.name == "goalOne")) {
let firstBody = contact.bodyA.node as! SKSpriteNode
let secondBody = contact.bodyB.node as! SKSpriteNode
collisionGoalOne(BallOne: firstBody, GoalOne: secondBody)
} else if ((contact.bodyA.node?.name == "goalOne") && (contact.bodyB.node?.name == "ballOne")) {
let firstBody = contact.bodyA.node as! SKSpriteNode
let secondBody = contact.bodyB.node as! SKSpriteNode
collisionGoalOne(BallOne: secondBody, GoalOne: firstBody)
}