0

Forgive me as I am extremely novice with SwiftUI... I am attempting to pull data from the CMS and put it in my app however it is throwing three errors on each attempt for the data to be retrieved and placed...

The errors are highlighting in the sections that read "api.beers.title", "api.beers.type" and "api.beers.description".

Errors

  • Value of type 'API' has no dynamic member 'beers' using key path from root type 'API'
  • Referencing subscript 'subscript(dynamicMember:)' requires wrapper 'ObservedObject.Wrapper'
  • Initializer 'init(_:)' requires that 'Binding' conform to 'StringProtocol'

API Call Code

func getArray(id: String, completion: @escaping([Entry]) -> ()) {
    let query = Query.where(contentTypeId: id)

    client.fetchArray(of: Entry.self, matching: query) { result in
        switch result {
        case .success(let array):
            DispatchQueue.main.async {
               completion(array.items)
            }
        case .failure(let error):
            print(error)
        }
    }
}

class API: ObservableObject {
    @Published var draft: [Draft] = draftData

    init() {
        getArray(id: "beers") { (items) in
            items.forEach { (item) in
                self.draft.append(Draft(
                    title: item.fields["title"] as! String,
                    type: item.fields["type"] as! String,
                    description: item.fields["type"] as! String
                ))
            }
        }
    }
}
struct LandingPageView: View {
        var body: some View {
            VStack {
                VStack {
                    Text("Problem Solved")
                    Text("Brewing Company")
                }
                .font(.system(size: 24, weight: .bold))
                .multilineTextAlignment(.center)
                .foregroundColor(Color("TextColor"))

                VStack {
                    Text("NEWS & EVENTS")
                        .font(.title)
                        .fontWeight(.bold)
                        .padding(.top, 40)
                        .foregroundColor(Color("TextColor"))

                    NewsTile()
                    
                    Text("On Draft" .uppercased())
                        .font(.title)
                        .fontWeight(.bold)
                        .padding(.top)
                        .foregroundColor(Color("TextColor"))

                    ScrollView(.horizontal, showsIndicators: false) {
                        HStack(spacing: 20) {
                            ForEach(draftData) { item in
                                GeometryReader { geometry in
                                    DraftList(beer: item)
                                        .rotation3DEffect(Angle(degrees: Double(geometry.frame(in: .global).minX - 30) / -20), axis: (x: 0, y: 10.0, z: 0))
                                }
                                .frame(width: 275, height: 200)
                                
                            }
                        }
                    .padding(.leading, 30)
                    .padding(.trailing, 30)
                }
            }
            .frame(width: 400, height: 850)
            .background(Color("PageBackground"))
            .edgesIgnoringSafeArea(.all)
            
        }
    }
}


struct DraftList: View {
    var width: CGFloat = 275
    var height: CGFloat = 200
    
    @ObservedObject var api = API()
    var beer: Draft
    
    var body: some View {
        VStack {
            Spacer()
            Text(api.beers.title)
                .font(.system(size: 24, weight: .bold))
                .padding(.horizontal, 20)
                .frame(width: 275, alignment: .leading)
                .foregroundColor(Color("TextColor"))
            
            Text(api.beers.type .uppercased())
                 .font(.system(size: 14, weight: .bold))
                 .frame(maxWidth: .infinity, alignment: .leading)
                 .padding(.horizontal, 20)
            
            Text(api.beers.description)
                .font(.system(size: 12))
                .padding(.horizontal, 20)
                .padding(.top, 10)
            Spacer()
            HStack {
//                Add OnTapGesture to bring to full view + cart options.
                Text("Click To Add To Cart")
                    .font(.footnote)
                Image(systemName: "cart")

            }
            .padding(.bottom)

            
        }
        .padding(.horizontal, 20)
        .frame(width: width, height: height)
        .background(Color("TileOrangeColor"))
        .cornerRadius(15)
        .shadow(color: Color.black.opacity(0.2), radius: 5, x: 0, y: 5)

        
    }
}

hallux
  • 61
  • 1
  • 8

1 Answers1

0
  1. Your draft is array, you can access by index like Text(api.draft[0].title)
  2. @Published var draft: [Draft] = draftData instead @Published var draft: [Draft] = []

Updated:

class API: ObservableObject {
    @Published var draft: [Draft] = [] 

    init() {
        getArray(id: "beers") { (items) in
            items.forEach { (item) in
                self.draft.append(Draft(
                    title: item.fields["title"] as! String,
                    type: item.fields["type"] as! String,
                    description: item.fields["type"] as! String
                ))
            }
        }
    }
}

struct DraftList: View {
    var width: CGFloat = 275
    var height: CGFloat = 200
    @ObservedObject var api = API()
    var body: some View {
            VStack {
             ForEach(api.draft) {item in 
                Spacer()
                Text(item.title)
                    .font(.system(size: 24, weight: .bold))
                    .padding(.horizontal, 20)
                    .frame(width: 275, alignment: .leading)
                    .foregroundColor(Color("TextColor"))
    
                ...
             }
            }
            .padding(.horizontal, 20)
            .frame(width: width, height: height)
            .background(Color("TileOrangeColor"))
            .cornerRadius(15)
            .shadow(color: Color.black.opacity(0.2), radius: 5, x: 0, y: 5)
        }
    }
Ernist Isabekov
  • 1,205
  • 13
  • 20
  • So, if I didn't want to get the first index being [0], I would need to iterate over the indices correct? – hallux Sep 23 '20 at 02:16
  • Yes. You need to foreach array, kinda foreach(draft){ item in Text(item.title) ... } – Ernist Isabekov Sep 23 '20 at 02:19
  • Thanks. I was able to get a return but it threw a new error... 2020-09-22 22:18:26.945306-0400 PSBC[2691:4738524] Fatal error: Unexpectedly found nil while unwrapping an Optional value: file /Users/rob/Desktop/SwiftProjects/PSBC/PSBC/API.swift, line 38 – hallux Sep 23 '20 at 02:24
  • That might have helped huh! LOL My fault type: item.fields["type"] as! String, – hallux Sep 23 '20 at 02:29
  • i think need to check is Client array has got ["type"] field or can do like this type: (item["type"] as! String?) ?? "" – Ernist Isabekov Sep 23 '20 at 02:41