如何使用CAKeyframeAnimation实现SceneKit节点旋转与飞机飞行动画
SceneKit 飞机路径飞行动画实现方案
方案1:优化SCNAction实现带平滑过渡的方形路径
你需要的动作叠加效果可以通过SCNAction.sequence嵌套SCNAction.group实现,将转弯动作和前后段的移动动作做时间重叠,同时添加缓动效果提升真实感:
func animateAirplaneSmoothSquare(nodeToAnimate: SCNNode) { let overlapTurnDuration: TimeInterval = 0.8 // 转弯和移动的重叠时间 let straightMoveDuration: TimeInterval = 2 // 纯直飞的时长 // 第一段X轴移动:总时长包含直飞+重叠转弯阶段 let moveXFull = SCNAction.moveBy(x: 1, y: 0, z: 0, duration: straightMoveDuration + overlapTurnDuration) moveXFull.timingMode = .easeOut // 快进入转弯时减速更符合真实飞行逻辑 let waitForStraight = SCNAction.wait(duration: straightMoveDuration) // 转弯阶段同步执行:旋转+启动Z轴移动 let rotateRight = SCNAction.rotateBy(x: 0, y: -CGFloat(deg2rad(90)), z: 0, duration: overlapTurnDuration * 2) rotateRight.timingMode = .easeInEaseOut let moveZFull = SCNAction.moveBy(x: 0, y: 0, z: 1, duration: straightMoveDuration + overlapTurnDuration) moveZFull.timingMode = .easeIn // 组合动作序列 let turnPhase = SCNAction.group([rotateRight, moveZFull]) let fullSequence = SCNAction.sequence([ SCNAction.group([moveXFull, waitForStraight]), turnPhase ]) // 循环4次即可实现完整方形路径飞行 nodeToAnimate.runAction(SCNAction.repeatForever(fullSequence)) }
方案2:CAKeyframeAnimation实现环形/任意路径飞行
这是更推荐的方案,无需手动拼接旋转和位移动画,系统可以自动处理沿路径的朝向:
原有代码问题修正
你之前的实现存在两个核心问题:
rotation关键帧的取值应为SCNVector4(x/y/z为旋转轴,w为旋转弧度),而非SCNVector3- 旋转动画和位移动画的时间轴未对齐,导致动作节奏不匹配
环形路径实现代码
func animateAirplaneCirclePath(nodeToAnimate: SCNNode) { let circleRadius: CGFloat = 2 // 环形路径半径,单位和3D场景单位保持一致 // 生成环形路径,可替换为矩形、自定义曲线路径 let flightPath = UIBezierPath(ovalIn: CGRect(x: -circleRadius, y: -circleRadius, width: circleRadius*2, height: circleRadius*2)) let positionAnim = CAKeyframeAnimation(keyPath: "position") positionAnim.path = flightPath.cgPath positionAnim.duration = 8 // 飞一圈的总时长 positionAnim.repeatCount = .infinity positionAnim.calculationMode = .paced // 保持匀速飞行 // 自动沿路径切线调整朝向,无需单独写旋转动画 positionAnim.rotationMode = .rotateAuto // 根据你的飞机模型默认朝向调整偏移量即可 positionAnim.rotationOffset = .pi / 2 nodeToAnimate.addAnimation(positionAnim, forKey: "circleFlight") }
如果要实现方形路径,将UIBezierPath的生成逻辑替换为矩形绘制即可,还可以添加圆角实现平滑转弯效果。如果需要模拟真实飞机转弯时的侧倾效果,可以额外添加一个Z轴旋转的关键帧动画,和位移动画的时间轴对齐即可。
内容的提问来源于stack exchange,提问作者Damiano Miazzi
相关产品推荐
相关产品推荐

