Как сделать анимацию вращения с помощью CGAffineTransform в SwiftUI? - PullRequest
0 голосов
/ 22 сентября 2019

В моем приложении компаса, для некоторых причин, я должен использовать CGAffineTransform, чтобы вращать мою стрелку.Но я не знаю, как я могу создать анимацию с помощью CGAffineTransform.

Мой код:

import SwiftUI
import CoreLocation

struct Arrow: View {

  var locationManager = CLLocationManager()
  @ObservedObject var location: LocationManager = LocationManager()
  @State private var angle: CGFloat = 0

  var body: some View {
    VStack {
      Image("arrow")
        .resizable()
        .aspectRatio(contentMode: .fit)
        .frame(width: 300, height: 300)
        .modifier(RotationEffect(angle: CGFloat(self.location.heading.degreesToRadians)))
      Text(String(self.location.heading.degreesToRadians))
        .font(.system(size: 20))
        .fontWeight(.light)
        .padding(.top, 15)

      Text(String(self.location.coordinates[0]))
        .font(.system(size: 20))
        .fontWeight(.light)
        .padding(.top, 15)

      Text(String(self.location.coordinates[1]))
        .font(.system(size: 20))
        .fontWeight(.light)
        .padding(.top, 15)
    }
  }
}

struct RotationEffect: GeometryEffect {
  var angle: CGFloat

  var animatableData: CGFloat {
    get { angle }
    set { angle = newValue }
  }

  func effectValue(size: CGSize) -> ProjectionTransform {
    return ProjectionTransform(
      CGAffineTransform(translationX: -150, y: -150)
        .concatenating(CGAffineTransform(rotationAngle: angle))
        .concatenating(CGAffineTransform(translationX: 150, y: 150))
    )
  }
}

Я знаю, что могу использовать withAnimation, как код ниже, но мне нужноустановить переменную угла автоматически с моим location.heading.без необходимости нажимать любую кнопку.

struct ContentView: View {
    @State private var angle: CGFloat = 0

    var body: some View {
        VStack {
            Rectangle()
                .frame(width: 50, height: 50)
                .modifier(MyEffect(angle: angle))

            Button("Go to 0") {
                withAnimation(.easeInOut(duration: 2.0)) {
                    self.angle = 0
                }
            }

            Button("Go to 360") {
                withAnimation(.easeInOut(duration: 2.0)) {
                    self.angle = .pi * 2
                }
            }
        }
    }
}
...