使用 RxDatasources 实现多个部分
Implementing multiple sections with RxDatasources
我正在尝试使用 RxDatasources 制作多个部分(实际上是两个部分)。通常只有一个部分,我会这样:
剖面模型:
import Foundation
import RxDataSources
typealias NotificationSectionModel = AnimatableSectionModel<String, NotificationCellModel>
struct NotificationCellModel : Equatable, IdentifiableType {
static func == (lhs: NotificationCellModel, rhs: NotificationCellModel) -> Bool {
return lhs.model.id == rhs.model.id
}
var identity: String {
return model.id
}
var model: NotificationModel
var cellIdentifier = "NotificationTableViewCell"
}
那么实际型号:
struct NotificationModel: Codable, Equatable {
let body: String
let title:String
let id:String
}
我会像这样使用它(在视图控制器中):
private func observeTableView(){
let dataSource = RxTableViewSectionedAnimatedDataSource<NotificationSectionModel>(
configureCell: { dataSource, tableView, indexPath, item in
if let cell = tableView.dequeueReusableCell(withIdentifier: item.cellIdentifier, for: indexPath) as? BaseTableViewCell{
cell.setup(data: item.model)
return cell
}
return UITableViewCell()
})
notificationsViewModel.notifications
.map{ notifications -> [NotificationCellModel] in
return notifications.map{ NotificationCellModel( model: [=12=], cellIdentifier: NotificationTableViewCell.identifier) }
}.map{ [NotificationSectionModel(model: "", items: [=12=])] }
.bind(to: self.tableView.rx.items(dataSource: dataSource)).disposed(by: disposeBag)
}
但是我如何使用多个部分,使用不同类型的models/cells?
这是一种最坏的情况。您可以根据您的用例简化此代码:
// MARK: Model Code
struct ViewModel {
let sections: Observable<[SectionModel]>
}
typealias SectionModel = AnimatableSectionModel<String, CellModel>
enum CellModel: IdentifiableType, Equatable {
case typeA(TypeAInfo)
case typeB(TypeBInfo)
var identity: Int {
switch self {
case let .typeA(value):
return value.identity
case let .typeB(value):
return value.identity
}
}
var cellIdentifier: String {
switch self {
case .typeA:
return "TypeA"
case .typeB:
return "TypeB"
}
}
}
struct TypeAInfo: IdentifiableType, Equatable {
let identity: Int
}
struct TypeBInfo: IdentifiableType, Equatable {
let identity: Int
}
// MARK: View Code
class Example: UIViewController {
var tableView: UITableView!
var viewModel: ViewModel!
let disposeBag = DisposeBag()
private func observeTableView(){
let dataSource = RxTableViewSectionedAnimatedDataSource<SectionModel>(
configureCell: { _, tableView, indexPath, item in
guard let cell = tableView.dequeueReusableCell(withIdentifier: item.cellIdentifier, for: indexPath) as? BaseCell else { fatalError() }
cell.setup(model: item)
return cell
})
viewModel.sections
.bind(to: tableView.rx.items(dataSource: dataSource))
.disposed(by: disposeBag)
}
}
class BaseCell: UITableViewCell {
func setup(model: CellModel) { }
}
final class TypeACell: BaseCell { }
final class TypeBCell: BaseCell { }
我正在尝试使用 RxDatasources 制作多个部分(实际上是两个部分)。通常只有一个部分,我会这样:
剖面模型:
import Foundation
import RxDataSources
typealias NotificationSectionModel = AnimatableSectionModel<String, NotificationCellModel>
struct NotificationCellModel : Equatable, IdentifiableType {
static func == (lhs: NotificationCellModel, rhs: NotificationCellModel) -> Bool {
return lhs.model.id == rhs.model.id
}
var identity: String {
return model.id
}
var model: NotificationModel
var cellIdentifier = "NotificationTableViewCell"
}
那么实际型号:
struct NotificationModel: Codable, Equatable {
let body: String
let title:String
let id:String
}
我会像这样使用它(在视图控制器中):
private func observeTableView(){
let dataSource = RxTableViewSectionedAnimatedDataSource<NotificationSectionModel>(
configureCell: { dataSource, tableView, indexPath, item in
if let cell = tableView.dequeueReusableCell(withIdentifier: item.cellIdentifier, for: indexPath) as? BaseTableViewCell{
cell.setup(data: item.model)
return cell
}
return UITableViewCell()
})
notificationsViewModel.notifications
.map{ notifications -> [NotificationCellModel] in
return notifications.map{ NotificationCellModel( model: [=12=], cellIdentifier: NotificationTableViewCell.identifier) }
}.map{ [NotificationSectionModel(model: "", items: [=12=])] }
.bind(to: self.tableView.rx.items(dataSource: dataSource)).disposed(by: disposeBag)
}
但是我如何使用多个部分,使用不同类型的models/cells?
这是一种最坏的情况。您可以根据您的用例简化此代码:
// MARK: Model Code
struct ViewModel {
let sections: Observable<[SectionModel]>
}
typealias SectionModel = AnimatableSectionModel<String, CellModel>
enum CellModel: IdentifiableType, Equatable {
case typeA(TypeAInfo)
case typeB(TypeBInfo)
var identity: Int {
switch self {
case let .typeA(value):
return value.identity
case let .typeB(value):
return value.identity
}
}
var cellIdentifier: String {
switch self {
case .typeA:
return "TypeA"
case .typeB:
return "TypeB"
}
}
}
struct TypeAInfo: IdentifiableType, Equatable {
let identity: Int
}
struct TypeBInfo: IdentifiableType, Equatable {
let identity: Int
}
// MARK: View Code
class Example: UIViewController {
var tableView: UITableView!
var viewModel: ViewModel!
let disposeBag = DisposeBag()
private func observeTableView(){
let dataSource = RxTableViewSectionedAnimatedDataSource<SectionModel>(
configureCell: { _, tableView, indexPath, item in
guard let cell = tableView.dequeueReusableCell(withIdentifier: item.cellIdentifier, for: indexPath) as? BaseCell else { fatalError() }
cell.setup(model: item)
return cell
})
viewModel.sections
.bind(to: tableView.rx.items(dataSource: dataSource))
.disposed(by: disposeBag)
}
}
class BaseCell: UITableViewCell {
func setup(model: CellModel) { }
}
final class TypeACell: BaseCell { }
final class TypeBCell: BaseCell { }