沿运动方向旋转物体

Lah*_*hav 1 vector rotation sprite-kit skspritenode swift

是否有一种相对简单的方法来旋转SKSpriteNode,使其始终面向它正在移动的方向?我的类Gamescene有一个物体系统,它们的相对物理体在碰撞时互相施加冲动.这使得跟踪对象移动的确切方向变得相对困难.一些对象也没有规律地形状,这使得事情变得更加混乱.我尝试过使用三角函数(例如arctangent),但它只能在非常特殊的情况下使用.可能有办法找出SKSpriteNode轨迹的角度,以便我可以将对象旋转到该角度?感谢您的任何帮助,您可以提供!

编辑:

我为CGVector创建了一个扩展,并尝试在两个对象相撞时,在其速度方向上旋转SKSpriteNode(感谢0x141E),但它似乎没有正常工作

func didBeginContact(contact: SKPhysicsContact) {
    var firstBody : SKPhysicsBody = contact.bodyA
    var secondBody : SKPhysicsBody = contact.bodyB
    if ((firstBody.categoryBitMask == PhysicsCatagory.Blade) && (secondBody.categoryBitMask == PhysicsCatagory.Laser))
    {
        if (secondBody.node != nil)
        {
            if (saberAngle <= 0 && LCR == 1) // Blade pointing right
            {
                let rebound = CGVectorMake(-reboundStrength*sin(1.5707 + saberAngle), reboundStrength*cos(1.5707 + saberAngle))
                secondBody.applyImpulse(rebound)
            }
            else if (saberAngle > 0 && LCR == -1) // Blade pointing left
            {
                let rebound = CGVectorMake(reboundStrength*sin(1.5707 - saberAngle), reboundStrength*cos(1.5707 - saberAngle))
                secondBody.applyImpulse(rebound)
            }
            if (secondBody.velocity.speed() > 0.01){
                (secondBody.node as! SKSpriteNode).zRotation = secondBody.velocity.angle() - offset
            }
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

我没有在didSimulatePhysics()方法中这样做,因为有时候我试图旋转的节点不存在,并且我会得到诸如"使用未解析的标识符'sprite'"之类的错误

编辑:

我通过简单地创建和运行一个名为rotate的动作来实现它的工作,该动作将精灵旋转到secondBody.velocity.angle() - offset,但我仍然很好奇为什么我的代码在^^之前没有工作

0x1*_*41E 9

在运动方向上旋转精灵是相当简单的.您可以通过将精灵的速度xy组件转换为与atan2函数成一个角度来实现.只有当精灵的速度大于某个标称值时才应该旋转精灵,以防止精灵在精灵的速度(接近)为零时重置为零度.

如果我们扩展CGVector到从速度的分量计算速度和角度

extension CGVector {
    func speed() -> CGFloat {
        return sqrt(dx*dx+dy*dy)
    }
    func angle() -> CGFloat {
        return atan2(dy, dx)
    }
}
Run Code Online (Sandbox Code Playgroud)

我们可以旋转一个精灵来朝向它的运动方向

override func didSimulatePhysics() {
    if let body = sprite.physicsBody {
        if (body.velocity.speed() > 0.01) {
            sprite.zRotation = body.velocity.angle() - offset
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

offset = CGFloat(M_PI_2)如果你的精灵在zRotation零时面朝上,如果你的精灵在零时offset = 0朝向右边zRotation.

  • 您不能使用`SKAction`来使用此方法旋转精灵,因为`didSimulatePhysics`被调用〜每秒60次.操作需要时间来执行,但下一个操作会覆盖当前操作. (2认同)