在 SwiftUI 图像上重复动画

Posted

技术标签:

【中文标题】在 SwiftUI 图像上重复动画【英文标题】:Repeating animation on SwiftUI Image 【发布时间】:2019-10-10 04:50:39 【问题描述】:

鉴于以下struct

struct PeopleList : View 
    @State var angle: Double = 0.0
    @State var isAnimating = true

    var foreverAnimation: Animation 
        Animation.linear(duration: 2.0)
            .repeatForever()
    

    var body: some View 
        Button(action: , label: 
            Image(systemName: "arrow.2.circlepath")
                .rotationEffect(Angle(degrees: self.isAnimating ? self.angle : 0.0))
                .onAppear 
                    withAnimation(self.foreverAnimation) 
                        self.angle += 10.0
                    
                
        )
    

我希望Image 会顺时针旋转并重复,直到self.isAnimating 变为false,尽管它只有一次动画。

【问题讨论】:

【参考方案1】:

这是在出现和开始/停止时持续进行的可能解决方案。使用 Xcode 11.4 / ios 13.4 测试。

struct PeopleList : View 
    @State private var isAnimating = false
    @State private var showProgress = false
    var foreverAnimation: Animation 
        Animation.linear(duration: 2.0)
            .repeatForever(autoreverses: false)
    

    var body: some View 
        Button(action:  self.showProgress.toggle() , label: 
            if showProgress 
                Image(systemName: "arrow.2.circlepath")
                    .rotationEffect(Angle(degrees: self.isAnimating ? 360 : 0.0))
                    .animation(self.isAnimating ? foreverAnimation : .default)
                    .onAppear  self.isAnimating = true 
                    .onDisappear  self.isAnimating = false 
             else 
                Image(systemName: "arrow.2.circlepath")
            
        )
        .onAppear  self.showProgress = true 
    

【讨论】:

【参考方案2】:

更新:在停止动画时涉及到一个倒转,这可以通过this 解决方案解决。

我想这就是你要找的东西:

struct PeopleList : View 
    @State var angle: Double = 0.0
    @State var isAnimating = false
    
    var foreverAnimation: Animation 
        Animation.linear(duration: 2.0)
            .repeatForever(autoreverses: false)
    
    
    var body: some View 
        Button(action: , label: 
            Image(systemName: "arrow.2.circlepath")
                .rotationEffect(Angle(degrees: self.isAnimating ? 360.0 : 0.0))
                .animation(self.foreverAnimation)
                .onAppear 
                    self.isAnimating = true
            
        )
    

【讨论】:

这让我走上了正轨。唯一的问题是如果self.isAnimating 设置为false,那么动画仍然会继续运行。如果self.isAnimatingfalse,有没有办法完全停止动画? 太棒了!这是聪明的做法。 @fuzz 我认为您可以在 isAnimating 为 false 时将 nil 传递给动画修改器,否则您的 foreverAnimation 看起来我们必须以某种方式摆脱“repeatForever”动画,例如 .animation(self.isAnimating ? foreverAnimation : foreverAnimationNo)。 foreverAnimationNo 将是一个不重复的动画。 或者只是 .animation(self.isAnimating ? foreverAnimation : .none) 在How to STOP Animation().repeatForever in SwiftUI解决

以上是关于在 SwiftUI 图像上重复动画的主要内容,如果未能解决你的问题,请参考以下文章

SwiftUI - 在当前视图中为新图像设置动画

同一元素的 SwiftUI 多个动画

SwiftUI 动画:如何延迟重复动画

SwiftUI 动画并不总是运行

随着时间的推移,重复的 SwiftUI 动画变得不稳定

SwiftUI - 奇怪的动画