SwiftUI 中的动画状态变化

Posted

技术标签:

【中文标题】SwiftUI 中的动画状态变化【英文标题】:Animate State change in SwiftUI 【发布时间】:2019-06-08 20:09:53 【问题描述】:

我目前正在使用 SwiftUI。在 SwiftUI 中,可以为状态更改设置动画,例如:

struct Foo: View 
    @State private var show = false

    var body: some View 
        VStack 
            if show 
                Text("Foo")
            
            Button(action: 
                withAnimation 
                    self.show.toggle()
                
            ) 
                Text(show ? "Hide" : "Show")
            
        
    

但如果我有一个 TextField:

struct Foo: View 
    @State private var text = ""

    var body: some View 
        VStack 
            TextField($text, placeholder: Text("Foo")) 
                print("editing ended")
            
            if !text.isEmpty 
                Button(action: ) 
                    Text("Done")
                
            
        
    

我无法找到一种方法来为这种更改设置动画,因为 TextField 更改了 State 属性,而无需调用 withAnimation()。

是否有可能让这个变化变成动画?

【问题讨论】:

在 SwiftUI 之外会有什么样的动画?换句话说,您认为这里的“变化”是什么,以及如何? 在 SwiftUI 之外是什么意思?在我的示例中,我想淡入和淡出 Button,但对于涉及颜色等的更复杂的动画,我需要此动画功能。但是,如果调用 withAnimation() 函数,我需要的所有动画都将正常运行. 淡入\淡出按钮或TextField?在您的示例中,您尝试为用户点击时正在更改的文本设置动画,但它看起来不像您想要的 在示例 #1 中,当我按下按钮时,会发生两件事。首先显示或隐藏“Foo”文本,其次按钮文本在“隐藏”和“显示”之间切换。这两种“变化”都发生在默认动画上,它只是一个淡入淡出动画。在示例 #2 中,只要文本不为空,就会显示“完成”按钮,否则它会被隐藏。这在没有动画的情况下发生。但这并不重要,在哪个示例中究竟发生了哪些动画,我唯一感兴趣的是,在示例 #2 中没有动画,而在示例 #1 中有一些动画。 但在第一个示例中,您有一个 withAnimation 包装状态更改。在第二个例子中你没有。所以不清楚你想象的动画应该是什么。 【参考方案1】:

只需添加动画修饰符来包裹你的按钮

  var body: some View 
    VStack 
      TextField($text, placeholder: Text("Foo")) 
        print("editing ended")
      
//      if !text.isEmpty 
        Button(action: ) 
          Text("Done")
        
        .background(text.isEmpty ? Color.red : Color.yellow )
         //.animation(.basic(duration: 1))
        .animation(Animation.default.speed(1))
      
    
  

【讨论】:

好的。我试过了,但不幸的是它只会在 Button 中淡出,但会立即将其移除。可能是虫子?我还尝试了一些修饰符更改,例如 Button 上的 .foregroundColor(text.isEmpty ? .red : .green) 而不是 if,但这也没有动画效果。 我的代码应该只淡入/淡出按钮。 foregroundColor 的动画真的不行。尝试与背景相同。不要忘记将更改放在动画修改器之前 是的,我知道,但它不会淡出。仅在 嗯。这段代码对我来说很奇怪的输入/输出 是的,我现在在 Playground 中尝试过,它可以工作,但不适用于颜色。在模拟器中它只适用于淡入。我不知道......【参考方案2】:

TextField("Placeholder", text:$text.animation())

使用文本的所有内容在更改时都会被动画化。

【讨论】:

以上是关于SwiftUI 中的动画状态变化的主要内容,如果未能解决你的问题,请参考以下文章

如何将 SwiftUI 状态从特定值更改为新状态值设置动画?

SwiftUI视图状态更改使用withAnimation()方法无动画效果的解决

SwiftUI视图状态更改使用withAnimation()方法无动画效果的解决

SwiftUI - 脉动动画和改变颜色

如何在 SwiftUI 中自定义角度变化的动画

为啥我的 SwiftUI 动画在旋转时恢复到前一帧?