如何处理iOS UITableView中的动态Sections和Rows

问题描述 投票:3回答:3

我的问题

当我处理UITableView时,我基本上有一个数组table_data与我的部分和行。

[
   {
      title : "section A title",
      rows: [
          {data: row_1_data},
          {data: row_2_data}
      ]
   },
   {
      title : "section B title",
      rows: [
          {data: row_1_data},
          {data: row_2_data}
      ]
   },
]

我用heightForHeaderInSectioncellForRowAtindexPathtitleForHeaderInSectiondidSelectRowAtindexPath这样的方法

 if indexPath.section == 0 {
        //section A
        if indexPath.row == 0 {
             //do something with table_data[0]["rows"][0]["data"]
        }
        elesif indexPath.row == 1 {
             //do something else
        }
 }
 if indexPath.section == 1 {
      //do something for section B
 }

当我的0阵列是动态的时,使用数字1table_data等会变得很头疼。动态意味着某些部分或行可以具有不同的位置或根本不存在。

例如,我删除A部分,我的数组是

[
   {
      title : "section B title",
      rows: [
          {data: row_1_data},
          {data: row_2_data}
      ]
   }
]

我喜欢这个

self.section_A_position = 0
self.section_B_position = 1
func afterRemoveSectionA() {
    section_A_position = -999
    section_B_position = section_B_position - 1
    //write here another new sections for -1 
}

将另一个C部分添加为0元素

self.section_C_position = -999
func afterAddSectionC() {
   section_C_position = 0
   section_A_position = section_A_position + 1
   section_B_position = section_B_position + 1
}

然后在函数中使用section_positions

 if indexPath.section == section_A_position {
        //section A
        if indexPath.row == 0 {
             //do something with table_data[0]["rows"][0]["data"]
        }
        elesif indexPath.row == 1 {
             //do something else
        }
 }
 if indexPath.section == section_B_position {
      //do something for section B
 }

它看起来很简单,但是当我有许多部分和许多情况要隐藏或移动它的数组时,很难控制和添加新类型的部分。有时候我会创建section_positions_map数组来将它存储在一起并使循环中的+1-1操作。但是当我需要这种行为时,它仍然很难在每个TableViewController中组织它。

您是否知道使这部分更容易的任何方法或框架?

我的想法

  1. type属性添加到我的词典中
{
  title : "section A title",
  rows: [
      {data: row_1_data},
      {data: row_2_data}
  ]
  type : "section_a"
}

并检查if table_data[0]["type"] == "section_a"(或使用enum收集类型)

  1. 对我的词典进行子类化并检查

if table_data[0] is SubClassSectionA

但是他们两个看起来都很难看。

ios swift xcode uitableview sections
3个回答
5
投票

我在创建表时使用的方法,我知道所有可能的部分都是枚举。您为每个可能的节类型创建枚举:

enum SectionTypes { case sectionA, sectionB, sectionC }

然后创建一个变量来保存部分:

var sections: [SectionTypes]

准备好数据后,可以使用需要显示的部分填充部分。我通常也会制作一个方法来帮助获取该部分:

func getSection(forSection: Int) -> SectionTypes {
        return sections[forSection]
    }

有了这个,您就可以开始实现常见的DataSource委托方法:

func numberOfSections(in collectionView: UICollectionView) -> Int {
    return sections.count
}

func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
    switch getSection(forSection: section) {
    case .sectionA:
        return 0 //Add the code to get the count of rows for this section
    case .sectionB:
        return 0
    default:
        return 0
    }
}

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
    switch getSection(forSection: indexPath.section) {
    case .sectionA:
        //Get section A cell type and format as your need
    //etc
    }
}

1
投票

使用NSDictionary存储数据是一种不好的做法。为section(即SectionData)和row(即RowData)创建新类。您的ViewController(或其他一些数据提供程序)将保留SectionData数组,其中SectionData保留RowData数组。 RowData可能包含用于处理行选择的func,因此在didSelectRowAtindexPath中,您只需执行以下操作:

let rowData = rowDataAtIndexPath(indexPath)
rowData.tapHandler()

其中rowDataAtIndexPath是您定义的函数,它为您提供indexPath的数据。

当您需要删除某些部分时,只需将其从部分数组中删除并重新加载tableView即可。


0
投票

我认为这个谈话比你所寻求的更广泛,但他谈到了它。

https://realm.io/news/altconf-benji-encz-uikit-inside-out-declarative-programming/

© www.soinside.com 2019 - 2024. All rights reserved.