如何在SwiftUI中使用ZStack重现高度/堆叠效果

时间:2019-10-17 15:54:23

标签: swiftui

我想在ZStack中重现在iOS 13中呈现模态时看到的高度效果:

背景略透明,并带有模糊效果的灰色。

想法是创建一个似乎漂浮在ZStack内部下面元素上方的视图。

1 个答案:

答案 0 :(得分:0)

您可以拥有一个ZStack,其视图根据@State变量而有条件地显示。该变量还将确定基础视图上的.blur数量,以及它们之间是否显示透明的灰色视图(这会使背​​景看起来变灰)。我举了一个例子来说明:

struct ContentView: View {
    @State var modalIsPresented = false
    @State var alertIsPresented = false
    @State var customAlertIsPresented = false
    var body: some View {
        ZStack {
            Text("Test!!!")

            VStack {
                Spacer()
                Text("Lorem ipsum dolor sit amet")
                Spacer()
                Text("Lorem ipsum dolor sit amet")
                Image(systemName: "star")
                Button(action: {
                    self.modalIsPresented = true
                }) {
                    Text("Present an actual modal")
                }
                Button(action: {
                    self.alertIsPresented = true
                }) {
                    Text("Present an actual alert")
                }
                Button(action: {
                    withAnimation {
                        self.customAlertIsPresented = true
                    }
                }) {
                    Text("Present your custom alert")
                }
            }
            .blur(radius: self.customAlertIsPresented ? 3 : 0)
            .animation(.easeOut)
            if customAlertIsPresented {
                Rectangle()
                    .background(Color.black)
                    .opacity(0.3)
                    .edgesIgnoringSafeArea(.all)
                    .animation(.easeIn)
            }
            if customAlertIsPresented {
                CustomAlert(isPresented: $customAlertIsPresented).frame(width: 300)
                    .background(Color.white)
                    .animation(.easeIn)
                    .cornerRadius(10)
                    .shadow(radius: 10)
            }
        }.sheet(isPresented: $modalIsPresented) {
            Text("This is what an actual modal looks like")
        }.alert(isPresented: $alertIsPresented) {
            Alert(title: Text("This is what an alert looks like"))
        }
    }
}

struct CustomAlert: View {
    @Binding var isPresented: Bool
    var body: some View {
        VStack {
            Text("This is my custom alert").padding()
            Divider()
            Button(action: {
                self.isPresented = false
            }) {
                HStack {
                    Spacer()
                    Text("Dismiss")
                    Spacer()
                }
            }.padding([.top, .bottom], 10)
        }
    }
}

我添加了一些动画来使过渡更加平滑。您可以调整.blur.opacity之类的内容,以及各种.animation来自定义外观,这些都只是您想要的方式。这是我的示例:

Prior to showing alert After showing the alert