【问题标题】:UICollectionview section and rows from JSON来自 JSON 的 UICollectionview 部分和行
【发布时间】:2017-12-03 18:34:53
【问题描述】:

我正在尝试从 JSON 中为 UICollectionview 中的每顿饭设置部分。我只是做不到

{
  "meals" : [
    {
      "id" : 279,
      "unit" : "حبة",
      "disable" : "0",
      "created_at" : "2017-03-06 19:17:23",
      "time" : "فوري",
      "small" : "0",
      "type" : "2",
      "desc" : "",
      "price" : "6",
      "image" : "a4f730f447e753a995e342e12446ab1958bdb5c3136b6.jpg",
      "family_id" : "115",
      "updated_at" : "2017-03-06 19:17:23",
      "deleted_at" : null,
      "medium" : "0",
      "large" : "0",
      "name" : "ساندوتش فلافل كعك بالسمسم "
    },
    {
      "id" : 280,
      "unit" : "حبة",
      "disable" : "0",
      "created_at" : "2017-03-06 19:21:51",
      "time" : "فوري",
      "small" : "0",
      "type" : "2",
      "desc" : "",
      "price" : "5",
      "image" : "1c65581aa774203a4335bc6d93fe2b6358bdb6f3edb23.jpg",
      "family_id" : "115",
      "updated_at" : "2017-03-06 19:22:27",
      "deleted_at" : null,
      "medium" : "0",
      "large" : "0",
      "name" : "سندويش فلافل عربي اصناف "
    },

type 是餐食的部分名称。每顿饭都会有一个部分 1 ,2 ,3,4

现在我像这样设置 UICollectionview 的行:

func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
        if meals.count > 0 {
            self.collectionView.backgroundView = nil
            return meals.count
        }
        let rect = CGRect(x: 0,
                          y: 0,
                          width: self.collectionView.bounds.size.width,
                          height: self.collectionView.bounds.size.height)
        let noDataLabel: UILabel = UILabel(frame: rect)

        noDataLabel.text = "تقدر تطلب اي شي من \(nameOfShop.text!)"
        noDataLabel.textColor = UIColor.black
        noDataLabel.textAlignment = NSTextAlignment.center
        self.collectionView.backgroundView = noDataLabel

        return 0

    }

    func numberOfSections(in collectionView: UICollectionView) -> Int {
        return 1
    }


    func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
        let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "mealsCell", for: indexPath) as! MealCollectionViewCell

        let entry = meals[indexPath.row]

        cell.mealName.text = entry.meal_name
        cell.mealPrice.text = "\(entry.price) ريال"

        cell.mealImage.hnk_setImage(from: URL(string: entry.Logo))
        return cell

    }

这是我从 API 获取数据的方式

 let name = subJson["name"].stringValue
            let price = subJson["price"].stringValue
            let logo = subJson["image"].stringValue
            let id = subJson["id"].stringValue
           let logoString = "http://app.com/upload/img/\(logo)"

            let info = Meals(meal_id: id, Logo: logoString, meal_name: name, price: price)

            self.meals.append(info)

抱歉,代码太长了,我想我应该解释一下。

【问题讨论】:

  • 到底是什么问题?什么不工作?
  • 我想为餐点添加部分。部分名称是来自 json 的 type。每餐都附有type
  • allShops 是您的数据数组吗?那么最简单的方法是将其组织为一个数组数组,或者一个带有数组的字典(类型是每个数组的键)。这样你就可以直接在你的 dataSource 委托方法中查找每个部分的数组:而不是 allShops.count 然后你有 allShops[section].count 和而不是 let shop = allShops[indexPath.row] 你将有 let shop = allShops[indexPath.section][indexPath.row]
  • 对不起,你能再检查一下我的问题吗?不是这个代码我复制了错误的代码......

标签: ios swift uicollectionview swift4


【解决方案1】:

使用一个数组来为您的数据源建模。将 meals 初始化为数组数组,而不是 self.meals.append(info),然后:

let type = subJson["type"].intValue 
self.meals[type-1].append(info)  // note here that you may need to adjust depending on the possible values of type.

然后在collectionView(_:numberOfItemsInSection:):

if meals[section].count > 0 {
    etc...
}

numberOfSections(in:):

return meals.count

collectionView(_:cellForItemAt:):

let entry = meals[indexPath.section][indexPath.row]

或者,如果type 不是一个连续的整数列表,则Dictionary 可能是存储meals 的更好方法:

var meals = Dictionary<String, Array<Meals>>()
for type in types {
     meals[type] = []
}

...

self.meals[type] = info

这样您就不必担心数组的起始数量是否正确,如果 JSON 响应中缺少一个 type 值,它仍然可以工作。然后需要更改 UITableView dataSource 方法以将部分编号映射到您的类型键。

【讨论】:

  • 谢谢您的回答!!当您说将餐食初始化为数组时,我只是没听懂
  • 好吧,在代码中的某处声明属性meals。确保它是一个数组数组。例如。 var meals = [[Meals]]()
  • 您需要双括号,以便为每种类型获得一个单独的数组。同样重要的是:我正在创建 0、1、2、3、......如果type 不是连续整数,那么您可能需要创建一个Enum 映射您的类型。
  • 如果饭菜[section].count > 0 致命错误:索引超出范围我认为是因为类型是字符串。所以我将type 从数字更改为名称如何将其更改为使用字符串self.meals[type-1].append(info)
  • 我在 Web 服务中将类型从 Int 更改为 String
猜你喜欢
  • 1970-01-01
  • 2011-12-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-09-06
  • 2016-04-22
  • 1970-01-01
相关资源
最近更新 更多