简体   繁体   中英

SwiftUI WatchOS: Animation behaves strangely when placed inside a list?

I have this pulse animation below which works well by itself, but when I place it inside of a List then the animation of the circles pulsing is correct but all of the circles also move vertically from the top to the center of the screen as well? Outside of a list the circles remain in the center. Why is a list causing this and how to get around?

import SwiftUI

struct HeartRatePulseView: View {
  @State var animate = false

  @Environment(\.scenePhase) private var scenePhase

  func circlesColor() -> Color {
    Color.blue
  }

  var body: some View {
    VStack(spacing: -3) {
      ZStack {
        ZStack {
          GeometryReader { geometry in
            ZStack {
              Circle().fill(circlesColor().opacity(0.25)).frame(width: geometry.size.width, height: geometry.size.height).scaleEffect(self.animate ? 1 : 0.01)
              Circle().fill(circlesColor().opacity(0.35)).frame(width: geometry.size.width * 0.79, height: geometry.size.height * 0.79).scaleEffect(self.animate ? 1 : 0.01)
              Circle().fill(circlesColor()).frame(width: geometry.size.width * 0.60, height: geometry.size.height * 0.60)
            }
        
            .frame(width: geometry.size.width, height: geometry.size.height)
          }
        }
        .onAppear { self.animate = true }
        .onChange(of: scenePhase, perform: { newValue in
          if newValue == .active {
            self.animate = true
          } else {
            self.animate = false
          }
        })
        .animation(animate ? Animation.easeInOut(duration: 1.5).repeatForever(autoreverses: true) : .default)
    
      }
    }
    .frame(height: 145)
  }
}

struct HeartRatePulseView_Previews: PreviewProvider {
  static var previews: some View {
    List {
      HeartRatePulseView()
    }
    .listStyle(.carousel)
  }
}

Ok, if you change the animation method slightly it works,

Note the value argument, it seems this is the new way to animate

.animation(animate ? Animation.easeInOut(duration: 1.5).repeatForever(autoreverses: true) : nil, value: animate)
import SwiftUI

struct HeartRatePulseView: View {
  @State var animate = false

  @Environment(\.scenePhase) private var scenePhase

  func circlesColor() -> Color {
    Color.blue
  }

  var body: some View {
    VStack(spacing: -3) {
      ZStack {
        ZStack {
          GeometryReader { geometry in
            ZStack {
              Circle().fill(circlesColor().opacity(0.25)).frame(width: geometry.size.width, height: geometry.size.height).scaleEffect(self.animate ? 1 : 0.01)
              Circle().fill(circlesColor().opacity(0.35)).frame(width: geometry.size.width * 0.79, height: geometry.size.height * 0.79).scaleEffect(self.animate ? 1 : 0.01)
              Circle().fill(circlesColor()).frame(width: geometry.size.width * 0.60, height: geometry.size.height * 0.60)
            }
    
            .frame(width: geometry.size.width, height: geometry.size.height)
          }
        }
        .onAppear { self.animate = true }
        .onChange(of: scenePhase, perform: { newValue in
          if newValue == .active {
            self.animate = true
          } else {
            self.animate = false
          }
        })
        .animation(animate ? Animation.easeInOut(duration: 1.5).repeatForever(autoreverses: true) : nil, value: animate)

      }
    }
    .frame(height: 145)
  }
}

struct HeartRatePulseView_Previews: PreviewProvider {
  static var previews: some View {
    List {
      HeartRatePulseView()
      HeartRatePulseView()
    }
    .listStyle(.carousel)
  }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM