SwiftUI 基础之提示框Activity Indicator制做

SwiftUI目前还在发展阶段,有些视图还未能提供。可是苹果给咱们提供复用机制,很容易将历史代码移植到SwiftUI世界中。下面咱们经过UIViewRepresentable将UIKit的UIActivityIndicator封装一下

最终效果

SwiftUI 基础之提示框Activity Indicator制做

实现步骤

首先,咱们将UIActivityIndi​​cator包装到一个ActivityIndi​​cator视图中,该视图可用做SwiftUI视图。其中 isAnimating做为动画的开关swift

struct ActivityIndicator: UIViewRepresentable {
    
    @Binding var isAnimating: Bool
    let style: UIActivityIndicatorView.Style
    
    func makeUIView(context: UIViewRepresentableContext<ActivityIndicator>) -> UIActivityIndicatorView {
        return UIActivityIndicatorView(style: style)
    }
    
    func updateUIView(_ uiView: UIActivityIndicatorView, context: UIViewRepresentableContext<ActivityIndicator>) {
        isAnimating ? uiView.startAnimating() : uiView.stopAnimating()
    }
}

在实际开发中,咱们不多单独使用UIActivityIndi​​cator,由于实在太单调了。我一般是添加UILabel来告知用户咱们正在处理的事项,例如:加载,计算,载入等,在SwiftUI世界里咱们用Text就能够很好的完成这个任务。ide

因为咱们如今将ActivityIndi​​cator做为SwiftUI视图,所以咱们能够轻松地利用SwiftUI强大组合功能,联合其余View来建立功能强大的HUD(Head up Display))提示框。动画

另外,为此了示范loading页面的显示与隐藏,咱们还增长了隐藏和显示按钮。
显示按钮效果ui

显示按钮代码spa

Button(action:{
                    self.isShowing = !self.isShowing
                    //self.isAnimating = false
                    
                }){
                    Text(" Show loading ").foregroundColor(.white)
                }.background(Color.orange)
                    .cornerRadius(2.0)
                .shadow(radius: 2)

隐藏按钮效果
隐藏按钮效果code

隐藏按钮代码blog

Button(action:{
                        self.isShowing = false
                        //self.isAnimating = false
                        
                    }){
                        Text(" Hide ")
                    }.background(Color.white)
                        .cornerRadius(2.0)
                    .shadow(radius: 2)

组装教程

struct LoadingView<Content>: View where Content: View {
    
    @Binding var isShowing: Bool
    @State var isAnimating: Bool = true
    var content: () -> Content
    
    var body: some View {
        GeometryReader { geometry in
            ZStack(alignment: .center) {
                
                self.content()
                    .disabled(self.isShowing)
                    .blur(radius: self.isShowing ? 3 : 0)
                
                
                VStack {
                    Text("Loading...")
                    ActivityIndicator(isAnimating: self.$isAnimating, style: .large)
                    Button(action:{
                        self.isShowing = false
                        //self.isAnimating = false
                        
                    }){
                        Text(" Hide ")
                    }.background(Color.white)
                        .cornerRadius(2.0)
                    .shadow(radius: 2)
                }
                    
                .frame(width: geometry.size.width / 2,
                       height: geometry.size.height / 5)
                    .background(Color.secondary.colorInvert())
                    .foregroundColor(Color.primary)
                    .cornerRadius(20)
                    .opacity(self.isShowing ? 1 : 0)
                
            }
        }
    }
    
}

主页面ci

struct ContentView: View {
    @State var isShowing: Bool = true
    var body: some View {
        
        LoadingView(isShowing:self.$isShowing) {
            VStack{
                Button(action:{
                    self.isShowing = !self.isShowing
                    //self.isAnimating = false
                    
                }){
                    Text(" Show loading ").foregroundColor(.white)
                }.background(Color.orange)
                    .cornerRadius(2.0)
                .shadow(radius: 2)
                
                NavigationView {
                    List(["1", "2", "3", "4", "5"], id: \.self) { row in
                        Text(row)
                    }.navigationBarTitle(Text("A List"), displayMode: .large)
                }
            }
        }
    }
}

项目完整代码

import SwiftUI
struct ActivityIndicator: UIViewRepresentable {
    
    @Binding var isAnimating: Bool
    let style: UIActivityIndicatorView.Style
    
    func makeUIView(context: UIViewRepresentableContext<ActivityIndicator>) -> UIActivityIndicatorView {
        return UIActivityIndicatorView(style: style)
    }
    
    func updateUIView(_ uiView: UIActivityIndicatorView, context: UIViewRepresentableContext<ActivityIndicator>) {
        isAnimating ? uiView.startAnimating() : uiView.stopAnimating()
    }
}
struct LoadingView<Content>: View where Content: View {
    
    @Binding var isShowing: Bool
    @State var isAnimating: Bool = true
    var content: () -> Content
    
    var body: some View {
        GeometryReader { geometry in
            ZStack(alignment: .center) {
                
                self.content()
                    .disabled(self.isShowing)
                    .blur(radius: self.isShowing ? 3 : 0)
                
                
                VStack {
                    Text("Loading...")
                    ActivityIndicator(isAnimating: self.$isAnimating, style: .large)
                    Button(action:{
                        self.isShowing = false
                        //self.isAnimating = false
                        
                    }){
                        Text(" Hide ")
                    }.background(Color.white)
                        .cornerRadius(2.0)
                    .shadow(radius: 2)
                }
                    
                .frame(width: geometry.size.width / 2,
                       height: geometry.size.height / 5)
                    .background(Color.secondary.colorInvert())
                    .foregroundColor(Color.primary)
                    .cornerRadius(20)
                    .opacity(self.isShowing ? 1 : 0)
                
            }
        }
    }
    
}

struct ContentView: View {
    @State var isShowing: Bool = true
    var body: some View {
        
        LoadingView(isShowing:self.$isShowing) {
            VStack{
                Button(action:{
                    self.isShowing = !self.isShowing
                    //self.isAnimating = false
                    
                }){
                    Text(" Show loading ").foregroundColor(.white)
                }.background(Color.orange)
                    .cornerRadius(2.0)
                .shadow(radius: 2)
                
                NavigationView {
                    List(["1", "2", "3", "4", "5"], id: \.self) { row in
                        Text(row)
                    }.navigationBarTitle(Text("A List"), displayMode: .large)
                }
            }
        }
    }
}

参考资料

https://peacemoon.de/blog/2019/06/10/activity-indicator-with-swiftui/开发

更多SwiftUI教程和代码关注专栏

QQ:3365059189
SwiftUI技术交流QQ群:518696470

https://www.jianshu.com/c/7b3...

相关文章
相关标签/搜索