使用 UIViewPropertyAnimator 为 UILabel textColor 属性设置动画

Posted

技术标签:

【中文标题】使用 UIViewPropertyAnimator 为 UILabel textColor 属性设置动画【英文标题】:Animating UILabel textColor property with UIViewPropertyAnimator 【发布时间】:2021-01-10 12:50:37 【问题描述】:

我有一个看起来很简单的问题,但我还没有找到解决方案。

我使用UIViewPropertyAnimator 为带有标签的视图制作动画,并使用滑块手动调整动画师的fractionComplete 属性。

在我制作动画的视图中,我有一个 UILabel,我想为它的 textColor 制作动画。

我发现SO answers 建议像这样为textColor 设置动画:

UIView.transition(with: yourLabel, duration: 0.3, options: .transitionCrossDissolve, animations: 
  self.yourLabel.textColor = .red
, completion: nil)

但是,对我来说这不起作用,因为我希望动画根据我为动画师设置的fractionComplete 进行。

【问题讨论】:

标签文本颜色不是动画视图属性。 @matt 无论如何我都想对其进行动画处理,视图的其余部分按应有的动画效果看起来是错误的,并且文本颜色只是突然改变。有什么解决办法吗? 有多种方法可以做到这一点。 This thread 似乎是一个很好的起点 【参考方案1】:

正如 cmets 中所说,textColor 属性不能设置动画。 但是,有一种称为颜色插值的技术,它可能是一个很好的解决方法。

您可以在this thread 中找到解决此问题的多种方法,但是,我也为您提供了一种解决方案:

extension UIColor 
var components: (r: CGFloat, g: CGFloat, b: CGFloat, a: CGFloat) 
    let components = self.cgColor.components!

    switch components.count == 2 
    case true : 
        return (r: components[0], g: components[0], b: components[0], a: components[1])
    case false: 
        return (r: components[0], g: components[1], b: components[2], a: components[3])
    


static func interpolate(from fromColor: UIColor, to toColor: UIColor, with progress: CGFloat) -> UIColor 
    let fromComponents = fromColor.components
    let toComponents = toColor.components
    
    let r = (1 - progress) * fromComponents.r + progress * toComponents.r
    let g = (1 - progress) * fromComponents.g + progress * toComponents.g
    let b = (1 - progress) * fromComponents.b + progress * toComponents.b
    let a = (1 - progress) * fromComponents.a + progress * toComponents.a
    
    return UIColor(red: r, green: g, blue: b, alpha: a)


然后,您所要做的就是在滑块值发生变化时调用的函数中:

@objc func sliderChanged(_ sender: UISlider) 
     animator.fractionComplete = CGFloat(sender.value)
     yourLabel.textColor = UIColor.interpolate(from: fromColor, to: toColor, with: sender.value)

您没有为textColor 设置动画,而是在每次调用sliderChanged 时将其更改为不同的颜色,但这种变化看起来是渐进的,并且不会从您的起始颜色跳到您的第二种颜色,所以我认为它应该会达到你想要的结果。

【讨论】:

以上是关于使用 UIViewPropertyAnimator 为 UILabel textColor 属性设置动画的主要内容,如果未能解决你的问题,请参考以下文章

无法使用 UIViewPropertyAnimator.fractionComplete 驱动 UIView.transition

使用 UIViewPropertyAnimator 同步动画 CALayer 属性和 UIView

UIViewPropertyAnimator 自动布局完成问题

使用 UIViewPropertyAnimator 为 UILabel textColor 属性设置动画

使用 UIViewPropertyAnimator 依次为 UIView 的 alpha 设置动画

使用 UIViewPropertyAnimator 通过触摸中断动画