youssef SULTAN
youssef SULTAN

Reputation: 47

tableview does not update

i'm trying to make a ordering food app for restaurants, when i add items to the cart for the first time table view loads the singleton array i've made. but when i go back to the menu and choose another item the array is updated but the table view of the cart doesn't, i'm using tabbarcontroller. tried to use tableview.reloadData() in different places still new data added to the array doesn't appear

class CartVC: UIViewController, UITableViewDelegate, UITableViewDataSource{

    @IBOutlet weak var priceLbl: UILabel!
    @IBOutlet weak var tableView: UITableView!


    override func viewDidLoad() {
        super.viewDidLoad()
        tableView.reloadData()
        // Do any additional setup after loading the view.
        tableView.delegate = self
        tableView.dataSource = self
        tableView.reloadData()

        updateView()
    }
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return DataService.instance.cartItems.count
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        if let cell = tableView.dequeueReusableCell(withIdentifier: "cartCell") as? CartCell{
            let item = DataService.instance.cartItems[indexPath.row]
            cell.configCell(cart: item)
            return cell
        } else {
            return UITableViewCell()
        }
    }
    func numberOfSections(in tableView: UITableView) -> Int {
        return 1
    }

    func tableView(_ tableView: UITableView, canEditRowAt indexPath: IndexPath) -> Bool {
        return true
    }

    func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCell.EditingStyle, forRowAt indexPath: IndexPath) {
        if editingStyle == .delete {
            DataService.instance.cartItems.remove(at: indexPath.row)

            tableView.beginUpdates()
            tableView.deleteRows(at: [indexPath], with: .automatic)
            updateView()
            tableView.endUpdates()
        }
    }

    func updateView(){
        var sum = 0
        for item in DataService.instance.cartItems{
            sum += item.itemPrice * item.quantity
            print(item.itemPrice)
        }
        priceLbl.text = "$\(sum)"
    }

    @IBAction func orderPressed(_ sender: Any) {
        // upload order to firebase, clear cart and move to orderVC
    }


}

Upvotes: 3

Views: 1966

Answers (2)

Chirag Shah
Chirag Shah

Reputation: 3016

In tabbar every time viewDidLoad not called so you need to reload the data in viewWillAppear or viewDidAppear. Here is the reference.

override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view.
        tableView.delegate = self
        tableView.dataSource = self

        updateView()
    }
override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)

        tableView.reloadData()

    }

Upvotes: 1

jtouzy
jtouzy

Reputation: 1639

UITableViewDelegate is not reactive. You have to call reloadData() when you want to update the tableView content (when your DataService.instance value is updated).

In a MVP world, your "add" action will trigger an event to the presenter. And the presenter sends back to the view an action to update the tableView, after updating your DataService.

Maybe you should look at RxSwift/ReactiveCocoa, which provides APIs to automatically bind your DataService.instance array to the cells rendered in the UITableView.

Upvotes: 0

Related Questions