0
votes

import UIKit

//MARK: - Model struct MobileModel { var brand: String? var isExpanded = false var model: [String]? }

class ViewController: UIViewController {

@IBOutlet weak var productInfoTableView: UITableView!
private var mobileDataArray = [MobileModel]()
private var isSelected = false

//MARK: - Life Cycle
override func viewDidLoad() {
    super.viewDidLoad()
    //MARK: - Data
    mobileDataArray = [MobileModel(brand: "Nokia", model: ["Nokia 1","Nokia 6.1","Nokia 10","Nokia 8.5"]),
    MobileModel(brand: "Mi", model: ["Redmi Note 4","Redmi Note 5","Redmi Note 5 Pro","Redmi Note 6","Redmi 5","Redmi Note 10"]),
    MobileModel(brand: "Samsung", model: ["Samsung Galaxy S8","Samsung M20","Samsung A50","Samsung Champ"]),
    MobileModel(brand: "Apple", model: ["iPhone 6s","iPhone 8","iPhone 10","iPhone 10 Pro","iPhone 7"])]
}

}

//MARK: - Table View Delegates extension ViewController: UITableViewDataSource, UITableViewDelegate {

//MARK: - No of Sections
func numberOfSections(in tableView: UITableView) -> Int {
    return mobileDataArray.count
}

//MARK: - No of cells
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    if self.mobileDataArray[section].isExpanded {
        return mobileDataArray[section].model?.count ?? 0
    } else {
        return 0
    }
}

//MARK: - Cell Items
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
        cell.textLabel?.text = mobileDataArray[indexPath.section].model?[indexPath.row]
        return cell
}

//MARK: - Section Header
func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let view = UIView(frame: CGRect(x: 0, y: 0, width: tableView.frame.width, height: 40))
    view.backgroundColor = .cyan
    let btn = UIButton(type: .system)
    btn.setTitle(mobileDataArray[section].brand, for: .normal)
    btn.titleColor(for: .normal)
    btn.tag = section
    btn.frame = view.bounds
    btn.addTarget(self, action: #selector(selectHeader(sender:)), for: .touchUpInside)
    //let lbl = UILabel(frame: CGRect(x: 15, y: 0, width: view.frame.width - 15, height: 40))
    //lbl.text = mobileData[section].brand
    view.addSubview(btn)
    return view
}

@objc func selectHeader(sender: UIButton) {
    if isSelected {
        self.mobileDataArray[sender.tag].isExpanded = !self.mobileDataArray[sender.tag].isExpanded
        self.productInfoTableView.reloadSections([sender.tag], with: .fade)
    } else {
        self.mobileDataArray[sender.tag].isExpanded = true
    }
}

}

1
Why don't you first collapse all sections and then expand the newly selected ? - claude31
Yes that's fine but my question is that when one section is expanded then no other sections should be able to expand and if any section is expanded already then it should be collapsed. So how to do this can you provide me with the logic behind this ? - Anoop Kumar

1 Answers

1
votes

Edited:

implement this and see how its work

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
if section == self.selectedIndex {
    return mobileDataArray[section].model?.count ?? 0
} else {
    return 0
}
}

explaination:

since i cant debug your code, maybe there is some isExpanded variable at index X doesn't changed.

by doing adjustment condition as above , at least only 1 index section is same.

if you have concern about the animation if you already use tableView.reloadData()

just use this instead:

@objc func selectHeader(sender: UIButton) {
if isSelected {
    self.mobileDataArray[sender.tag].isExpanded = !self.mobileDataArray[sender.tag].isExpanded

    UIView.animate(withDuration: 0.5) {
    tableView.beginUpdates()
    tableView.reloadData()
        self.view.layoutIfNeeded()
    tableView.endUpdates()

    }
} else {
    self.mobileDataArray[sender.tag].isExpanded = true
}

}

note : i'm not using compiler so there will be grammatical error