Skip to content

SwitUI如何实现页面跳转(iOS16)

refers to ios - NavigationView and NavigationLink on button click in SwiftUI? - Stack Overflow

https://www.hackingwithswift.com/quick-start/swiftui/how-to-use-programmatic-navigation-in-swiftui

我们在写SwiftUI的时候,通常点击按钮进行跳转的时候,是通过如下代码进行跳转

swift
struct ButtonJump: View {
    var body: some View {
        NavigationView {
            NavigationLink {
                Button("Button") {}
            } label: {
                Text("Hello, World!")
            }
        }
    }
}

// 页面返回 pop
import SwiftUI
struct NextView: View {    
    @Environment(\.presentationMode) var presentation    
    var body: some View {
        Button("Finished") {
            self.presentation.wrappedValue.dismiss()
        }
    }
}
struct ButtonJump: View {
    var body: some View {
        NavigationView {
            NavigationLink {
                Button("Button") {}
            } label: {
                Text("Hello, World!")
            }
        }
    }
}

// 页面返回 pop
import SwiftUI
struct NextView: View {    
    @Environment(\.presentationMode) var presentation    
    var body: some View {
        Button("Finished") {
            self.presentation.wrappedValue.dismiss()
        }
    }
}

如何在按钮点击的时候进行页面跳转?

方式1

swift
import SwiftUI

struct ButtonNavigationView: View {
    @State private var isShowingSecondView: Bool = false

    var body: some View {
        NavigationStack {
            VStack {
                Button(action: { isShowingSecondView = true }) {
                    Text("Show second view")
                }
            }.navigationDestination(isPresented: $isShowingSecondView) {
                Text("SecondView")
            }
        }
    }
}

struct ButtonNavigationView_Previews: PreviewProvider {
    static var previews: some View {
        ButtonNavigationView()
    }
}
import SwiftUI

struct ButtonNavigationView: View {
    @State private var isShowingSecondView: Bool = false

    var body: some View {
        NavigationStack {
            VStack {
                Button(action: { isShowingSecondView = true }) {
                    Text("Show second view")
                }
            }.navigationDestination(isPresented: $isShowingSecondView) {
                Text("SecondView")
            }
        }
    }
}

struct ButtonNavigationView_Previews: PreviewProvider {
    static var previews: some View {
        ButtonNavigationView()
    }
}

TODO: 最终解

Section(header: Text("趋势")) {

                    Rectangle()

                        .foregroundColor(.clear)

                        .frame(width: 200, height: 200)

                        .background(

                            NavigationLink("", destination: TrendingView())

                                .opacity(0)

                        )

                }
Section(header: Text("趋势")) {

                    Rectangle()

                        .foregroundColor(.clear)

                        .frame(width: 200, height: 200)

                        .background(

                            NavigationLink("", destination: TrendingView())

                                .opacity(0)

                        )

                }

方式2

支持通过值绑定的方式进行跳转

swift
import SwiftUI

struct StackAndLink: View {
    var body: some View {
        NavigationStack {
            NavigationLink(value: "NewView") {
                Text("Show NewView")
            }
            .navigationDestination(for: String.self) { view in
                if view == "NewView" {
                    Text("This is NewView")
                }
            }
        }
    }
}
import SwiftUI

struct StackAndLink: View {
    var body: some View {
        NavigationStack {
            NavigationLink(value: "NewView") {
                Text("Show NewView")
            }
            .navigationDestination(for: String.self) { view in
                if view == "NewView" {
                    Text("This is NewView")
                }
            }
        }
    }
}

当然可以换成枚举的方式:

swift
enum Route {
    case NewView
}

struct StackAndLink: View {
    var body: some View {
        NavigationStack {
            NavigationLink(value: Route.NewView) {
                Text("Show NewView")
            }
            .navigationDestination(for: Route.self) { view in
                if view == Route.NewView {
                    Text("This is NewView")
                }
            }
        }
    }
}
enum Route {
    case NewView
}

struct StackAndLink: View {
    var body: some View {
        NavigationStack {
            NavigationLink(value: Route.NewView) {
                Text("Show NewView")
            }
            .navigationDestination(for: Route.self) { view in
                if view == Route.NewView {
                    Text("This is NewView")
                }
            }
        }
    }
}

方式3

使用 NavigationPath

swift
import SwiftUI

struct NavigationPathView: View {
    
    @State
    private var navPath:NavigationPath = NavigationPath()
    
    var body: some View {
        NavigationStack.init(path: $navPath) {
            Button.init {
                navPath.append("NextPage")
            } label: {
                Text("Next Page")
            }.navigationDestination(for: String.self) { name in
                if name == "NextPage" {
                    Text("This is Next Page")
                }
            }
        }
    }
}
import SwiftUI

struct NavigationPathView: View {
    
    @State
    private var navPath:NavigationPath = NavigationPath()
    
    var body: some View {
        NavigationStack.init(path: $navPath) {
            Button.init {
                navPath.append("NextPage")
            } label: {
                Text("Next Page")
            }.navigationDestination(for: String.self) { name in
                if name == "NextPage" {
                    Text("This is Next Page")
                }
            }
        }
    }
}