由于您没有提供任何代码(下次请务必提供),我将提供一个解决方案,应该能指引您正确的方向。
让我们从创建一个PathItem类
开始,我们将使用它来创建完整的路径,例如一行路径:
class PathItem: SCNNode{
init(size: CGFloat = 0.2, texture: UIColor, position: SCNVector3){
super.init()
let pathGeometry = SCNPlane(width: size, height: size)
pathGeometry.firstMaterial?.diffuse.contents = texture
self.geometry = pathGeometry
self.position = position
self.eulerAngles.x = GLKMathDegreesToRadians(-90)
}
required init?(coder aDecoder: NSCoder) { fatalError("Path Item Coder Has Not Been Implemented") }
}
现在已经完成了这个步骤,让我们创建一个func
来创建一条PathItem
(路径)。
首先要创建一个全局变量,它引用每个PathItem
的大小:
let pathItemSize: CGFloat = 0.2
接下来我们创建一个函数,该函数交替改变每个PathItem
的颜色,并为它们提供独特的name
或索引,以便在后面的动画中使用:
func createdPathOfSize(_ numberOfElements: Int) {
var pathColour: UIColor!
for pathIndex in 0 ..< numberOfElements{
let pathPosition = SCNVector3(0, -0.2, -pathItemSize * CGFloat(pathIndex+1))
if pathIndex % 2 == 0 { pathColour = UIColor.white } else { pathColour = UIColor.black }
let pathItem = PathItem(texture: pathColour, position: pathPosition)
pathItem.name = String(pathIndex)
pathItem.isHidden = true
self.augmentedRealityView.scene.rootNode.addChildNode(pathItem)
}
}
为了生成一个
Path
,我们现在可以这样做:
override func viewDidLoad() {
super.viewDidLoad()
augmentedRealityView.session = augmentedRealitySession
sessionConfiguration.planeDetection = .horizontal
augmentedRealityView.debugOptions = .showFeaturePoints
augmentedRealitySession.run(sessionConfiguration, options: [.resetTracking, .removeExistingAnchors])
createdPathOfSize(10)
}
我有以下的全局变量
:
@IBOutlet var augmentedRealityView: ARSCNView!
let augmentedRealitySession = ARSession()
let sessionConfiguration = ARWorldTrackingConfiguration()
现在我们已经生成了路径,需要对其进行动画处理!
为了增加一些多样性,让我们创建一个枚举类型,以便创建不同的路径动画:
enum AnimationType
由于我们将进行一些动画效果,因此让我们创建2个全局变量,用于在计时器上运行我们的动画并跟踪我们的进度:
var pathAnimationTimer: Timer?
var time: Int = 0
现在让我们创建我们的动画函数:
func animatePathElements(_ numberOfElements: Int, withAnimation animation: AnimationType ){
if animation == .FlipIn {
let pathItems = self.augmentedRealityView.scene.rootNode.childNodes
pathItems.forEach({ (pathItemToAnimate) in
pathItemToAnimate.isHidden = false
pathItemToAnimate.eulerAngles.x = GLKMathDegreesToRadians(0)
})
}
pathAnimationTimer = Timer.scheduledTimer(withTimeInterval: 0.25, repeats: true) { timer in
if self.time != numberOfElements{
guard let pathItemToAnimate = self.augmentedRealityView.scene.rootNode.childNode(withName: "\(self.time)", recursively: false) else { return }
switch animation{
case .UnHide:
pathItemToAnimate.isHidden = false
case .FadeIn:
pathItemToAnimate.isHidden = false
pathItemToAnimate.opacity = 0
let fadeInAction = SCNAction.fadeOpacity(to: 1, duration: 0.25)
pathItemToAnimate.runAction(fadeInAction)
case .FlipIn:
pathItemToAnimate.eulerAngles.x = GLKMathDegreesToRadians(-90)
}
self.time += 1
}else{
self.pathAnimationTimer?.invalidate()
self.time = 0
}
}
}
我们需要将以下内容添加到我们的createPathOfSize函数的末尾:
func createdPathOfSize(_ numberOfElements: Int) {
var pathColour: UIColor!
for pathIndex in 0 ..< numberOfElements{
let pathPosition = SCNVector3(0, -0.2, -pathItemSize * CGFloat(pathIndex+1))
if pathIndex % 2 == 0 { pathColour = UIColor.white } else { pathColour = UIColor.black }
let pathItem = PathItem(texture: pathColour, position: pathPosition)
pathItem.name = String(pathIndex)
pathItem.isHidden = true
self.augmentedRealityView.scene.rootNode.addChildNode(pathItem)
}
animatePathElements(10, withAnimation: .FlipIn)
}
以下是完整的示例:
import UIKit
import ARKit
enum AnimationType{
case UnHide
case FadeIn
case FlipIn
}
class PathItem: SCNNode{
init(size: CGFloat = 0.2, texture: UIColor, position: SCNVector3){
super.init()
let pathGeometry = SCNPlane(width: size, height: size)
pathGeometry.firstMaterial?.diffuse.contents = texture
self.geometry = pathGeometry
self.position = position
self.eulerAngles.x = GLKMathDegreesToRadians(-90)
}
required init?(coder aDecoder: NSCoder) { fatalError("Path Item Coder Has Not Been Implemented") }
}
class ViewController: UIViewController {
typealias PATH = SCNNode
@IBOutlet var augmentedRealityView: ARSCNView!
let augmentedRealitySession = ARSession()
let sessionConfiguration = ARWorldTrackingConfiguration()
var pathPlaced = false
let pathItemSize: CGFloat = 0.2
var pathAnimationTimer: Timer?
var time: Int = 0
override func viewDidLoad() {
super.viewDidLoad()
augmentedRealityView.session = augmentedRealitySession
sessionConfiguration.planeDetection = .horizontal
augmentedRealityView.debugOptions = .showFeaturePoints
augmentedRealitySession.run(sessionConfiguration, options: [.resetTracking, .removeExistingAnchors])
createdPathOfSize(10)
}
func animatePathElements(_ numberOfElements: Int, withAnimation animation: AnimationType ){
if animation == .FlipIn {
let pathItems = self.augmentedRealityView.scene.rootNode.childNodes
pathItems.forEach({ (pathItemToAnimate) in
pathItemToAnimate.isHidden = false
pathItemToAnimate.eulerAngles.x = GLKMathDegreesToRadians(0)
})
}
pathAnimationTimer = Timer.scheduledTimer(withTimeInterval: 0.25, repeats: true) { timer in
if self.time != numberOfElements{
guard let pathItemToAnimate = self.augmentedRealityView.scene.rootNode.childNode(withName: "\(self.time)", recursively: false) else { return }
switch animation{
case .UnHide:
pathItemToAnimate.isHidden = false
case .FadeIn:
pathItemToAnimate.isHidden = false
pathItemToAnimate.opacity = 0
let fadeInAction = SCNAction.fadeOpacity(to: 1, duration: 0.3)
pathItemToAnimate.runAction(fadeInAction)
case .FlipIn:
pathItemToAnimate.eulerAngles.x = GLKMathDegreesToRadians(-90)
}
self.time += 1
}else{
self.pathAnimationTimer?.invalidate()
self.time = 0
}
}
}
func createdPathOfSize(_ numberOfElements: Int) {
var pathColour: UIColor!
for pathIndex in 0 ..< numberOfElements{
let pathPosition = SCNVector3(0, -0.2, -pathItemSize * CGFloat(pathIndex+1))
if pathIndex % 2 == 0 { pathColour = UIColor.white } else { pathColour = UIColor.black }
let pathItem = PathItem(texture: pathColour, position: pathPosition)
pathItem.name = String(pathIndex)
pathItem.isHidden = true
self.augmentedRealityView.scene.rootNode.addChildNode(pathItem)
}
animatePathElements(10, withAnimation: .FlipIn)
}
}
这应该足以为您指明正确的方向^_____^。