Sander Frenken
Sander Frenken

Reputation: 43

subclassed uitableviewcell subview color

I got a strange issue (in my opinion;)) considering a subclass of uitableview cell. The code for my subclass is:

class SubLevelTableCell: UITableViewCell {
    var subLevelLabel:UILabel
    var subLevelBack:UIView
    var subLevelScore:UIImageView

    override init(style: UITableViewCellStyle, reuseIdentifier: String!)
    {
        self.subLevelBack = UIView()
        self.subLevelLabel = UILabel()
        self.subLevelScore = UIImageView()

        super.init(style: UITableViewCellStyle.Value1, reuseIdentifier: reuseIdentifier)

        self.subLevelLabel.textColor = whiteColor

        self.subLevelLabel.font = UIFont(name: subLevelLabel.font.fontName, size: 20)

        self.addSubview(self.subLevelBack)
        self.subLevelBack.addSubview(self.subLevelLabel)
        self.subLevelBack.addSubview(self.subLevelScore)
    }

    required init(coder aDecoder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    override func layoutSubviews() {
        self.subLevelBack.frame = CGRectMake(10, 10, self.bounds.size.width-20, self.bounds.size.height-20)
        self.subLevelLabel.frame = CGRectMake(5, 0, subLevelBack.frame.size.width/2-10, subLevelBack.frame.size.height)
        self.subLevelScore.frame = CGRectMake(subLevelBack.frame.size.width-120, 15, 100, subLevelBack.frame.size.height-30)
    }

}

Now I create these cells in my view controller as follows:

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        var cell:SubLevelTableCell? = SubLevelTable?.dequeueReusableCellWithIdentifier("Cell") as? SubLevelTableCell
        if (cell == nil)
        {
            cell = SubLevelTableCell(style: UITableViewCellStyle.Subtitle,
                reuseIdentifier: "Cell")
            cell!.backgroundColor = grayColor
        }
        if (indexPath.row == 0){nextLevelCanBePlayed = true}
        if(nextLevelCanBePlayed){
            canBePlayedArray[indexPath.row] = true
            cell!.subLevelBack.backgroundColor = blueColor
        }else{
            canBePlayedArray[indexPath.row] = false
            cell!.subLevelBack.backgroundColor = redColor
        }
        cell!.subLevelLabel.text = "Stage \(indexPath.row+1)"
        let data = db.query("SELECT * FROM LEVEL_DETAIL WHERE MAIN_LEVEL =\(MainLevelNr!) AND SUB_LEVEL = \(indexPath.row+1)")[0]
        var levelScore: Int = 0
        if let columnValue = data["COMPLETED"]{
            levelScore = columnValue.asInt()
            if (levelScore > 0){nextLevelCanBePlayed = true}else{nextLevelCanBePlayed = false}
            cell!.subLevelScore.image = UIImage(named: "\(levelScore)Stars.png")
        }
        return cell!
    }

My problem is that when the view loads for the first time, the subLevelBack.backgroundColor is set properly, ie. the subview's color is correct.

Though when I start scrolling, it becomes a bit of a mess with different cells having incorrect background colors, and I don't know how to solve this issue. I don't have this same issue with the image displayed in the UIImageView btw.

I hope someone will point me in the right direction. Kind regards, Sander

Upvotes: 3

Views: 119

Answers (1)

hlfcoding
hlfcoding

Reputation: 2542

if (indexPath.row == 0){nextLevelCanBePlayed = true}
if(nextLevelCanBePlayed){ ...

The above code seems incorrect. You're trying to keep track of how many levels have been played, but each time the first cell gets re-rendered, nextLevelCanBePlayed will be reset. Perhaps try just if(nextLevelCanBePlayed || indexPath.row == 0){.

The other thing is you're making the assumption that the table view will re-render its cells near the viewport in order, but isn't documented anywhere and very likely isn't reliably true, and is especially likely if you're scrolling in the reverse direction. So when the table view re-builds cell 4 (nextLevelCanBePlayed calculates and sets to false) and maybe goes back to cell 3 next, and even if 3 is actually playable, nextLevelCanBePlayed will be false and 3 will show up incorrect. It then starts making sense that your colors start erratically changing as you scroll up and down.

My suggestion is to properly use your UITableViewDataSource methods and use those to work with the db and return proper data objects that represent the state and data of your cells.

Upvotes: 1

Related Questions