首页 > 解决方案 > 如果从 VStack 或 NavigationItem 中调用,SwiftUI 动画会有所不同

问题描述

我有一个非常简单VStack的,直接基于Paul Hudson 的优秀 SwiftUI 示例之一。有两行Text,一隐藏。有一种方法可以切换@State var控制隐藏的Text.

如果我从 中调用该函数VStack,它会正确设置动画。如果我从 a 调用它navigationBarItems,它会丢失动画。我是否遗漏了有关视图如何组成的信息?

struct ContentView: View {
    @State var showDetails = false
    func toggleDetails() { withAnimation { self.showDetails.toggle() } }

    var body: some View {
        NavigationView() {
            VStack {
                Button(action: { self.toggleDetails() }) { Text("Tap to show details") }

                if showDetails { Text("Details go here.") }
            }
            .navigationBarTitle(Text("Nav Bar"))
            .navigationBarItems(trailing: 
               Button(action: { self.toggleDetails() }) {
                    Text("Details")
               })
        }
    }
}

#if DEBUG
struct ContentView_Previews : PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}
#endif

不一致的动画

标签: swiftui

解决方案


Beta 5 更新

似乎 beta 5 解决了这个问题。不再需要解决方法。


beta 4 和以前版本的解决方法

我认为它不起作用的原因是因为您从视图树的不同分支调用 withAnimation 。“详细信息”按钮和需要动画的视图位于层次结构的不同分支上。我只是在猜测,但我在此处发布的解决方法似乎支持它。

如果不使用显式动画(即withAnimation),而是在 VStack 和 Text 上使用隐式动画,它可以工作:

在此处输入图像描述

struct ContentView: View {
    @State var showDetails = false
    func toggleDetails() { self.showDetails.toggle() }

    var body: some View {
        NavigationView() {
            VStack {
                Button(action: { self.toggleDetails() }) { Text("Tap to show details") }

                if showDetails {
                    Text("Details go here.").animation(.basic())

                }
            }
            .animation(.basic())
            .navigationBarTitle(Text("Nav Bar"))
            .navigationBarItems(trailing:
                Button(action: {
                    self.toggleDetails()

                }) { Text("Details") })
        }
    }
}

推荐阅读