SwiftUI NavigationLink freezing when tapped

Any one getting any issues with NavigaitonLink to seemingly innocuous views freezing when tapped on? 1 CPU at 100% memory steadily increasing until app gets killed by the system. Will freeze if any NavigationLink on the view is tapped if certain views are linked to using NavigaitonLink.

I note some people have been getting similar freezes if they use @AppStorage, but I'm not using @AppStorage. I do use CoreData tho. tho I have some views that use core data that don't freeze. https://developer.apple.com/forums/thread/708592?page=1#736374022

has anyone experienced similar issues? or know the cause. it doesn't seem to be any of my code because if I pause the debugger it stops on system code.

I've found that in some cases setting .id(UUID()) on the navigationLink fixes the problem, but it doesn't work all the time.

I recently finished implementing programmatic SwiftUI navigation in my app and I ran into this. In my experience, it was related to using a different custom type for the navigationDestinations on different screens and having their root NavigationStack path bound to a NavigationPath.

To fix it, I ended up making my own NavigationDestination enum with a list of all possible navigation destinations in my app.

Now, every .navigationDestionation in my app is for NavigationDestination.self and the root NavigationStack is bound to an array of [NavigationDestination]. No more freezing!

I'm having the same issue. I tried everything I could google and ChatGPT...only thing that worked for me is to remove the path with the custom object and let the stack use the default path. no more freezing.

I've had similar issue. When clicking NavigationLink there was an infinite init loop. It appears to be caused by initiating a class object labeled as @State instead of @StateObject.

@State var viewModel = PortalSelectionViewModel() corrected to @StateObject var viewModel = PortalSelectionViewModel()

For me it started happening when I added

@Environment(.dismiss) var dismiss

in one of the views that also contains navigationDestination

@emovla did you use .environment or .environmentObject in "navigationDestination" ? remove that, you will find loop won't happen anymore. To complete fix this problem, use NavigationLink(destination,lable) instead of navigationDestination

I have had this same issue, after hearing you say about cpu maxing I checked my own program and saw that was the same case for me.

After some playing around here's what I noticed:

  • Clicking the NavigationLink caused my app to stop responding
  • Clicking the NavigationLink caused my CPU to constantly be at 99-100%
  • Clicking the NavigationLink caused my App Memory to steadily increase in about the same increment it took to load the page in another view
  • Calling the destination view that was causing an error in a different parent view no longer causes an error and the destination view loads
  • The NavigationLink doesn't work anywhere within the view, I tested in multiple places in the ViewBuilder
  • The destination view was tested with a newly generated object, JobFile(), to rule out it being unable to locate the custom object job from the list it originally comes from

Some notes about the destination view:

  • The body of the destination view was a simple body of Hello, World!, so the error is probably happening upon initialization or in the NavigationLink itself
  • The destination view only has 2 properties: var body: some view and @Binding var job: JobFile, where JobFile is a small, simple, and Identifiable object
  • The destination view is using the default initializer, there is not a custom init() implemented

Parent view notes:

  • The parent view originates from a NavigationStack
  • The parent view is consistently located at a 3rd level in its parent NavigationStack

It seems there is something that may be wrong with the parent view itself, or how it is working in tandem with the navigation stack. Any help would be appreciated.

I'm having a similar issue when using SwiftData. If I do an if let desiredObject = modelContext.model(for: desiredObjectId) as ? Type (or the registeredModel version) in a .navigationDestination(item: $desiredObjectId), the Swift Data object will be found and assigned but the view doesn't finish initializing. Even a simple Text("") won't load. Adding a print statement to a View's init shows it printing infinitely.

Thank you @emovla, removing the @Environment(.dismiss) (which was unnecessary anyway in my case) fixed it for me.

Thanks @emovla. Just run into this problem with the iPadOS 17.4.1 update. Previously no problems! Anyway , your suggestion has been a lifesaver.

Thanks @emovla, the same issue - @Environment(.dismiss) causes app hanging.

I found this post by a SwiftUI engineer describing the issue, what's causing it and how to fix it.

https://hachyderm.io/@teissler/112533860374716961

Basically, if the view in the navigationDestination references any property in the presenting view, it will capture self and all its properties.

This is a problem if you have environment values that are not Equatable (like \.dismiss) and will cause a SwiftUI cycle that freezes the app.

The solution is to use a capture list in the navigationDestination closure to only capture the properties that are needed to construct the presented view. Also, if you have custom environment values, make them Equatable whenever possible to avoid this issue.

Anyone who comes across this may want to check this related SO post: https://stackoverflow.com/questions/76123128/navigationlink-causing-freeze-99-debug-cpu I realized that in my case I could easily just switch from NavigationStack to NavigationView and my problems all disappeared.

SwiftUI NavigationLink freezing when tapped
 
 
Q