【问题标题】:SwiftUI synchronizing multiple SwiftUI animations with delaysSwiftUI 同步多个带有延迟的 SwiftUI 动画
【发布时间】:2021-10-17 04:56:18
【问题描述】:

我正在尝试构建一个包含多个项目的视图,这些项目应该彼此同步动画;例如,如果一项为 25%,则其他三项应为 50%、75% 和 100%。

只使用.delay(delay) 的幼稚选项一开始似乎效果很好,但是一旦我切换应用程序,不同的动画都会被重置为完全偏移(不再有任何偏移)。 我尝试了许多 hacky 解决方法,包括:

  • 当视图背景化/恢复时切换整个动画容器;这不起作用。 (我认为是因为容器与动画状态一起保留,即使它不可见。)
  • 使用DispatchQueue.main.asyncAfter();这与动画没有任何不同(因为我认为它是内部动画状态本身正在丢失。)

请注意,我根本没有投资于这个特定的解决方案;非常欢迎任何有关解决此问题的更好方法的建议。

Before switching apps After switching apps

struct MyRepeatingItemView: View {
    var delay: Double
    
    @State
    var isTranslated = false
    
    var body: some View {
        Color.red
            .opacity(0.2)
            .frame(width: 256, height: 256)
            .scaleEffect(isTranslated ? 1 : 0.01)
            .onAppear {
                withAnimation(Animation.linear(duration: 4).repeatForever(autoreverses: false).delay(delay)) {
                    isTranslated.toggle()
                }
            }
    }
}

struct MyRepeatingContainerView: View {
    
    var body: some View {
        ZStack {
            Color.blue
                .frame(width: 256, height: 2)
            Color.blue
                .frame(width: 2, height: 256)
            MyRepeatingItemView(delay: 0.0)
            MyRepeatingItemView(delay: 1.0)
            MyRepeatingItemView(delay: 2.0)
            MyRepeatingItemView(delay: 3.0)
        }
    }
}

【问题讨论】:

    标签: animation swiftui


    【解决方案1】:

    解决不同步视图的方法是将它们全部放在一个视图中,该视图会同时同步所有内容。我花了一些时间来制定模式,但这里是:

    struct MyRepeatingItemView: View {
        
        @State var isTranslated = false
        
        var body: some View {
            ZStack {
                Rectangle()
                    .fill(Color.red)
                    .frame(width: 256, height: 256)
                    .opacity(isTranslated ? 0 : 0.25)
                    .scaleEffect(isTranslated ? 1 : 0.75)
                Rectangle()
                    .fill(Color.red)
                    .frame(width: 256, height: 256)
                    .opacity(0.25)
                    .scaleEffect(isTranslated ? 0.75 : 0.5)
                Rectangle()
                    .fill(Color.red)
                    .frame(width: 256, height: 256)
                    .opacity(0.25)
                    .scaleEffect(isTranslated ? 0.5 : 0.25)
                Rectangle()
                    .fill(Color.red)
                    .frame(width: 256, height: 256)
                    .opacity(0.25)
                    .scaleEffect(isTranslated ? 0.25 : 0)
            }
            .onAppear {
                withAnimation(Animation.linear(duration: 1).repeatForever(autoreverses: false)) {
                    isTranslated.toggle()
                }
            }
        }
    }
    
    struct MyRepeatingContainerView: View {
        
        var body: some View {
            ZStack {
                Color.blue
                    .frame(width: 256, height: 2)
                Color.blue
                    .frame(width: 2, height: 256)
                
                MyRepeatingItemView()
            }
        }
    }
    

    【讨论】:

    • 我试过了,问题和以前一样;当切换应用程序并再次切换回来时(切换回之前在另一个应用程序上进行了几秒钟的交互),时间错误并且四个动画似乎失去了同步。
    • 答案已更新。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-03-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-03-26
    相关资源
    最近更新 更多