Swift DRY collectionView(_ cellForItemAt) 调用
Posted
技术标签:
【中文标题】Swift DRY collectionView(_ cellForItemAt) 调用【英文标题】:Swift DRY collectionView(_ cellForItemAt) call 【发布时间】:2018-02-27 18:58:00 【问题描述】:当我有不同类型的单元格时,我发现自己经常做这种重复的代码。有没有办法把它弄干?或者它是否尽可能好。
override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
switch cells[indexPath.item].type
case .aCell:
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: ACellID, for: indexPath) as! ACell
cell.data = somedata
return cell
case .bCell:
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: BCellID, for: indexPath) as! BCell
cell.data = somedata
return cell
case .cCell:
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: CCellID, for: indexPath) as! CCell
cell.data = somedata
return cell
我正在考虑让所有单元格采用 protocol
并将它们放入一个数组中
【问题讨论】:
我看到相同的模块 var 它们之间的主要区别是什么?? 不管怎样,我在很多不同的代码库中都有这种模式,我个人认为任何进一步删除重复的尝试都违反了其他一些编程原则,或者只是没有改进解决方案。 【参考方案1】:据我了解,您可以使用所有单元格都可以遵守的协议,并扩展您的单元格类型枚举以返回单元格 ID,这样您就不需要每次都切换到出列。
enum CellType
case aCell, bCell, cCell
var id: String
switch self
case .aCell: return "aCellId"
case .bCell: return "bCellId"
case .cCell: return "cCellId"
protocol CellData
// Remove since you probably have your modlue type.
typealias Module = String
var type: CellType get
var modlues: [Module] get // Module type
protocol CommonCellProperty: AnyObject
var data: CellData! get
typealias CommonCell = CommonCellProperty & UICollectionViewCell
class MasterCell: UICollectionViewCell, CommonCellProperty
var data: CellData! // set data
class HolderCell: UICollectionViewCell, CommonCellProperty
var data: CellData! // set data
//...
class ViewController: UIViewController, UICollectionViewDataSource
var cells: [CellData] = []
override func viewDidLoad()
super.viewDidLoad()
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
let cellData: CellData = cells[indexPath.section]
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: cellData.type.id, for: indexPath) as! CommonCell
//cell.data = somedata
return cell
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int
return cells.count
【讨论】:
【参考方案2】:是的,如果这真的是您的代码模式并且唯一不同的是标识符,我建议创建一个字典,其中键是单元格类型,值是标识符:
//Create a dictionary to map from cell type to identifier
let cellIDs = [
.aCell: ACellID,
.bCell: BCellID,
.cCell: CCellID
]
//Define a common class for the different cell types
class MyCell: UICollectionViewViewCell
var data: Data
override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
let cell: MyCell
let cellType = cells[indexPath.item].type
let cellIdentifier = cellIDs[cellType]
cell = collectionView.dequeueReusableCell(
withReuseIdentifier:
cellIdentifier,
for: indexPath) as! MyCell
cell.data = someData
return cell
或者,将另一个字段 identifier
添加到包含每个单元格类型的数组 cells
中,然后像当前处理单元格类型一样从该数组中获取单元格的重用标识符。
【讨论】:
在 OP 中,单元格被实例化为不同的 UITableViewCell 子类。此解决方案不适用于此。以上是关于Swift DRY collectionView(_ cellForItemAt) 调用的主要内容,如果未能解决你的问题,请参考以下文章
Swift:按下collectionView项目时推送新视图
swift 优化Swift CollectionView和TableView
Swift 3 - CollectionView 选择不可见
CollectionView 在 StackView (Swift) 中消失
在 iOS Swift 中,在 Swift 4 中的 TableView 中为 CollectionView 集成不同的数组