Reputation: 1866
I have a custom tableView, entirely created in code. IE, the cells need to be in code too.
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "inventoryCell", for: indexPath)
let namelabel = UILabel()
namelabel.frame = CGRect(x: 145, y: 10 , width: 200, height: 30 )
namelabel.text = itemToShow.name
namelabel.font = UIFont.boldSystemFont(ofSize: 20)
namelabel.backgroundColor = .clear
cell.addSubview(namelabel)
let detailLabel = UILabel()
detailLabel.frame = CGRect(x: 145, y: 50 , width: 200, height: 50 )
detailLabel.text = itemToShow.detail
detailLabel.backgroundColor = .clear
cell.addSubview(detailLabel)
let inventoryImage = UIImageView()
inventoryImage.frame = CGRect(x: 10, y: 10, width: 130, height: 130)
inventoryImage.image = UIImage(named: "emptyInventorySlot")
cell.addSubview(inventoryImage)
return cell
}
It works great, and you can see it loads perfectly. The top image is the load, the bottom image is once I scroll to the bottom. You can see the text labels seem to all stack on top of each other.
Upvotes: 1
Views: 306
Reputation: 134
I would not recommend doing it this way. It's better to move the code that creates namelabel, detailLabel and inventoryImage to an inventoryCell class derived from UITableViewCell.
But you can make it work. Since table cells are reused and the reused cells already contain the created subviews, you need to either remove the subviews or treat cells with already created subviews differently.
And you should place your labels in the contentView of your UITableCellView.
To make your code work you can do this:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "inventoryCell", for: indexPath)
// remove any subviews from contentView from recycled cells
cell.contentView.subviews.forEach{ $0.removeFromSuperview() }
let namelabel = UILabel()
namelabel.frame = CGRect(x: 145, y: 10 , width: 200, height: 30 )
namelabel.text = itemToShow.name
namelabel.font = UIFont.boldSystemFont(ofSize: 20)
namelabel.backgroundColor = .clear
// add any label to contentView of the cell
cell.contentView.addSubview(namelabel)
let detailLabel = UILabel()
detailLabel.frame = CGRect(x: 145, y: 50 , width: 200, height: 50 )
detailLabel.text = itemToShow.detail
detailLabel.backgroundColor = .clear
// add any label to contentView of the cell
cell.contentView.addSubview(detailLabel)
let inventoryImage = UIImageView()
inventoryImage.frame = CGRect(x: 10, y: 10, width: 130, height: 130)
inventoryImage.image = UIImage(named: "emptyInventorySlot")
// add any label to contentView of the cell
cell.contentView.addSubview(inventoryImage)
return cell
}
Better would be:
Upvotes: 1