Swift 套现层复制品
我试图在给定的x和y坐标下每隔20毫秒添加一次CAShapelayer。我想形状消失了一秒钟(像一个跟踪器)。我创建的功能可以正常工作,形状在正确的位置创建并逐渐消失。但我得到了多余的形状留下混乱的屏幕上Swift 套现层复制品,swift,cashapelayer,cabasicanimation,Swift,Cashapelayer,Cabasicanimation,我试图在给定的x和y坐标下每隔20毫秒添加一次CAShapelayer。我想形状消失了一秒钟(像一个跟踪器)。我创建的功能可以正常工作,形状在正确的位置创建并逐渐消失。但我得到了多余的形状留下混乱的屏幕上 func shadowBall (x: CGFloat, y: CGFloat){ let xpos : CGFloat = ((self.frame.width/2) + x) let ypos : CGFloat = ((self.frame.height/2) + y)
func shadowBall (x: CGFloat, y: CGFloat){
let xpos : CGFloat = ((self.frame.width/2) + x)
let ypos : CGFloat = ((self.frame.height/2) + y)
let shadowBall = CAShapeLayer()
let shadowBalllRadius :CGFloat = 4
let shadowBallPath : UIBezierPath = UIBezierPath(ovalInRect: CGRect(x: xpos, y: ypos, width: CGFloat(shadowBalllRadius*2), height: CGFloat(shadowBalllRadius*2)))
shadowBall.path = shadowBallPath.CGPath
shadowBall.fillColor = UIColor.clearColor().CGColor
shadowBall.strokeColor = UIColor.whiteColor().CGColor
shadowBall.lineWidth = 0.5
let animation: CABasicAnimation = CABasicAnimation(keyPath: "strokeColor")
animation.fromValue = UIColor.whiteColor().CGColor
animation.toValue = UIColor.clearColor().CGColor
animation.duration = 1.0;
animation.repeatCount = 0;
animation.removedOnCompletion = true
animation.additive = false
self.layer.addSublayer(shadowBall)
shadowBall.addAnimation(animation, forKey: "strokeColor")
}
问题是,当动画完成时,它会将
strokeColor
恢复为原始颜色。您应该将原始形状层的strokeColor
设置为clearColor()
,这样,当您完成从whiteColor()
到clearColor()
的动画制作时,它将保持在clearColor()
您还可以将层的fillMode
设置为kCAFillModeForwards
,并将removedOnCompletion
设置为false
,这样层将保持其“动画结束”状态。但我个人只会按照上面所述设置strokeColor
,因为使用true
的removedOnCompletion
会干扰animationDidStop
(见下文)
此外,我可能建议您在动画完成后删除该层,这样它就不会继续消耗内存,尽管它不再可见
func shadowBall (x: CGFloat, y: CGFloat) {
let xpos: CGFloat = ((self.frame.width/2) + x)
let ypos: CGFloat = ((self.frame.height/2) + y)
let shadowBall = CAShapeLayer()
let shadowBalllRadius: CGFloat = 4
let shadowBallPath = UIBezierPath(ovalInRect: CGRect(x: xpos, y: ypos, width: CGFloat(shadowBalllRadius*2), height: CGFloat(shadowBalllRadius*2)))
shadowBall.path = shadowBallPath.CGPath
shadowBall.fillColor = UIColor.clearColor().CGColor
shadowBall.strokeColor = UIColor.clearColor().CGColor
shadowBall.lineWidth = 0.1
let animation = CABasicAnimation(keyPath: "strokeColor")
animation.fromValue = UIColor.whiteColor().CGColor
animation.toValue = UIColor.clearColor().CGColor
animation.duration = 1.0
animation.repeatCount = 0
animation.removedOnCompletion = true
animation.additive = false
animation.delegate = self
animation.setValue(shadowBall, forKey: "animationLayer")
self.layer.addSublayer(shadowBall)
shadowBall.addAnimation(animation, forKey: "strokeColor")
}
override func animationDidStop(anim: CAAnimation, finished flag: Bool) {
if let layer = anim.valueForKey("animationLayer") as? CALayer {
layer.removeFromSuperlayer()
}
}
请参见问题在于,当动画完成时,它会将
strokeColor
恢复为原始颜色。您应该将原始形状层的strokeColor
设置为clearColor()
,这样,当您完成从whiteColor()
到clearColor()
的动画制作时,它将保持在clearColor()
您还可以将层的fillMode
设置为kCAFillModeForwards
,并将removedOnCompletion
设置为false
,这样层将保持其“动画结束”状态。但我个人只会按照上面所述设置strokeColor
,因为使用true
的removedOnCompletion
会干扰animationDidStop
(见下文)
此外,我可能建议您在动画完成后删除该层,这样它就不会继续消耗内存,尽管它不再可见
func shadowBall (x: CGFloat, y: CGFloat) {
let xpos: CGFloat = ((self.frame.width/2) + x)
let ypos: CGFloat = ((self.frame.height/2) + y)
let shadowBall = CAShapeLayer()
let shadowBalllRadius: CGFloat = 4
let shadowBallPath = UIBezierPath(ovalInRect: CGRect(x: xpos, y: ypos, width: CGFloat(shadowBalllRadius*2), height: CGFloat(shadowBalllRadius*2)))
shadowBall.path = shadowBallPath.CGPath
shadowBall.fillColor = UIColor.clearColor().CGColor
shadowBall.strokeColor = UIColor.clearColor().CGColor
shadowBall.lineWidth = 0.1
let animation = CABasicAnimation(keyPath: "strokeColor")
animation.fromValue = UIColor.whiteColor().CGColor
animation.toValue = UIColor.clearColor().CGColor
animation.duration = 1.0
animation.repeatCount = 0
animation.removedOnCompletion = true
animation.additive = false
animation.delegate = self
animation.setValue(shadowBall, forKey: "animationLayer")
self.layer.addSublayer(shadowBall)
shadowBall.addAnimation(animation, forKey: "strokeColor")
}
override func animationDidStop(anim: CAAnimation, finished flag: Bool) {
if let layer = anim.valueForKey("animationLayer") as? CALayer {
layer.removeFromSuperlayer()
}
}
请参见精彩而简单,感谢您的快速回复。这个问题困扰了我一段时间…聪明而简单,谢谢你的快速回复。这个问题困扰了我一段时间……与此无关,但我发现“每隔20毫秒”非常接近(但不等于)60 fps的最大帧速率。您是否正在使用
NSTimer
进行此操作?为什么不使用一个CADisplayLink
,它本质上是一个为帧更新而优化的计时器?我有一个刷新频率最高为50Hz的BLE设备。。。因此20ms是相关的,但我发现“每隔20ms”非常接近(但不等于)60 fps的最大帧速率。您是否正在使用NSTimer
进行此操作?为什么不使用一个CADisplayLink
,它本质上是一个为帧更新而优化的计时器?我有一个刷新频率最高为50Hz的BLE设备。。。因此20毫秒