I am trying to implement code for changing a row's button image source on click of the row. This is for a checklist table view.The table view is split into sections. Not sure what I'm doing wrong:
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
//change tickBtn's image src to tick.png
print("in didselect")
if let cell = tableView.cellForRowAtIndexPath(indexPath) as? CheckListCell {
let tickedImg = UIImage(named: "tick.png")
cell.tickBtn.setImage(tickedImg, forState: UIControlState.Selected)
//cell.tickBtn.alpha = 0
}
else{
print("in the else of didSelect")
}
}
func tableView(tableView: UITableView, didDeselectRowAtIndexPath indexPath: NSIndexPath) {
//change tickBtn's image src to unTicked.png
print("in didDeselect")
if let cell = tableView.cellForRowAtIndexPath(indexPath) as? CheckListCell{
let tickedImg = UIImage(named: "unTicked.png")
cell.tickBtn.setImage(tickedImg, forState: UIControlState.Selected)
//cell.tickBtn.alpha = 1
}
else{
print("in the else of didDeSelect")
}
}
I'm getting the logs for didSelect and didDeSelect but the image source is not changing. Must be something to do with how i'm accessing the cell and I need to take into account the section?
UPDATE:
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
//change tickBtn's image src to tick.png
let cell = tableView.cellForRowAtIndexPath(indexPath) as? CheckListCell
cell!.cellTickedImage = UIImage(named: "tick.png")
self.checkListTableView.beginUpdates()
self.checkListTableView.reloadRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Automatic)
self.checkListTableView.endUpdates()
}
func tableView(tableView: UITableView, didDeselectRowAtIndexPath indexPath: NSIndexPath) {
let cell = tableView.cellForRowAtIndexPath(indexPath) as? CheckListCell
cell!.cellTickedImage = UIImage(named: "unTicked.png")
self.checkListTableView.beginUpdates()
self.checkListTableView.reloadRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Automatic)
self.checkListTableView.endUpdates()
}
class CheckListCell : UITableViewCell {
@IBOutlet weak var tickBtn: UIButton!
@IBOutlet weak var taskLbl: UILabel!
var cellTickedImage : UIImage?
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell = checkListTableView.dequeueReusableCellWithIdentifier("CheckListCell", forIndexPath: indexPath) as! CheckListCell
cell.taskLbl?.text = checkListData[indexPath.section][indexPath.row]
cell.tickBtn.setImage(cell.cellTickedImage, forState: UIControlState.Normal)
cell.tickBtn.setImage(cell.cellTickedImage, forState: UIControlState.Highlighted)
//cell.tickBtn.titleLabel!.text = ""
return cell
}
Try this out:
Step 1 : In didSelectRowAtIndexPath
update the model that drives cell image:
self.cellTickedImage = UIImage(named: "tick.png”)
Step 2 : In didSelectRowAtIndexPath
reload the cell to see the change:
self.tableView.beginUpdates()
self.tableView.reloadRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Automatic)
self.tableView.endUpdates()
Step 3 : In didDeselectRowAtIndexPath
update the model that drives cell image:
self.cellTickedImage = UIImage(named: "unTicked.png”)
Step 4 : In didDeselectRowAtIndexPath
reload the cell to see the change:
self.tableView.beginUpdates()
self.tableView.reloadRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Automatic)
self.tableView.endUpdates()
Step 5 : In cellForRowAtIndexPath
set the cell image correctly:
cell.tickBtn.setImage(self.cellTickedImage, forState: UIControlState.Normal)
cell.tickBtn.setImage(self.cellTickedImage, forState: UIControlState.Highlighted)
EDIT: Post discussion with OP on chat - Few assumptions from discussion
Considering this, here is the high level algorithm for the fix:
checkListDict
with key as cell text and value as image status flag. Initially set value is 0 for all cell text. Considering 1 as tick.png
and 0 as unTicked.png
.didSelectRowAtIndexPath
update the flag like this:->
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
//change tickBtn's image src to tick.png
let cell = tableView.cellForRowAtIndexPath(indexPath) as? CheckListCell
let selectedCellText = (cell!.taskLbl?.text)!
if checkListDict[selectedCellText] == 0 {
checkListDict[selectedCellText] = 1
}
else{
checkListDict[selectedCellText] = 0
}
self.checkListTableView.beginUpdates()
self.checkListTableView.reloadRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Automatic)
self.checkListTableView.endUpdates()
}
cellForRowAtIndexPath
like this:->
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell = checkListTableView.dequeueReusableCellWithIdentifier("CheckListCell", forIndexPath: indexPath) as! CheckListCell
let selectedCellText = checkListData[indexPath.section][indexPath.row]
cell.taskLbl?.text = selectedCellText
let cellImage = checkListDict[selectedCellText] == 0 ? UIImage(named: "unTicked.png") : UIImage(named:"tick.png")
cell.tickBtn.setImage(cellImage, forState: UIControlState.Normal)
cell.tickBtn.setImage(cellImage, forState: UIControlState.Highlighted)
return cell
}