SagittariusA
SagittariusA

Reputation: 5427

Swift: how to set UITableViewCell in cellForRowAtIndexPath method

In my UITableViewController I have many custom cells whose height depends on the length of the UITextView inside them. This means I cannot return a precise size from heightForRowAtIndexPath() method because I still don't know it at that point. Moreover, as I cannot create a @IBOutlet weak var to the constraint ruling the UITextView, here's the code I have tried:

let cell =  tableView.dequeueReusableCellWithIdentifier("BigTextCell", forIndexPath: indexPath) as! BigTextCell

cell.backgroundColor = UIColor(patternImage: UIImage(named: "icons/background.png")!)

cell.paragraph.layer.borderColor = UIColor(red: 0/255, green: 0/255, blue: 0/255, alpha: 1).CGColor
cell.paragraph.layer.borderWidth = 0.5
cell.paragraph.editable = false
cell.title.enabled = false


switch (indexPath.row) {
  case 1:
        cell.title.text = "Chi è:"
        cell.icon.image = UIImage(named: "icons/field_fish.png")
        cell.paragraph.text = self.fieldsCollection["life_method"] as! String
        cell.paragraph.backgroundColor = UIColor(patternImage: UIImage(named: "icons/quadretti.png")!)

        for constraint in cell.icon.constraints {
          if (constraint.identifier == "icon_width") {
            constraint.constant = 64.0
            break
          }
        }

        for constraint in cell.paragraph.constraints {
          if (constraint.identifier == "longTextConstraint") {
            constraint.constant = cell.paragraph.sizeThatFits(CGSize(width: cell.paragraph.frame.width, height: CGFloat.max)).height
            break
          }
        }
...

Thus, the UITextView correctly sizes according to the length of the text but often the height of the cell is too much. How can I fix this? Thank you

UPDATE As some of you suggested, if I try this in heightForRowAtIndexPath

if (indexPath.row == 1) {
        //return 235.0
        let cell =  tableView.dequeueReusableCellWithIdentifier("BigTextCell", forIndexPath: indexPath) as! BigTextCell
        cell.paragraph.text = self.fieldsCollection["life_method"] as! String

        for constraint in cell.paragraph.constraints {
            if (constraint.identifier == "longTextConstraint") {
                constraint.constant = cell.paragraph.sizeThatFits(CGSize(width: cell.paragraph.frame.width, height: CGFloat.max)).height
                return constraint.constant+30.0
                break
            }
      }
}

the simulator blocks.

Upvotes: 0

Views: 730

Answers (3)

Santosh
Santosh

Reputation: 2914

Try this in your viewDidLoad method:

    tableView.rowHeight = UITableViewAutomaticDimension
    tableView.estimatedRowHeight = 100.0 //Change this to any value

Upvotes: 1

A-Live
A-Live

Reputation: 8944

You can (and should) return the exact height at - tableView:heightForRowAtIndexPath: and - tableView:estimatedHeightForRowAtIndexPath: (not necessarily the exact height here, but the closest the better, if the values are not precise enough you might get visual glitches and issues with autolayout if you are using it). The only thing missing for the calculation is a cell instance, you can either get it from the table view by calling the corresponding method cellForRowAtIndexPath or by using a static cell instance that you never display but use for calculation. The former is fast and easy to use, the latter has its own specific use cases, e.g. if you for some reason want to calculate the height that a cell would have without having an actual table view.

Note that even though UITableView and UITableViewDataSource have methods with similar signatures, - cellForRowAtIndexPath and - tableView:cellForRowAtIndexPath: respectively, they function differently and the method of table view can return nil, refer to the documentation for the details.

Upvotes: 0

Sunny
Sunny

Reputation: 137

You could set tableView.rowHeight = UITableViewAutomaticDimension or calculate cell height for appropriate text in every heightForRowAtIndexPath() method call.

Upvotes: 1

Related Questions