SwiftUI NavigationStack: 列表视图导航行为意外

huangapple go评论113阅读模式
英文:

SwiftUI NavigationStack: Unexpected Navigation Behavior from List View

问题

I'm here to provide the translated content:

我正在使用SwiftUI构建iOS应用程序,在从“List”视图导航到详细视图时遇到意外行为。

我有三个视图:ViewA、ViewB和ViewC。ViewA导航到ViewB,ViewB是一个Item实例的列表。在ViewB中点击一个Item应该导航到ViewC,显示所选Item的详细信息。

导航到ViewC的行为不正常。当我在ViewB中点击一个Item时,ViewC会短暂显示,然后立即导航回ViewB。导航堆栈在ViewB之前有ViewC。堆栈:[ViewA、ViewC、ViewB]

最小可重现的示例:

  1. struct Item: Identifiable, Hashable {
  2. let id = UUID()
  3. let title: String
  4. let description: String
  5. }
  6. struct ViewA: View {
  7. var body: some View {
  8. NavigationStack {
  9. NavigationLink("转到ViewB") {
  10. ViewB()
  11. }
  12. }
  13. }
  14. }
  15. struct ViewB: View {
  16. let items: [Item] = [
  17. Item(title: "项目1", description: "这是项目1"),
  18. Item(title: "项目2", description: "这是项目2")
  19. ]
  20. var body: some View {
  21. List(items, id: \.id) { item in
  22. NavigationLink(value: item) {
  23. Text(item.title)
  24. }
  25. }
  26. .navigationDestination(for: Item.self) { item in
  27. ViewC(item: item)
  28. }
  29. }
  30. }
  31. struct ViewC: View {
  32. let item: Item
  33. var body: some View {
  34. Text(item.description)
  35. }
  36. }

我期望在ViewB中选择一个Item后直接导航到ViewC,并且返回按钮应该将我带回ViewB。堆栈应该是[ViewA(根)、ViewB、ViewC]。

导致这种行为的原因是什么,我该如何解决这个问题?

英文:

I'm building an iOS app with SwiftUI and am encountering unexpected behaviour when navigating from a List view to a detail view.

I have three views: ViewA, ViewB, and ViewC. ViewA navigates to ViewB, which is a list of Item instances. Tapping on an Item in ViewB should navigate to ViewC, presenting the details of the selected Item.

The navigation to ViewC is misbehaving. When I tap an Item in ViewB, ViewC is shown briefly and then the view immediately navigates back to ViewB. The navigation stack has ViewC before ViewB. Stack: [ViewA, ViewC, ViewB]

The minimal reproducible example:

  1. struct Item: Identifiable, Hashable {
  2. let id = UUID()
  3. let title: String
  4. let description: String
  5. }
  6. struct ViewA: View {
  7. var body: some View {
  8. NavigationStack {
  9. NavigationLink("Go to ViewB") {
  10. ViewB()
  11. }
  12. }
  13. }
  14. }
  15. struct ViewB: View {
  16. let items: [Item] = [
  17. Item(title: "Item 1", description: "This is item 1"),
  18. Item(title: "Item 2", description: "This is item 2")
  19. ]
  20. var body: some View {
  21. List(items, id: \.id) { item in
  22. NavigationLink(value: item) {
  23. Text(item.title)
  24. }
  25. }
  26. .navigationDestination(for: Item.self) { item in
  27. ViewC(item: item)
  28. }
  29. }
  30. }
  31. struct ViewC: View {
  32. let item: Item
  33. var body: some View {
  34. Text(item.description)
  35. }
  36. }

I expect to navigate directly to ViewC when an Item is selected in ViewB and the back button should take me back to ViewB. The stack should be [ViewA (root), ViewB, ViewC].

What caused the misbehaviour and how can I resolve this?

答案1

得分: 1

你可以如下修改ViewB的代码:

  1. struct ViewB: View {
  2. let items: [Item] = [
  3. Item(title: "项目1", description: "这是项目1"),
  4. Item(title: "项目2", description: "这是项目2")
  5. ]
  6. var body: some View {
  7. List(items) { item in
  8. NavigationLink {
  9. ViewC(item: item)
  10. } label: {
  11. Text(item.title)
  12. }
  13. }
  14. }
  15. }

SwiftUI NavigationStack: 列表视图导航行为意外
```

英文:

You can modify the code of ViewB as follows:

  1. struct ViewB: View {
  2. let items: [Item] = [
  3. Item(title: "Item 1", description: "This is item 1"),
  4. Item(title: "Item 2", description: "This is item 2")
  5. ]
  6. var body: some View {
  7. List(items) { item in
  8. NavigationLink {
  9. ViewC(item: item)
  10. } label: {
  11. Text(item.title)
  12. }
  13. }
  14. }
  15. }

<img src="https://i.stack.imgur.com/mfFtZ.gif" width="200" />

huangapple
  • 本文由 发表于 2023年6月1日 10:01:12
  • 转载请务必保留本文链接:https://go.coder-hub.com/76378239.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定