从.dae文件中提取CAAnimation,这样我就可以使用setAnimationSpeed来改变速度

时间:2017-09-11 16:48:19

标签: xcode animation scenekit caanimation

我有一个火车的.dae文件动画,我试图将火车的动画提取为CAAnimation,这样我就可以使用setAnimationSpeed函数来改变它的速度。 / p>

到目前为止,我已经有了场景资产的声明:

struct Assets {
        static let basePath = "art.scnassets/"

        static func animation(named name: String) -> CAAnimation {
            return CAAnimation.animation(withSceneName: basePath + name)
        }

        static func scene(named name: String) -> SCNScene {
            guard let scene = SCNScene(named: name) else {
                fatalError("Failed to load scene \(name).")
            }
            return scene
        }
    }

使用此扩展程序存储动画:

extension CAAnimation {
    class func animation(withSceneName name: String) -> CAAnimation {
        guard let scene = SCNScene(named: name) else {
            fatalError("Failed to find scene with name \(name).")
        }

        var animation: CAAnimation?
        scene.rootNode.enumerateChildNodes { (child, stop) in
            guard let firstKey = child.animationKeys.first else { return }
            animation = child.animation(forKey: firstKey)
            stop.initialize(to: true)
        }

        guard let foundAnimation = animation else {
            fatalError("Failed to find animation named \(name).")
        }
        return foundAnimation
    }
}

然后我设置SCNScene并初始化动画:

let scene = Assets.scene(named: "Astro_Train_Loop_V1.dae")

let trainAnimationName: String?

required init?(coder: NSCoder) {
      trainAnimationName = scene.rootNode.animationKeys.first
      super.init(coder: coder)
      }

最后在viewDidLoad()中,我调用一个函数,它从用户输入中执行一堆数学运算,更新速度,并将其应用于动画:

 func updateSpeed () {

    SCNTransaction.begin()
    scene.rootNode.setAnimationSpeed(CGFloat(effectiveSpeed), forKey: trainAnimationName!)
    SCNTransaction.commit()

}

现在最后一点是我得到致命错误:在解开可选值时意外发现nil 我采取的意思是trainAnimationName!是空的,或者没有功能需要的东西......

setAnimationSpeed需要动画的名称(String),但这不是从animation()扩展名返回的内容,是吗?

我知道.dae文件有动画,因为它在构建项目时循环播放。请在缺失的链接上帮助提供一个总Noob!

干杯。

更新:根据该参考资料(相关),我设法将我的问题提炼到这个解释版本:

let train: SCNNode = scene.rootNode.childNode(withName: "Astro_Train_Loop_V1.dae", recursively: true)!
let trainAnimation: CAAnimation = train.animation(forKey: "Astro_Train_Loop_V1.dae")!
let trainAnimationGroup: CAAnimationGroup = (trainAnimation as? CAAnimationGroup)!

for key in trainAnimationGroup.animations [] {
    let animation: CAAnimation = train.animation(forKey: key)!
    animation.speed = 0

}

现在,这给了我一个错误,因为数组trainAnimationGroup.animations是空的。因此,一旦我们有一组动画(动画场景文件中的所有节点),我们就可以循环播放它并改变每个动画的速度。大!但动画阵列如何充满动画?我们已经确定我们有一个包含动画的CAAnimation,并且我们已经建立了animationGroup,它是一组动画。如何使用这些动画填充此数组?再次感谢你!

0 个答案:

没有答案