2016-05-26 14 views
6

Tôi muốn tạo lại màu nền với màu sắc khác nhau khi hoạt ảnh. Tôi có thể tạo thành công màu gradient bằng mã này.Tái tạo nền với màu sắc khác nhau nhanh chóng trong ios

let dayTopColor = CommonUtils.colorWithHexString("955EAC") 
let dayBottomColor = CommonUtils.colorWithHexString("9F3050") 
let dayToTopColor = CommonUtils.colorWithHexString("D15B52") 
let dayToBottomColor = CommonUtils.colorWithHexString("CC4645") 
let nightTopColor = CommonUtils.colorWithHexString("2D5E7C") 
let nightBottomColor = CommonUtils.colorWithHexString("19337D") 
let nightToTopColor = CommonUtils.colorWithHexString("21334E") 
let nightToBottomColor = CommonUtils.colorWithHexString("101A55") 
var isInSaudiArabia = false 
var gradient : CAGradientLayer? 
var toColors : AnyObject? 
var fromColors : AnyObject? 

func animateBackground(){ 
     var layerToRemove: CAGradientLayer? 
     for layer in self.view.layer.sublayers!{ 
      if layer.isKindOfClass(CAGradientLayer) { 
       layerToRemove = layer as? CAGradientLayer 
      } 
     } 
     layerToRemove?.removeFromSuperlayer() 

      self.gradient!.colors = [nightTopColor.CGColor, nightBottomColor.CGColor] 
      self.toColors = [nightToTopColor.CGColor, nightToBottomColor.CGColor] 

     self.view.layer.insertSublayer(self.gradient!, atIndex: 0) 
     animateLayer() 
    } 

    func animateLayer(){ 

     self.fromColors = self.gradient!.colors! 
     self.gradient!.colors = self.toColors as? [AnyObject] 
     let animation : CABasicAnimation = CABasicAnimation(keyPath: "colors") 
     animation.delegate = self 
     animation.fromValue = fromColors 
     animation.toValue = toColors 
     animation.duration = 3.50 
     animation.removedOnCompletion = true 
     animation.fillMode = kCAFillModeForwards 
     animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionLinear) 
     animation.delegate = self 

     self.gradient!.addAnimation(animation, forKey:"animateGradient") 
    } 

    override func animationDidStop(anim: CAAnimation, finished flag: Bool) { 

     self.toColors = self.fromColors; 
     self.fromColors = self.gradient!.colors! 

     animateLayer() 
    } 

CommonUtils.colorWithHexString() là chức năng chuyển đổi màu hex thành UIColor. Btw khi tôi cố gắng thay đổi màu nền thành màu ngày trong khi hoạt ảnh, màu nền gradient bị nhấp nháy.

Có ai biết giải pháp hay không.

Trả lời

6

Vấn đề là khi bạn xóa lớp, nó sẽ ngừng hoạt ảnh. Nhưng khi hoạt ảnh dừng lại, animationDidStop vẫn đang được gọi, điều này đang bắt đầu một hoạt ảnh mới. Vì vậy, bạn đang xóa lớp, dừng hoạt ảnh, ngay lập tức bắt đầu một hoạt ảnh khác, nhưng sau đó bạn sẽ bắt đầu một hoạt ảnh khác. Bạn có hình ảnh động dueling.

Bạn có thể kiểm tra flag để xem hoạt ảnh đã hoàn thành chính xác chưa trước animationDidStop phải gọi animateLayer.

override func animationDidStop(anim: CAAnimation, finished flag: Bool) { 
    if flag { 
     toColors = fromColors; 
     fromColors = gradient!.colors! 

     animateLayer() 
    } 
} 

Cá nhân, tôi không chắc chắn lý do bạn xóa và thêm và xóa lớp. Và nếu bạn là, tôi không chắc chắn lý do tại sao bạn không chỉ gradient?.removeFromSuperlayer() thay vì lặp qua các lớp.

Bất kể, tôi chỉ muốn giữ cho lớp gradient ở đó, chỉ cần kiểm tra presentationLayer của nó và bắt đầu các hình ảnh động từ đó:

class ViewController: UIViewController { 

    override func viewDidLoad() { 
     super.viewDidLoad() 

     fromColors = [dayTopColor.CGColor, dayBottomColor.CGColor] 
     toColors = [dayToTopColor.CGColor, dayToBottomColor.CGColor] 

     gradient = CAGradientLayer() 
     gradient!.colors = fromColors! 
     gradient!.frame = view.bounds 
     view.layer.addSublayer(gradient!) 

     animateLayer() 
    } 

    let dayTopColor = CommonUtils.colorWithHexString("955EAC") 
    let dayBottomColor = CommonUtils.colorWithHexString("9F3050") 
    let dayToTopColor = CommonUtils.colorWithHexString("D15B52") 
    let dayToBottomColor = CommonUtils.colorWithHexString("CC4645") 

    let nightTopColor = CommonUtils.colorWithHexString("2D5E7C") 
    let nightBottomColor = CommonUtils.colorWithHexString("19337D") 
    let nightToTopColor = CommonUtils.colorWithHexString("21334E") 
    let nightToBottomColor = CommonUtils.colorWithHexString("101A55") 

    var gradient : CAGradientLayer? 
    var toColors : [CGColor]? 
    var fromColors : [CGColor]? 

    var day = true 

    func toggleFromDayToNight() { 
     day = !day 

     if day { 
      fromColors = [dayTopColor.CGColor, dayBottomColor.CGColor] 
      toColors = [dayToTopColor.CGColor, dayToBottomColor.CGColor] 
     } else { 
      fromColors = [nightTopColor.CGColor, nightBottomColor.CGColor] 
      toColors = [nightToTopColor.CGColor, nightToBottomColor.CGColor] 
     } 

     let colors = (gradient!.presentationLayer() as! CAGradientLayer).colors // save the in-flight current colors 
     gradient!.removeAnimationForKey("animateGradient")      // cancel the animation 
     gradient!.colors = colors            // restore the colors to in-flight values 
     animateLayer()               // start animation 
    } 

    func animateLayer() { 
     let animation : CABasicAnimation = CABasicAnimation(keyPath: "colors") 
     animation.fromValue = gradient!.colors 
     animation.toValue = toColors 
     animation.duration = 3.50 
     animation.removedOnCompletion = true 
     animation.fillMode = kCAFillModeForwards 
     animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionLinear) 
     animation.delegate = self 

     gradient!.colors = toColors 

     gradient!.addAnimation(animation, forKey:"animateGradient") 
    } 

    override func animationDidStop(anim: CAAnimation, finished flag: Bool) { 
     if flag { 
      swap(&toColors, &fromColors) 
      animateLayer() 
     } 
    } 

    @IBAction func didTapButton() { 
     toggleFromDayToNight() 
    } 

} 
+0

Nó câu trả lời tuyệt vời, tôi đã cố gắng với điều này và giải quyết vấn đề của tôi. Cảm ơn rất nhiều. –

Các vấn đề liên quan