Peter Jacobs
Peter Jacobs

Reputation: 1667

SwiftUI NavigationLink highlight staying highlighted after returning to previous view

I have a series of views in SwiftUI. One is a "Menu View" which consists of a List of NavigationLinks wrapped in a NavigationView.

The code is as follows.

var body: some View {
        NavigationView {
            List {
                HStack {
                    NavigationLink(destination: History(), isActive: $isHistoryViewActive) {
                    Image(systemName: "clock")                        
                    Text("History")                    
                    }
                }
                
                HStack {
                    NavigationLink(destination: Settings(), isActive: $isSettingsActive) {
                        Image(systemName: "gear")
                        Text("Settings")
                    }
                }
                
                HStack {
                    Image(systemName: "info.circle.fill")
                    Button(action: {
                        ...
                    }) {
                        Text("My Button")
                    }
                }
            }
        }
   }

The Settings view is as follows

var body: some View {
     List {
        ...
        Section(header: "Background Music") {
           Toggle("Play", isOn: $isBackGroundMusicOn)
        }
           
        Section(header: "Voice Setting") {
           HStack {
              NavigationLink(destination: VoiceList() {
                 Text(self.voiceNames[self.selectedVoice])
           }
        }
     }
}

And lastly, the VoiceList view is as follows:

var body: some View {
        List {
            ForEach(0 ..< VoiceList.voiceNames.count) {voiceIndex in
                HStack {
                    Button(action: {
                        voiceChanged(selectedVoice: voiceIndex)
                    }){
                        Text(VoiceList.voiceNames[voiceIndex])
                    }
                    Spacer()
                    Image(systemName: "checkmark")
                        .frame(alignment: .trailing)
                        .foregroundColor(.blue)
                        .isHidden(hidden: voiceIndex != selectedVoice)
                }
            }
        }
}

The problem that I am having is that when the app returns from the VoiceList view to the Settings view, the NavigationLink remains highlighted, as if it is still active, as shown in the attached screenshot. I honestly have no idea what may be causing this. Any ideas or insights are greatly appreciated.

enter image description here

Upvotes: 4

Views: 709

Answers (2)

Koraktor
Koraktor

Reputation: 42893

You can use a onReceive action on the List:

List {
    …
}.onReceive(NotificationCenter.default.publisher(for: UITableView.selectionDidChangeNotification)) {
    guard let tableView = $0.object as? UITableView,
          let selectedRow = tableView.indexPathForSelectedRow else { return }

    tableView.deselectRow(at: selectedRow, animated: true)
}

This will deselect the selected row.

Credit for the initial idea for this workaround goes to Pivaisan (from this Apple Developer thread).

Upvotes: 6

Wesley Brito
Wesley Brito

Reputation: 163

I had the same problem working with List, to solve this i use: UITableViewCell.appearance().selectionStyle = .none, but as you can expected you will not have the selection aspect, so the right way is try to store the state of selection and clean before leave the screen but in my trys i have no idea how to do that.

Example:

struct YourApp: App {
    
    init() {
        UITableView.appearance().backgroundColor = .clear
        UITableViewCell.appearance().selectionStyle = .none
    }

    var body: some Scene {
        WindowGroup {
            ContentView()
        }
    }
}

Upvotes: 0

Related Questions