我在以表格视图显示JSON图像时遇到麻烦 [英] I'm having troubles displaying an image from JSON in a Table View

查看:69
本文介绍了我在以表格视图显示JSON图像时遇到麻烦的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试显示来自API的图像.这些图像位于URL内,我想用所有数组填充一个表格视图",但是在表格视图"中仅显示一张图像.

I'm trying to display images that comes from an API. The images are inside an URL and I want to fill a Table View with all the array, but it shows only one image at the Table View.

这是我的代码:

   struct Autos {
        let Marca:String
        let Modelo:String
        let Precio:String
        let RutaImagen:String

    init?(_ dict:[String:Any]?){
        guard let _dict = dict,
            let marca=_dict["Marca"]as?String,
            let modelo=_dict["Modelo"]as?String,
            let precio=_dict["Precio"]as?String,
            let rutaImagen=_dict["RutaImagen"]as?String

            else { return nil }

        self.Marca = marca
        self.Modelo = modelo
        self.Precio = precio
        self.RutaImagen = rutaImagen
   }
}

  var arrAutos = [Autos]()

 func getImage(from string: String) -> UIImage? {
        // Get valid URL
        guard let url = URL(string: string)
            else {
                print("Unable to create URL")
                return nil
        }
    var image: UIImage? = nil
    do {
        // Get valid data
        let data = try Data(contentsOf: url, options: [])

        // Make image
        image = UIImage(data: data)
    }
    catch {
        print(error.localizedDescription)
    }

    return image
}

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return 9
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
      let cell = tableView.dequeueReusableCell(withIdentifier: "carsCell", for: indexPath) as! CarsDetailTableViewCell
      let url = URL(string: "http://ws-smartit.divisionautomotriz.com/wsApiCasaTrust/api/autos")!

        let task = URLSession.shared.dataTask(with: url) {
            (data, response, error) in

            guard let dataResponse = data, error == nil else {
                print(error?.localizedDescription ?? "Response Error")
                return
            }

            do {
                let jsonResponse = try JSONSerialization.jsonObject(with: dataResponse, options: []) as? NSArray
                self.arrAutos = jsonResponse!.compactMap({ Autos($0 as? [String:String])})

                DispatchQueue.main.async {
                    // Get valid string
                    let string = self.arrAutos[indexPath.row].RutaImagen
                    if let image = self.getImage(from: string) {
                        // Apply image
                        cell.imgCar.image = image
                    }
                    cell.lblBrand.text = self.arrAutos[indexPath.row].Marca
                    cell.lblPrice.text = self.arrAutos[indexPath.row].Precio
                    cell.lblModel.text = self.arrAutos[indexPath.row].Modelo
                }

            } catch let parsingError {
                print("Error", parsingError)
            }
        }
        task.resume()

    return cell
}

JSON序列化工作正常,因为其他数据在表视图中正确显示,问题出在图像上,因为在表视图中仅出现一个图像,其他行为空.有人有建议吗?

The JSON serialization is working fine, because the other data is showed correctly at the table view, the issue is with the image, because in the table view only appears one image, the other rows are empty. Does anyone have an advise?

推荐答案

我认为您应该先下载完整的数据,然后再加载tableview并在完成处理程序中重新加载tableview.在viewDidLoad()中调用loadData()方法.

I think you should download your full data before loading tableview and reload tableview in the completion handler. Call loadData() method in your viewDidLoad().

fileprivate func loadData() {

    let url = URL(string: "http://ws-smartit.divisionautomotriz.com/wsApiCasaTrust/api/autos")!

    let task = URLSession.shared.dataTask(with: url) {
        (data, response, error) in

        guard let dataResponse = data, error == nil else {
            print(error?.localizedDescription ?? "Response Error")
            return
        }

        do {
            let jsonResponse = try JSONSerialization.jsonObject(with: dataResponse, options: []) as? NSArray
            self.arrAutos = jsonResponse!.compactMap({ Autos($0 as? [String:String])})

            DispatchQueue.main.async {
                self.tableView.reloadData()
            }

        } catch let parsingError {
            print("Error", parsingError)
        }
    }
    task.resume()
}

要在tableView单元格中加载图像,请在background线程中下载图像,然后在main线程中更新imageView.

For loading images in tableView cell, download the image in background thread and then update the imageView in the main thread.

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

        // Get valid string
    let string = self.arrAutos[indexPath.row].RutaImagen
        //print(string)
    cell.lblBrand.text = self.arrAutos[indexPath.row].Marca
    cell.lblPrice.text = self.arrAutos[indexPath.row].Precio
    cell.lblModel.text = self.arrAutos[indexPath.row].Modelo
    let url = URL(string: string)
    if url != nil {
        DispatchQueue.global().async {
            let data = try? Data(contentsOf: url!)
            DispatchQueue.main.async {
                if data != nil {
                    cell.imgCar.image = UIImage(data:data!)
                }
            }
        }
    }
    return cell
}

希望这会起作用.

这篇关于我在以表格视图显示JSON图像时遇到麻烦的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆