iOS SwiftUI-5 Animation Complete監聽


Posted by John on 2021-01-15

  1. 重寫View,監聽Animation Complete

     //VectorArithmetic 可動畫類型的數據
     extension View {
         //定義Data 為 VectorArithmetic
         //ModifiedContent是指,將此Self示圖,經由AnimationDataChangeModifier,修改後產生新的示圖
         //modifier主要是回傳ModifiedContent
         /*@inlinable public func modifier<T>(_ modifier: T) -> ModifiedContent<Self, T>*/
    
         func onAnimationDataChange<Data: VectorArithmetic>(for data: Data, onComplete: @escaping () -> Void) 
         -> ModifiedContent<Self, AnimationDataChangeModifier<Data>> {
             return modifier(AnimationDataChangeModifier(changeData: data, onComplete: onComplete))
         }
     }
    
     //指處where Data: VectorArithmetic,確保資料類型是VectorArithmetic
     // AnimatableModifier繼承於 Animatable, ViewModifier,就是可動畫的修改器
    
     struct AnimationDataChangeModifier<Data>: AnimatableModifier where Data: VectorArithmetic {
         //animatableData是繼承Animatable的資料,監聽他的變化
         //didSet是當資料變化的時候觸發
         var animatableData: Data {
             didSet {
                 dataChangeCallback()
             }
         }
    
         private var previousData: Data
         private var onComplete: () -> Void
         //此處要注意,順序很重要
         init(changeData: Data, onComplete: @escaping () -> Void) {
             //先註冊callback,確保觸發的時候,可以正常回調
             self.onComplete = onComplete
             //animatableData發生改變的時候,會調用dataChangeCallback(),才往下執行
             //此處是關鍵,因為animatableData改變時,previousData這個還是上次的資料
             //可以確定資料是否有改變完成
             self.animatableData = changeData
             previousData = changeData
         }
    
         private func dataChangeCallback() {
             guard animatableData == previousData else { return }
    
             DispatchQueue.main.async {
                 self.onComplete()
             }
         }
    
         func body(content: Content) -> some View {
             return content
         }
     }
    
  2. 引用方式

    //onAnimationDataChange必須要使用withAnimation的變數變化,才會觸發
    //因為VectorArithmetic 可動畫類型的數據
    struct MainView: View {
     @State var opacity: Double = 1
     @State var animation = false
     var body: some View {
         Text("1234567890abcdefg")
             .opacity(animation ? opacity : 1)
             .animation(animation ? Animation.linear(duration: 1) : nil)
             .onAnimationDataChange(for: opacity) {
                 if opacity == 0.1 {
                     withAnimation(Animation.default, {
                         opacity = 1
                     })
                 } else {
                     withAnimation(Animation.default, {
                         opacity = 0.1
                     })
                 }
             }
             .onAppear {
                 animation = true
                 withAnimation(Animation.default, {
                     opacity = 0.1
                 })
    
             }
     }
    }
    

最後更新日期:2021/01/15


##Swift #SwiftUI #XCode #軟體設計 #電腦程式







Related Posts

[0] 寫在一開始,關於這個系列文

[0] 寫在一開始,關於這個系列文

prop drilling 與 context

prop drilling 與 context

Day 3 - 了解 Git 及 GitHub

Day 3 - 了解 Git 及 GitHub


Comments