I have a UITableView and I made a custom cellview to add a button inside each cell, the button is supposed to change its color when clicked. Although the data is updated and printed correctly, the view always lags one step behind i.e. when I click the first button it doesn't change its color until I click the next one.I suspect that the reloadRows() function causes this problem when called from inside the tableview Cell.
import UIKit
class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
var mlist = [["1","2","3"], ["4","5","6","7","8"],["9","10"],["11","12"],["13","14"]]
var leagues = ["LaLiga", "Premier League", "Bundesliga", "Serie A", "Ligue 1"]
var hidden = Set<Int>()
@IBOutlet weak var tbl: UITableView!
var fv = Set<IndexPath>()
func indxs(_ section:Int) -> [IndexPath] {
var indxs = [IndexPath]()
for row in 0..<mlist[section].count {
indxs.append(IndexPath(row: row, section: section))
}
return indxs
}
@objc
private func hideSection(sender: UIButton) {
let section = sender.tag
if hidden.contains(section) {
hidden.remove(section)
tbl.insertRows(at: indxs(section), with: .fade)
}else{
hidden.insert(section)
tbl.deleteRows(at: indxs(section), with: .fade)
}
}
func cellMethod(cell: UITableViewCell) {
guard let i = tbl.indexPath(for: cell) else { return }
if fv.contains(i){fv.remove(i)}else{fv.insert(i)}
tbl.reloadRows(at: [i], with: .none)
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
if hidden.contains(section) {
return 0
}
return mlist[section].count
}
func numberOfSections(in tableView: UITableView) -> Int {
return mlist.count
}
func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
let sectionButton = UIButton()
sectionButton.setTitle(leagues[section], for: .normal)
sectionButton.backgroundColor = .purple
sectionButton.tag = section
sectionButton.addTarget(self, action: #selector(self.hideSection(sender:)), for: .touchUpInside)
return sectionButton
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell1", for: indexPath) as! mcell
cell.link = self
cell.textLabel?.text = mlist[indexPath.section][indexPath.row]
if fv.contains(indexPath){
cell.accessoryView?.tintColor = .orange
}else{
cell.accessoryView?.tintColor = .gray
}
return cell
}
override func viewDidLoad() {
super.viewDidLoad()
tbl.register(mcell.self, forCellReuseIdentifier: "cell1")
}
}
import UIKit
class mcell: UITableViewCell{
var link:ViewController?
override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) {
super.init(style: style, reuseIdentifier: reuseIdentifier)
let starButton = UIButton(type: .system)
starButton.setImage(#imageLiteral(resourceName: "fav_star"), for: .normal)
starButton.frame = CGRect(x: 0, y: 0, width: 50, height: 50)
starButton.tintColor = .red
starButton.addTarget(self, action: #selector(handleMarkAsFavorite), for: .touchUpInside)
accessoryView = starButton
}
@objc private func handleMarkAsFavorite() {
print(self.textLabel!.text!)
link?.cellMethod(cell: self)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}