Leo Guo
Leo Guo

Reputation: 195

Swift: How to set dynamic cell height in TableViewController which contains more than one cell

I have a TableViewController, which contains three different customized cell. For the first cell, I want to contain a horizontal scrolled CollectionView, the second cell contains a CollectionView as well, and the third one contains a vertical CollectionView. I write my code like this:

override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
    return 3
}

override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return 1
}

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {


    if indexPath.section == 0 {

        let cell = tableView.dequeueReusableCellWithIdentifier("TableViewCell1") as! HomePageTableViewCell1


        return cell
    }

     else if indexPath.section == 1 {

        let cell = tableView.dequeueReusableCellWithIdentifier("TableViewCell2") as! HomePageTableViewCell2


        return cell
    }
     else {

        let cell = tableView.dequeueReusableCellWithIdentifier("TableViewCell3") as! HomePageTableViewCell3


        return cell
    }

}

it works like I want, but I am not sure is this the best way to achieve what I want? cause I am new to Swift, maybe there are some better way to do this?

Secondly, for these three cell, I want to retain dynamic height based one the content. for example, the first cell contains a ImageView which height is 260, the second cell contains a ImageView with 140 of the height. the third cell contains a CollectionView which will return 4 rows, and in each row, there is a ImageView with height 96. what I have done is :

 override func tableView(tableView: UITableView, heightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat {
    if indexPath.section == 0 {
         return 260
    }
    else if indexPath.section == 1 {
        return 140
    }
    else {
        return 500

    }
}

but this means I have to hard code these height in the case I know the height of the content. But what if I don't know the height, like if the third cell will return 5 row, which means 500 is not enough, then what should I do to give the cell a dynamic height.

Upvotes: 2

Views: 2139

Answers (2)

Er. Khatri
Er. Khatri

Reputation: 1414

you can always have the dynamic height for your tableView on the base of your content, no need to return the static height for just setup the constraints in your cell properly and always use preferred priority for content-hugging content-compressionResistance.

in -viewDidLoad just set

self.tableView.rowHeight = UITableViewAutomaticDimension
self.tableView.estimatedRowHeight = 60; // or whatever is suitable for you 

you can also have reference from the Ray Wenderlich's tutorial Self-sizing Table View Cells

Upvotes: 0

Rutger Huijsmans
Rutger Huijsmans

Reputation: 2408

This is possible:

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {

    if indexPath.section == 0 {

        let cell = tableView.dequeueReusableCellWithIdentifier("TableViewCell1") as! HomePageTableViewCell1

        let string1 = "blablabla"
        let charCountString1 = string1.character.characters.count

        tableView.rowHeight = CGFloat(charCountString1)
        return cell
    }

     else if indexPath.section == 1 {

        let cell = tableView.dequeueReusableCellWithIdentifier("TableViewCell2") as! HomePageTableViewCell2

        let imageHeight = imageView.frame.height

        tableView.rowHeight = CGFloat(imageHeight)
        return cell
    }
     else {

        let cell = tableView.dequeueReusableCellWithIdentifier("TableViewCell3") as! HomePageTableViewCell3

        let string3 = "ldsakjfalksdjflk"
        let charCountString3 = string3.character.characters.count

        tableView.rowHeight = CGFloat(charCountString3)
        return cell
    }

}

Upvotes: 2

Related Questions