我正在尝试制作一个“发射(呃)游戏”,即使用SpriteKit以Toss the turle,Learn to fly和Burrito Bison的风格进行游戏。我已经使用SpriteKit的内置物理开始工作了,但是当我尝试使用SKCameraNode来跟随主角时,看起来总是一个(或更多)步骤使主角“摇动” “在高速下。
我已尝试使用SKAction和.position-property设置摄像机的位置,结果相同。
我想这是因为物理更新的速度比实际更新速度快(),我尝试搜索有关此内容的信息,但发现了zilch。
“启动”主角的功能:
func touchStopped(touchPoint: CGPoint) {
if !inAir {
arrow.removeFromParent()
inAir = true
mainCharNode.physicsBody = SKPhysicsBody(circleOfRadius: mainCharNode.size.width/2)
mainCharNode.physicsBody?.mass = mainChar.mass
mainCharNode.physicsBody?.restitution = mainChar.restitution
mainCharNode.physicsBody?.linearDamping = mainChar.airResistance
mainCharNode.physicsBody?.velocity = CGVectorMake(touchPoint.x*2, touchPoint.y)
mainCharNode.physicsBody?.categoryBitMask = mainCategory
mainCharNode.physicsBody?.collisionBitMask = groundCategory
} else {
mainCharNode.physicsBody?.applyImpulse(CGVectorMake(10000, 10000))
}
}
更新() - 功能:
override func update(currentTime: CFTimeInterval) {
if lastUpdateTime > 0 {
dt = currentTime - lastUpdateTime
} else {
dt = 0
}
lastUpdateTime = currentTime
if mainCharNode.position.x > 1000 {
let moveCamera = SKAction.moveTo(CGPoint(x: mainCharNode.position.x, y: cameraNode.position.y), duration: dt)
cameraNode.runAction(moveCamera)
}
if(inAir && !gameOver) {
distance += (mainCharNode.physicsBody?.velocity.dx)!*CGFloat(dt)
if(mainCharNode.physicsBody?.velocity == CGVector(dx: 0,dy: 0)) {
gameOver = true
mainCharNode.physicsBody?.dynamic = false
}
}
}
https://github.com/CalleLundstedt/LauncherGame这是github上的完整项目。
答案 0 :(得分:2)
通过在LinearLayout
中手动设置相机位置,您将相机移动至少延迟一帧 - 物理在update
之后运行,因此在角色移动后相机会在帧上移动
当您使用移动操作而不是直接设置位置,并将该操作设置为非零持续时间时,您将延迟相机移动。 (代码中的update
是此帧与之前的最后一帧之间的时间,您将该时间应用于 future 运动。)因为角色仍在移动你的动作运行,相机永远不会赶上 - 你总是将相机移动到角色 的位置。
完全设置相机位置只是为自己做了额外的工作。使用SKConstraint
代替,SpriteKit本身将确保相机位置贴在角色上 - 它在物理学之后解决了约束,但是在同一帧上。