Replacing UITableViewDiffableDataSource with DifferenceKit
This commit is contained in:
parent
7d838e4e07
commit
1c86331d7d
@ -184,15 +184,7 @@ class Vehicle: Object, Decodable, Identifiable, Differentiable, Cloneable {
|
||||
var osagoContracts = List<Osago>()
|
||||
var ads = List<VehicleAd>()
|
||||
|
||||
var identifier: String = ""
|
||||
var id: String {
|
||||
if self.identifier.isEmpty {
|
||||
self.identifier = self.number
|
||||
}
|
||||
return self.identifier
|
||||
}
|
||||
|
||||
var differenceIdentifier: String { id }
|
||||
var differenceIdentifier: String { self.number }
|
||||
|
||||
func isContentEqual(to source: Vehicle) -> Bool {
|
||||
return self == source
|
||||
@ -266,27 +258,19 @@ class Vehicle: Object, Decodable, Identifiable, Differentiable, Cloneable {
|
||||
if let ads = try container.decodeIfPresent([VehicleAd].self, forKey: .ads) {
|
||||
self.ads.append(objectsIn: ads)
|
||||
}
|
||||
|
||||
self.identifier = self.number
|
||||
}
|
||||
|
||||
required init() {
|
||||
super.init()
|
||||
self.identifier = self.number
|
||||
}
|
||||
|
||||
init(_ number: String) {
|
||||
self.identifier = number
|
||||
self.number = number
|
||||
self.addedDate = Date().timeIntervalSince1970
|
||||
self.updatedDate = self.addedDate
|
||||
}
|
||||
|
||||
func getNumber() -> String {
|
||||
if self.identifier.isEmpty {
|
||||
self.identifier = self.number
|
||||
}
|
||||
|
||||
return self.number
|
||||
}
|
||||
|
||||
|
||||
@ -5,39 +5,25 @@ import ExceptionCatcher
|
||||
|
||||
typealias FilterPredicate<T> = (T) -> Bool
|
||||
|
||||
class RealmDiffableDataSourse<Item>: UITableViewDiffableDataSource<DateSection<Item>, Item> where Item: Hashable & ContentEquatable & ContentIdentifiable {
|
||||
override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
|
||||
return snapshot().sectionIdentifiers[section].header
|
||||
}
|
||||
|
||||
override func tableView(_ tableView: UITableView, canEditRowAt indexPath: IndexPath) -> Bool {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
class RealmSectionedDataSource<Item,Cell> where Item: Object & Identifiable & Dated & Differentiable & Cloneable, Cell: UITableViewCell & ConfigurableCell, Cell.Item == Item {
|
||||
class RealmSectionedDataSource<Item,Cell>: NSObject, UITableViewDataSource
|
||||
where Item: Object & Identifiable & Dated & Differentiable & Cloneable,
|
||||
Cell: UITableViewCell & ConfigurableCell,
|
||||
Cell.Item == Item {
|
||||
|
||||
private var tv: UITableView
|
||||
private var data: Results<Item>
|
||||
private var notificationToken: NotificationToken?
|
||||
private var sections: [DateSection<Item>] = []
|
||||
private var cellIdentifier: String
|
||||
private var lastUpdateTime = Date()
|
||||
private var dataSource: RealmDiffableDataSourse<Item>!
|
||||
private var filterPredicate: FilterPredicate<Item>?
|
||||
|
||||
init(table: UITableView, data: Results<Item>, cellIdentifier: String = String(describing: Cell.self)) {
|
||||
self.tv = table
|
||||
self.data = data
|
||||
self.cellIdentifier = cellIdentifier
|
||||
|
||||
self.dataSource = RealmDiffableDataSourse<Item>(tableView: table) { tv, ip, model -> UITableViewCell? in
|
||||
let cell = tv.dequeueReusableCell(withIdentifier: self.cellIdentifier, for: ip) as? Cell
|
||||
cell?.configure(with: model)
|
||||
return cell
|
||||
}
|
||||
self.dataSource.defaultRowAnimation = .fade
|
||||
self.tv.dataSource = self.dataSource
|
||||
super.init()
|
||||
self.tv.dataSource = self
|
||||
self.tv.reloadData()
|
||||
|
||||
self.notificationToken = self.data.observe { changes in
|
||||
switch changes {
|
||||
@ -50,6 +36,30 @@ class RealmSectionedDataSource<Item,Cell> where Item: Object & Identifiable & Da
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - UITableViewDataSource
|
||||
|
||||
func numberOfSections(in tableView: UITableView) -> Int {
|
||||
return self.sections.count
|
||||
}
|
||||
|
||||
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
|
||||
return self.sections[section].elements.count
|
||||
}
|
||||
|
||||
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
|
||||
guard let cell = tableView.dequeueReusableCell(withIdentifier: self.cellIdentifier, for: indexPath) as? Cell else {
|
||||
return UITableViewCell()
|
||||
}
|
||||
|
||||
let item = self.sections[indexPath.section].elements[indexPath.row]
|
||||
cell.configure(with: item)
|
||||
return cell
|
||||
}
|
||||
|
||||
func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
|
||||
return self.sections[section].header
|
||||
}
|
||||
|
||||
// MARK: - Public
|
||||
|
||||
@ -62,13 +72,12 @@ class RealmSectionedDataSource<Item,Cell> where Item: Object & Identifiable & Da
|
||||
if let predicate = self.filterPredicate {
|
||||
items = items.filter(predicate)
|
||||
}
|
||||
self.sections = items.groupedByDate()
|
||||
var snapshot = NSDiffableDataSourceSnapshot<DateSection<Item>, Item>()
|
||||
snapshot.appendSections(self.sections)
|
||||
for section in self.sections {
|
||||
snapshot.appendItems(section.elements, toSection: section)
|
||||
|
||||
let newSections = items.groupedByDate()
|
||||
let changeset = StagedChangeset(source: self.sections, target: newSections)
|
||||
self.tv.reload(using: changeset, with: animated ? .fade : .none) { newSects in
|
||||
self.sections = newSects
|
||||
}
|
||||
self.dataSource.apply(snapshot, animatingDifferences: animated, completion: nil)
|
||||
}
|
||||
|
||||
func setFilterPredicate(_ predicate: FilterPredicate<Item>?) {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user