下载JSON数据然后重新加载集合视图

时间:2016-06-02 07:35:09

标签: ios json swift2

快点一个。我有一个名为NetworkService的类。它有一个设置NSURLSession和完成块的方法。我的对象类NewsItem有一个方法downloadNewsItems,它调用第一个方法并转到url,下载JSON数据,将其附加到数组并返回它。直到那一刻,一切都按照我想要的方式运作。我创建了对象并附加它然后返回它(该方法名为downloadImage,但它可以处理任何类型的数据)。

func downloadImage(completion: (NSData -> Void)) {
    let request = NSURLRequest(URL: self.url)
    let dataTask = session.dataTaskWithRequest(request) { (data, response, error) in

        if error == nil {
            if let httpResponse = response as? NSHTTPURLResponse {
                switch (httpResponse.statusCode) {
                case 200:
                    if let data = data {
                        completion(data)
                    }
                default:
                    print(httpResponse.statusCode)
                }
            }
        } else {
            print("Error: \(error?.localizedDescription)")
        }
    }

    dataTask.resume()
}

这是在我的对象类上实现相同的方法。

static func downloadNewsItems() -> [NewsItem] {

  var newsItems = [NewsItem]()

  let url = NSURL(string: "http://my-url.com.json")
  let networkService = NetworkService(url: url!)

  networkService.downloadImage { (data) -> Void in

    let jsonData = JSON(data:data)

    for item in jsonData["stories"].arrayValue {

     // print(item["title"])

      let newsArticle = NewsItem()
      newsArticle.category = item["category"].string
      newsArticle.titleText = item["title"].string
      newsArticle.paragraph1 = item["paragraph1"].string
      newsArticle.paragraph2 = item["paragraph2"].string
      newsArticle.featureImage = NSURL(string: "\(item["headerImage"].string)")
      newsArticle.date = item["date"].string
      newsArticle.majorReference = item["majorReference"].string
      newsArticle.fact = item["fact"].string

      newsItems.append(newsArticle)

    }

  print(newsItems.count)


  }

  return newsItems

}

print(newsItems.count)显示我已将我的对象正确下载并更新到字典中。现在问题来了。我有CollectionViewController。我想用方法调用得到的数据填充它。我创建一个数组并调用返回ViewDidLoad:内部对象的方法,但不是!当我打印时,我得到0而我的collectionView没有显示任何单元格。

var newsItems = [NewsItem]()

然后在viewDidLoad中:

newsItems = NewsItem.downloadNewsItems()
print(newsItems.count) 
collectionView.reloadData()

下载对象,通过我的init()方法设置并在NetworkService / NewsItem类内部添加到方法中的数组,但是当我从Collection View Controller调用该方法时,Nothing。最初我尝试了默认的JSONSerialisation路线,但我遇到了同样的问题。我想也许我做得不对。切换到第三方JSON库(SwiftyJSON)...确切的相同问题。请帮忙。我已经有3周了。我...我不能。不再是..

1 个答案:

答案 0 :(得分:2)

user2361090,

您正在进行webservice调用以获取downloadNewsItems中的所有newsItems。这是一个异步调用。因此,获取进程然后填充newsItems数组需要一点时间。但是你不是在等待它填充之前就已经填充了你已经返回它因此你将在newsItems = NewsItem.downloadNewsItems()中返回空数组。使用块来切换数据。将您的方法更改为

static func downloadNewsItems(completionBlock block : ([NewsItem]) -> ()){

    var newsItems = [NewsItem]()

    let url = NSURL(string: "http://my-url.com.json")
    let networkService = NetworkService(url: url!)

    networkService.downloadImage { (data) -> Void in

        let jsonData = JSON(data:data)

        for item in jsonData["stories"].arrayValue {

            // print(item["title"])

            let newsArticle = NewsItem()
            newsArticle.category = item["category"].string
            newsArticle.titleText = item["title"].string
            newsArticle.paragraph1 = item["paragraph1"].string
            newsArticle.paragraph2 = item["paragraph2"].string
            newsArticle.featureImage = NSURL(string: "\(item["headerImage"].string)")
            newsArticle.date = item["date"].string
            newsArticle.majorReference = item["majorReference"].string
            newsArticle.fact = item["fact"].string

            newsItems.append(newsArticle)

        }

        print(newsItems.count)
        //if the control comes here in background thread because you know you have to reload the collection view which is UI operation change it main thread
         dispatch_async(dispatch_get_main_queue(), { () -> Void in
            block(newsItems)
        })
    }

}

最后你可以称之为,

NewsItem.downloadNewsItems{ (passedArray) -> () in
      newsItems = passedArray
      collectionView.reloadData()
}
相关问题