Swift UITableView: How to Load data from JSON

后端 未结 3 657
一向
一向 2021-02-06 13:35

I am beginner in Swift and would like some help for my first application.I hope that I can explain it well. I am developing and app which is loading information from a JSON File

3条回答
  •  鱼传尺愫
    2021-02-06 14:08

    First of all, don't use multiple arrays for the data source. They are quite error-prone because you are responsible to keep the number of items in sync.

    • Since Swift is an object-oriented language use a custom struct as model

      struct Fruit {
        let name : String
        let imageURL : NSURL
        let description : String
      }
      
    • Declare an empty Swift array of Fruit as data source array. Basically use always Swift native collection types (rather than NSArray and NSDictionary) because they contain the type information.

      var fruits = [Fruit]()
      
    • Create a function to parse the JSON and reload the table view. The code assumes that the JSON file is named jsonFile.json and is located in the application bundle. Further it uses the SwiftyJSON library.

      func parseFruits() {
        guard let url = NSBundle.mainBundle().URLForResource("jsonFile", withExtension: "json"), jsonData = NSData(contentsOfURL: url) else {
          print("Error finding JSON File")
          return
        }
      
        let jsonObject = JSON(data: jsonData)
      
        let fruitArray = jsonObject["fruits"].arrayValue
        for aFruit in fruitArray {
          let name = aFruit["Name"].stringValue
          let imageURL = aFruit["Picture"].stringValue
          let description = aFruit["Description"].stringValue
      
          let fruit = Fruit(name: name, imageURL: NSURL(string:imageURL)!, description:description)
          fruits.append(fruit)
        }
      
        self.tableView.reloadData()
      }
      
    • in viewWillAppear call the parse function

      override func viewWillAppear() {
        super.viewWillAppear()
        parseFruits()
      }
      
    • These are the table view data source delegate methods assuming the identifier of the cell is Cell and the style of the cell is Right Detail or Subtitle

      override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return fruits.count
      }
      
      override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath)
        let fruit = fruits[indexPath.row]
        cell.textLabel!.text = fruit.name
        cell.detailTextLabel?.text = fruit.description
        // add code to download the image from fruit.imageURL
        return cell
      }
      

    Edit:

    In Swift 4 everything became much shorter and more convenient. The most significant change is to drop SwiftyJSON and use Decodable

    struct Fruit : Decodable {
       let name : String
       let imageURL : URL
       let description : String
    }
    
    func parseFruits() {
        let url = Bundle.main.url(forResource:"jsonFile", withExtension: "json")!
        let jsonData = try! Data(contentsOfURL: url)
        self.fruits = try! JSONDecoder().decode([Fruit].self, from: jsonData)
        self.tableView.reloadData()
    }
    

提交回复
热议问题