0

Below in my code I have simple setup whereby my FetchRequest is filtered by a string, this string comes from a text field that the user can input into. How do I return all results if said text field is empty?

struct TechList: View {

var fetchRequest: FetchRequest<HearingDevice>
@State private var selectedDevice: String?
@ObservedObject var model = Model()
init(filter: String) {
    fetchRequest = FetchRequest<HearingDevice>(entity: HearingDevice.entity(), sortDescriptors: [], predicate: NSPredicate(format: "model CONTAINS %@", filter))

}

var body: some View {
    VStack(alignment: .center){
        List(fetchRequest.wrappedValue, id: \.self) { device in
            VStack(alignment: .center) {
                HStack{
                    Text(device.model ?? "Unknown" + " ")
                        .font(.system(size: 17))
                        .fontWeight(.medium)
                     .foregroundColor(self.selectedDevice == device.model ? Color.white:Color.init(hex: "47535B"))
                         .multilineTextAlignment(.leading)
                        .padding(.leading)
                 Spacer()
             }
            }
            .frame(minWidth: 0, maxWidth: .infinity, minHeight: 0, maxHeight: 60)
            .background(self.selectedDevice == device.model ? Color.init(hex: "666699"):Color.init(hex: "F6F6F6"))
            .cornerRadius(7.0)
            .onTapGesture {
            self.model.deviceModel = device.model!
             withAnimation(.spring()){
                 self.selectedDevice = device.model!
             }
          }
        }
        .frame(minWidth: 0, maxWidth: .infinity, minHeight: 0, maxHeight: .infinity)
        .padding(.top, 160.0)
        .padding(.bottom, 20.0)
    }
  }
}

Is there a way I can return ALL of my results if there is no filter provided?

Update based on Asperi's comment:

struct TechList: View {
var filter: String
@FetchRequest(fetchRequest: HearingDevice.fetchRequest()) var fetchRequest: FetchedResults<HearingDevice>
@State private var selectedDevice: String?
@ObservedObject var model = Model()
init(filter: String) {
    self.filter = filter
    _fetchRequest = FetchRequest<HearingDevice>(entity: HearingDevice.entity(), sortDescriptors: [], predicate: NSPredicate(format: "model CONTAINS %@", filter))

}

var body: some View {
    VStack(alignment: .center){
        List(fetchRequest, id: \.self) { device in
            VStack(alignment: .center) {
                HStack{
                    Text(device.model ?? "Unknown" + " ")
                        .font(.system(size: 17))
                        .fontWeight(.medium)
                     .foregroundColor(self.selectedDevice == device.model ? Color.white:Color.init(hex: "47535B"))
                         .multilineTextAlignment(.leading)
                        .padding(.leading)
                 Spacer()
             }
            }
            .frame(minWidth: 0, maxWidth: .infinity, minHeight: 0, maxHeight: 60)
            .background(self.selectedDevice == device.model ? Color.init(hex: "666699"):Color.init(hex: "F6F6F6"))
            .cornerRadius(7.0)
            .onTapGesture {
            self.model.deviceModel = device.model!
             withAnimation(.spring()){
                 self.selectedDevice = device.model!
             }
          }
        }
        .frame(minWidth: 0, maxWidth: .infinity, minHeight: 0, maxHeight: .infinity)
        .padding(.top, 160.0)
        .padding(.bottom, 20.0)
     }
   }
 }

I have implemented the approach from your first comment although there are no errors and the code executes fine, my list remains empty. How do I pull the fetch request into my list if I am not using .wrappedValue?

5
  • 1
    You might find Input a dynamic value into @FetchRequest, to fetch a single entity from core data in SwiftUI topic helpful Commented Dec 20, 2019 at 10:24
  • or Is there a way to modify fetched results with a predicate after they are initialized? Commented Dec 20, 2019 at 10:26
  • @Asperi Updated my question to reflect your answer :) Commented Dec 20, 2019 at 11:10
  • 1
    I think the second post if more close to your case, because if there is not filter you should not specify predicate at all. So better design would be MainView + filterString & ResultView with a reconstructed fetch request in init (as you currently do) depending on filterString content with or w/o predicate. Commented Dec 20, 2019 at 11:19
  • Hi so I got it all working but now I am faced with optimisation issues, is this something that is common when loading medium sized data sets? Filtering takes 2-3 seconds an my list of data is literally 70 items. Perhaps its my search field implementation. I am using onEditingChanged to check for changes in the predicate but filtering takes a long time. Commented Dec 20, 2019 at 13:26

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.