Navigationlink Inside .Searchable Does Not Work

NavigationLink inside .searchable does not work

NavigationLink must always be inside NavigationView, no matter what. If you want to put it outside, like inside .searchable, you should use programmatic navigation with isActive.

struct ContentView: View {

@State private var term = ""
@State private var isPresenting = false

var body: some View {
NavigationView {

/// NavigationView must only contain 1 view
VStack {
Text("Hello, world!")
.padding()

/// invisible NavigationLink
NavigationLink(destination: SecondView(), isActive: $isPresenting) { EmptyView()}
}
}
.searchable(text: $term) {
Button { isPresenting = true } label: {
Text("Go to second view")
}
}
}
}

struct SecondView: View {
var body: some View {
Text("Goodbye!")
.padding()
}
}

Result:

Working navigation link that only appears when search bar tapped

Having problem making a searchable searchbar in Swift (xcode)

The search bar and its pattern do not change whenever you are using a list. Where you got confused is not understanding that you are returning an array of the type of your data, not just a string. [String] are often used as examples because they are simple, but the confusion comes from the fact that your search text is also a String. Really, you are returning an [Type] where Type is the type of your data. In this case, that is a Country. Therefore your code becomes this:

struct CountryListView: View {

// You should just declare this as @State var, NEVER just var in a struct.
// If you are not planning to mutate this list, declare it with let
// Also, you reused "Country" which caused the compiler to be confused.
// Types should begin with a capital letter and be singular
// Names of singular instances should be lowercased.
// Names of arrays of a type should be lowercased and plural
// You will see I changed the instance you called Country to countries.
@State private var countries = CountryList.allCountries
@State private var searchText = ""

var body: some View {

NavigationView {
// The list uses searchResults which is an [Country]
// Since Country is Identifiable, you do not need the id:\.id in the list.
List(searchResults) { country in
// You didn't provide CountryDetail, so I used CountryCell for both
NavigationLink(destination: CountryCell(country: country), label: {
CountryCell(country: country)
})
}
.navigationTitle("Find your country")
.searchable(text: $searchText)
}
}

var searchResults: [Country] {
if searchText.isEmpty {
return countries
} else {
return countries.filter({ $0.title.lowercased().contains(searchText.lowercased())})
}
}

struct CountryCell: View {

let country: Country

var body: some View {
HStack {
// Since we don't have the flag assets, I just used an SF Symbol
// Please do this sort of substitution before you post.
Image(systemName: country.imageName)
.resizable()
.scaledToFit()
.frame(height: 70)
.cornerRadius(16)
.padding(.vertical, 4)

VStack(alignment: .leading, spacing: 5) {
Text(country.title)
.fontWeight(.semibold)
.lineLimit(2)
.minimumScaleFactor(0.5)

Text(country.uploadDate)
.font(.subheadline)
.foregroundColor(.secondary)
}
}
}
}
}

struct CountryList {

static let allCountries = [
// Substitued SF Font for imageName
Country(imageName: "flag",
title: "Sweden",
description: "lorumibsum lorum ibsum sim sum sam",
viewCount: 370222,
uploadDate: "date of post",
url: URL(string: "https://test.com")!),
...]
}

SwiftUI: NavigationTitle display not normal with List and search field

Eventually, I found a way to circumvent this problem on my own.

We can manually set the List Style:

.listStyle(InsetGroupedListStyle())

Then It shows normally.

SwiftUI: NavigationView focus on last selected NavigationLink

you could try this approach, using the List with selection, such
as in this example code. It does not scroll back to the beginning of the list
after selecting a destination.

struct ContentView: View {
@State private var selections = Set<Thing>()
@State var things: [Thing] = []

var body: some View {
NavigationStack {
List(things, selection: $selections){ thing in
NavigationLink(destination: Text("destination-\(thing.val)")) {
Text("item-\(thing.val)")
}
}
}
.onAppear {
(0..<111).forEach{things.append(Thing(val: $0))}
}
}
}

EDIT-1:

Since there are so many elements missing from you code, I can only guess
and suggest something like this:

struct CategoryDetailView: View {

@EnvironmentObject var blindzeln: BLINDzeln
@AppStorage ("version") var version: Int = 0

@State var shouldRefresh: Bool = false
@State private var searchText = ""

@State private var selections = Set<Thing>() // <-- same type as item in the List

let categoryTitle: String
let catID: Int

var body: some View {
VStack {
// -- here
List(blindzeln.results.filter { searchText.isEmpty || ($0.title.localizedCaseInsensitiveContains(searchText) || $0.textBody.localizedCaseInsensitiveContains(searchText)) },
id: \.entryID,
selection: $selections){ item in

NavigationLink(destination: ItemDetailViewStandard(item: item, isFavorite: false, catID: catID)) {
DisplayEntryView(item: item, catID: catID)
}
.listRowSeparatorTint(.primary).listRowSeparator(.hidden)
}
}
.searchable(text: $searchText, placement: .navigationBarDrawer(displayMode: .always), prompt: "") {}

.navigationTitle(categoryTitle)
.navigationBarTitleDisplayMode(.inline)
.listStyle(.inset)
.task{
await blindzeln.decodeCategoryData(showCategory: categoryTitle)
}
.onAppear{
blindzeln.resetData()
}
}

}

SwiftUI encountered an issue when pushing aNavigationLink. Please file a bug

The error is resolved in Xcode 14 RC



Related Topics



Leave a reply



Submit