I'm working on an app that displays music records in a table. The table is divided in a section for each day.
The code works as intended, but as soon as an item gets deleted, some rows are rendered white. However, those white rows still can be deleted, but don't respond to the
didSelectRowAt
.Animation to illustrate the behavior
https://i.stack.imgur.com/r51ia.gif
View Hierarchy Debugger
https://i.stack.imgur.com/9Ekz0.png
Can't find the cell using the view hierarchy debugger either..
My attempt
I've created a
UITableViewController
subclass and implemented the protocols UITableViewDataSource
& UITableViewDelegate
.appData
is a structure, which conforms the Codable
protocol and is encoded & decoded as the app cycles through it's states.appData.scannedAlbums
isa dictionary of String: [ScannedAlbum]
(i.e. "2018-02-21": [ album1, album2, album3 ... ])Before I refactored the code to use sections, the view controller no problems to render the cell, even after an item was deleted, or at least it did not appear.... :/
HistoryTableViewController
class HistoryTableViewController: UITableViewController {
let appDelegate = UIApplication.shared.delegate as! AppDelegate
[...]
UITableViewDataSource
override func numberOfSections(in tableView: UITableView) -> Int {
guard let sections = appDelegate.appData?.scannedAlbums else { return 0 }
return sections.count
}
override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
guard let albumsInSection = appDelegate.appData?.getAlbums(in: section) else { return 0 }
return albumsInSection.count
}
UITableViewDelegate
override func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
if editingStyle == .delete {
guard let dateString = appDelegate.appData?.getDateString(for: indexPath.section) else {return}
guard let albumsInSection = appDelegate.appData?.getAlbums(in: indexPath.section) else {return}
guard let index = albumsInSection.index(of: albumsInSection[indexPath.row]) else {return}
if albumsInSection.count == 1 {
appDelegate.appData?.scannedAlbums.removeValue(forKey: dateString)
tableView.deleteSections([indexPath.section], with: .automatic)
}
else {
appDelegate.appData?.scannedAlbums[dateString]?.remove(at: index)
tableView.deleteRows(at: [indexPath], with: .automatic)
}
}
}
Wrapping the inner block of commit editinStyle in
DispatchQueue.main.async
removes those empty/white rows, but introduces animation bugs when deleting the row.Could someone explain me what's going on here?