macOS 上的 NavigationLink 无法在同一视图中打开

NavigationLink on macOS not opening in the same View

我目前正在使用 SwiftUI(没有 Catalyst)构建一个 macOS 应用程序,它应该有一个侧边栏和一个位于它右侧的视图。

NavigationView {
    List {
        ...
    }
    .listStyle(SidebarListStyle())

    HomeView()
}

我的主页视图中有一个 NavigationLink,指向另一个 DetailView

struct HomeView: View {
    var body: some View {
        NavigationLink("DetailView", destination: Text("This is the DV"))
    }
}

此 NavigationLink 始终显示为禁用状态,并且仅在我将另一列添加到 NavigationView 时才有效。我不想要另一个专栏,而是 NavigationLink HomeView 替换为 DetailView

有什么办法可以实现吗?

NavigationLinks 始终从导航视图的当前“列”打开详细视图,因此如果您的导航 link 呈现为 HomeView 的子视图,那么它会尝试打开为详细视图HomeView(缺少的第三列)。如果您希望视图以预期的方式替换 HomeView,那么用户应该 select 列表中的内容。如果您尝试以编程方式 select 列表中已存在的 NavigationLink,那么您应该通过更改绑定到列表的 selected 项目的变量的 HomeView 内的状态来实现,或者列表中 NavigationLink 的 selection。这是一个完整的工作示例,它在新的 MacOS SwiftUI Xcode 项目

的 ContentView.swift 中完成。
struct HomeView: View {
    @Binding var selectedItem: String?
    
    var body: some View {
        Button("Hello") {
            selectedItem = "Thing2"
        }
    }
}

struct ContentView: View {
    @State private var selectedItem: String?
    private let items = ["Thing1", "Thing2"]
    
    var body: some View {
        NavigationView {
            List(selection: $selectedItem) {
                ForEach(items, id: \.self) {item in
                    NavigationLink(
                        destination: Text(item),
                        tag: item,
                        selection: $selectedItem
                    ) {
                        Text(item)
                    }
                }
            }
            HomeView(selectedItem: $selectedItem)
        }
    }
}

这是显示 HomeView 的应用程序

这是在按下按钮后显示 selected 内容的应用程序

如果您不想在导航视图后在列表中显示任何内容 select,但仍想使用导航 link 来保持 NavigationView 中导航的完整性那么从技术上讲,您可以在列表

中放置一个隐藏的导航 link
NavigationView {
            List(selection: $selectedItem) {
                ForEach(items, id: \.self) {item in
                    NavigationLink(
                        destination: Text(item),
                        tag: item,
                        selection: $selectedItem
                    ) {
                        Text(item)
                    }
                }
                NavigationLink(
                    destination: Text("Sneaky"),
                    tag: "Sneaky",
                    selection: $selectedItem
                ) {
                    Text("")
                }.hidden()
            }
            HomeView(selectedItem: $selectedItem)
        }

在那种情况下,请确保您的按钮也 select 是偷偷摸摸的目的地 link

Button("Hello") {
  selectedItem = "Sneaky"
}

所以显然 SwiftUI 2 还不支持将视图推送到 macOS 上的导航堆栈。但是,我发现这个包可以帮助解决问题:

github.com/lbrndnr/StackNavigationView