【问题标题】:Swift UITableView: How to Load data from JSONSwift UITableView:如何从 JSON 加载数据
【发布时间】:2016-12-28 19:53:43
【问题描述】:

我是 Swift 的初学者,希望对我的第一个应用程序有所帮​​助。我希望我能解释清楚。我正在开发一个从 JSON 文件加载信息的应用程序。你们中有人知道如何将这些信息填充到 UI 表视图单元格中。我已经开发了 3 个视图控制器,在第一个中我有一个按钮,用户必须按下它,第二个 Tableview 控制器将被打开。我已经看过如何填充它的教程,但它似乎不起作用。第三个是表格视图单元格。让我告诉你:

class TableViewController: UITableViewController {
@IBOutlet weak var Bar: UIToolbar!
var TableData:Array< String > = Array < String >()
let ImageList = ["",""]
var TitleList = ["",""]
let DescriptionList = ["",""]

我必须在单元格图像、标题和描述中显示。 这是 JSON 文件:

 {
 “fruits” : [
 {
 “Name” : “Fruit1”,
 “Picture”:”http://www.starpropertiesindia.com/blog/wp-   content/uploads/2016/08/kochi1.jpg”,
“Description”:””,
},

  {
 “Name” : “Fruit2”,
 “Picture”:”http://www.starpropertiesindia.com/blog/wp-content/uploads/2016/08/kochi1.jpg”,
 “Description”:””,

},

如果有人建议我如何继续,我将非常感激..

准备在新视图中进行转场:

@IBOutlet weak var CellDescription: UILabel!
@IBOutlet weak var CellImage: UIImageView!
@IBOutlet weak var CellTitle: UILabel!
override func awakeFromNib() {
    super.awakeFromNib()
    // Initialization code
}

【问题讨论】:

  • 我尝试了很多东西,但我不确定我是否应该展示它们,因为它们似乎是错误的
  • 可以使用第三方库吗?
  • 太棒了。请在您的项目中添加 EVReflection,我正在帮助您完成整个路径。好吗?
  • 超级,但是什么是 EVReflection 以及如何添加它?

标签: json swift uitableview


【解决方案1】:

首先,不要对数据源使用多个数组。它们很容易出错,因为您有责任保持项目数量同步。

  • 由于 Swift 是一种面向对象的语言,因此使用自定义结构作为模型

    struct Fruit {
      let name : String
      let imageURL : NSURL
      let description : String
    }
    
  • Fruit 的空Swift 数组声明为数据源数组。基本上使用 always Swift 原生集合类型(而不是 NSArrayNSDictionary),因为它们包含类型信息。

    var fruits = [Fruit]()
    
  • 创建一个函数来解析 JSON 并重新加载表格视图。该代码假定 JSON 文件名为 jsonFile.json 并位于应用程序包中。此外,它使用SwiftyJSON 库。

    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()
    }
    
  • viewWillAppear调用解析函数

    override func viewWillAppear() {
      super.viewWillAppear()
      parseFruits()
    }
    
  • 这些是表格视图数据源委托方法,假设单元格的标识符是Cell,并且单元格的样式是Right DetailSubtitle

    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
    }
    

编辑:

在 Swift 4 中,一切都变得更短更方便。最显着的变化是去掉SwiftyJSON,改用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()
}

【讨论】:

  • 非常感谢!一个额外的问题。在我的应用程序中,如果我想从你的函数中查看结果,我必须为 segue 做准备并将其发送到我的 TableViewCell.swift 我应该从你的答案中为 segue 做些什么准备?
  • 我用表格视图单元格变量更新了我的代码。基本上我希望你能理解我我必须准备好为表格视图单元格中的每个 ma 变量(CellDescription,CellImage和 CellTitle)
  • 你能帮我怎么做吗?
  • 我不明白。如果表格视图单元格属于TableViewController 中的表格视图,则不需要segue,而是在Interface Builder 中对单元格进行子类化。无论如何,异步下载图像的代码是没有问题的,看看 Apple 的sample code
  • 嘿它现在可以工作了,但是我应该在注释行中添加什么://添加代码以从fruit.imageURL下载图像
【解决方案2】:

试试这个对你有帮助

 func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell
        {
             let cell = tableView.dequeueReusableCell(withIdentifier: "TableViewCell", for: indexPath) as! TableViewCell

        var dict = array[indexPath.row]
        cell.lbl1.text = dict["Name"] as? String
        cell.lbl2.text = dict["ad_created_date"] as? String
        cell.lbl3.text = dict["phone_number"] as? String
        cell.lbl4.text = dict["id"] as? String
        cell.lbl5.text = dict["ad_zip"] as? String

        let imageUrlString = dict["Picture"]
        let imageUrl:URL = URL(string: imageUrlString as! String)!
        let imageData:NSData = NSData(contentsOf: imageUrl)!
        cell.img.image = UIImage(data: imageData as Data)



        return cell
    }

【讨论】:

    【解决方案3】:

    您已经获得了 Json 数据,只需将其放入数组中并将它们加载到表视图中,如下所示:

        var tableData:NSArray = []
    
        self.tableData = json["fruits"] as! NSArray
        // In the place of json put your json object
        self.tableView.reloadData()
    
    }
    
    override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
    
        return 1
    }
    
    override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    
        return self.tableData.count
    }
    
    override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath) as! UITableViewCell
    
        let item = self.tableData[indexPath.row] as! [String : String]
        cell.nameLabel?.text = item["Name"]
        cell.descriptionLabel?.text = item["Description"]
    
        return cell
    }
    

    【讨论】:

      猜你喜欢
      • 2013-05-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-12-21
      相关资源
      最近更新 更多