0

I have Implemented Tableview in swift, but I want to Make an Expandable TableView, please give me an idea.

This is the code for Tableview,

//MARK: - TableView Delegate and Datasource
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return MenuNameArray.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "MenuTableViewCell", for: indexPath) as! MenuTableViewCell
    cell.menuNameLabel.text = NameArray[indexPath.row]
    return cell
}
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {

}
Heshan Sandeepa
  • 3,388
  • 2
  • 35
  • 45
B.Saravana Kumar
  • 1,208
  • 6
  • 20
  • 48
  • 1
    You’ll have to explain more about what you want? What do you mean by expandable? What interaction will it have? Etc... – Fogmeister Jan 25 '18 at 12:42
  • That means Expandable Table view cell. – B.Saravana Kumar Jan 25 '18 at 12:54
  • https://stackoverflow.com/q/47963568/2912282 – Milan Nosáľ Jan 25 '18 at 13:05
  • 1
    Possible duplicate of [Programmatically creating an expanding UItableViewCell](https://stackoverflow.com/questions/47963568/programmatically-creating-an-expanding-uitableviewcell) – Milan Nosáľ Jan 25 '18 at 13:05
  • Yes. But what do you mean by that? You already said “expandable table view cell” I asked you to explain that more. Not to repeat the same words. Do you want one cell to grow? Do you want more cells to be added/removed? Explain what you want. Pretend I have to write the feature for you. Give me an idea of what you want to happen. – Fogmeister Jan 25 '18 at 13:31

3 Answers3

1

Here You Go , Try This Out : -

struct ExpandableNames {
    var isExpanded : Bool
    var names : [String]
}

struct Contact {
    let names : String
}

in your Class - >

var twoDArray = [

    ExpandableNames(isExpanded : true,names:["Krishna","Rishabh","Aditya","Chandan","Nipun","Navdeesh","Steve"].map
    {
            Contact(names: $0)
    }),
    ExpandableNames(isExpanded : true,names:["Carl","Michal","Tommy","Jennny","Vikram","Swati"].map
    {
            Contact(names: $0)
    }),
    ExpandableNames(isExpanded : true,names:["David","dude","dfff","dcc","daa","dee","dsss"].map
    {
        Contact(names: $0)

    }),
    ExpandableNames(isExpanded : true,names:[Contact(names: "Pattrick", hasFav: false)])

                ]

let cellId = "cellID"
let identifier = "attachmentCellID"

func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat
{
    return 50
}
func numberOfSections(in tableView: UITableView) -> Int
{

    return twoDArray.count

}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int
{
    if !twoDArray[section].isExpanded
    {
        return 0
    }
    return twoDArray[section].names.count
}
func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView?
{
    let btn = UIButton(type: .system)
    if(section == 0)
    {
        btn.setTitle("Tap To View Classes", for: .normal)
    }
    else if(section == 1)
    {
        btn.setTitle("Tap To View Admins", for: .normal)
    }

    btn.setTitleColor(.black, for: .normal)
    btn.titleLabel?.font = UIFont.boldSystemFont(ofSize: 14)
    btn.addTarget(self, action: #selector(handleExpandClose), for: .touchUpInside)
    btn.backgroundColor = AppColors.greyBorderColor
    btn.tag = section
    return btn
}
@objc func handleExpandClose(button : UIButton)
{
    let section = button.tag

    var indexPaths = [IndexPath]()
    for row in twoDArray[section].names.indices
    {
        let indexPath = IndexPath(row: row, section: section)
        indexPaths.append(indexPath)
    }

    let isExpanded = twoDArray[section].isExpanded
    twoDArray[section].isExpanded = !isExpanded


    button.setTitle(isExpanded ? "Tap To View Classes" : "Classes", for: .normal)



    if isExpanded
    {
        tableView.deleteRows(at: indexPaths, with: .fade)
    }
    else
    {
        tableView.insertRows(at: indexPaths, with: .fade)

    }


}

And Rest in cellForRowAt -

 let contact = twoDArray[indexPath.section].names[indexPath.row]
    cell.textLabel?.text = contact.names
Shawn
  • 78
  • 8
Rishabh Shukla
  • 461
  • 6
  • 19
0

First you will need a model defining if the cell is open, for example, an array of indexPaths:

var openPaths = [IndexPath]()

now when select the cell you toggle wether it is open or not and reload the cell

        if let index = openPaths.index(indexPath) {
            openPaths.remove(atIndex: index)
        } else {
             openPaths.append(indexPath)
        }

        tableView.beginUpdates()
        tableView.reloadRows(at: [indexPath], with: .automatic)
        tableView.endUpdates()

Now in your cell setup, use a stackview, and in the cell config, you hide the expandable part based on if the cells indexPath is in openPaths

Sean Lintern
  • 3,103
  • 22
  • 28
0

Use heightForRowAt delegate method to change height of cell:- Add a boolean property to your object say isExpanded, change the value in didSelectRowAt delegate by

func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    YourModel[indexPath.row].isExpanded = !YourModel[indexPath.row].isExpanded
    tableView.reloadRows(at: [indexPath], with: Animation)
}

func tableView(_ tableView: UITableView, estimatedHeightForRowAt indexPath: IndexPath) -> CGFloat {
    return 50
}

func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
     if YourModel[indexPath.row].isExpanded {
         return 200
     } else {
         return 50
     }
}
Kuldeep
  • 4,466
  • 8
  • 32
  • 59
Anuraj
  • 1,242
  • 10
  • 25
  • you need to reload the affected row only instead of reloading the whole table... tableView.reloadRows(at: [indexPath], with: .automatic) – Musa almatri Jan 25 '18 at 13:20