Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Why NavigationStack's navigationDestination is not called when part of VStack?

NavigationStack .navigationDestination() is not called if the navigation stack is a child of another container.

The navigation happens visually but it only pushes to the stack a view with the typical yellow warning icon in the middle. If I make the NavigationStack the parent view then it does call the .navigationDestination() and everything works as expected except it does not satisfy the UI requirements.

iOS version: 16.2

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

Why is that and how can it be fixed?

An approximation of my code.

var body: some View {
    VStack {
        MyCustomTopBarView()
        MyAlwaysOnScreenNavigationStepsProgressBar()
        NavigationStack($path) {
            contentView()
        }
        .navigationDestination(for: NavigationState.self) { navigationState in

            switch navigationState {
            case .screen1:
                Text("screen 1")
            }
        }
        .navigationBarHidden(true)
    }
}

enter image description here

>Solution :

You just need to add .navigationDestination to the top level view within the NavigationStack, e.g…

enum NavigationState {
    case screen1
}

struct ContentView: View {
    
    @State private var path = NavigationPath()
    
    var body: some View {
        VStack {
            MyCustomTopBarView()
            MyAlwaysOnScreenNavigationStepsProgressBar()
            NavigationStack(path: $path) {
                contentView()
                    .navigationDestination(for: NavigationState.self) { navigationState in

                        switch navigationState {
                        case .screen1:
                            Text("screen 1")
                        }
                    }
                    .navigationBarHidden(true)
            }
            Button("Show content") {
                path.append(NavigationState.screen1)
            }
        }
    }
    
    func contentView() -> some View {
        Text("Content")
    }
}

struct MyCustomTopBarView: View {
    var body: some View {
        Rectangle().fill(.red)
            .frame(height: 40)
    }
}

struct MyAlwaysOnScreenNavigationStepsProgressBar: View {
    var body: some View {
        ProgressView()
            .progressViewStyle(.linear)
    }
}

enter image description here

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading