-2

I have 4 rows which shows and hide some data below the selected row. Its works fine Most of the time. But when I click second/third/fourth rows multiple times(like 13-14) times and then click on first row then sometime it crashes not always but it crashes most of the time after multiple clicks. I am changing row height as well. Crash only happen when I select first row(case a), after selecting other rows multiple times. Below is my code -

I tried multiple things like calling it between beginUpdate and endUpdate, check is indexPath exist before reloading

 func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return dataSource.count
    }



 func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

        let cell = tableView.dequeueReusableCell(withIdentifier: ”cell”, for: indexPath) as! CustomTableViewCell

        let model = dataSource[indexPath.row]
        cell.model = model

        switch model.type {
        case .a:
            cell.aList = savedCardList
            cell.addACallback = {[weak self] (sender) in
                self?.moveToAVC()
            }
            cell.addACallback= {[weak self] (a) in
                self?.selectedA = a
                self?.updateButton()
            }

        case .b:
            cell.bList = bList
            cell.bSelectedCallback = {[weak self] (bInfo) in
                self?.selectedB= bInfo
                self?.updateButton()
            }

        case .c:
            cell.cList = cList
            if let cInfo = selectedC {
                cell.selectOtherCButton.setTitle(cInfo.name, for: .normal)
            }
            cell.selectOtherCCallback = {[weak self] (sender) in
                self?.showSelectCVC()
            }
            cell.CSelectedCallback = {[weak self] (cInfo) in
                self?.selectedC = cInfo
                self?.updateButton()
            }

        case .d:
            cell.dTextField.text = dString
            cell.dChangedCallBack = {[weak self] (textField) in
                if let dStr = textField.text {
                    self?.dString = dStr
                }
                self?.updateButton()
            }

        default:
            break
        }
        return cell
    }


 func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
        let model = dataSource[indexPath.row]
        guard model.isSelected == true else {
            return 90
        }
        switch model.type {
        case .a:
            if aList.count > 0 {
                return 350
            }
            return 140

        case .b:
            return 200

        case .c:
            return 270

        case .d:
            return 130

        default:
            return 90
        }
    }


 func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
        let model = dataSource[indexPath.row]
        selectedType = model.type
        updateButtonState(false)
        updateButton()

        if let selectedIndexPath = selectedIndexPath, selectedIndexPath != indexPath {
            self.updatemodelSelectedState(false, at: selectedIndexPath)
            self.updatemodelSelectedState(true, at: indexPath)
            if let _ = tableView.cellForRow(at: indexPath), let _ = tableView.cellForRow(at: selectedIndexPath) {
                self.reloadTableViewRows([selectedIndexPath, indexPath])
                tableView.scrollToRow(at: indexPath, at: .top, animated: true)
            }
        }
        else if !model.isSelected {
            self.updatemodelSelectedState(true, at: indexPath)
                if let _ = tableView.cellForRow(at: indexPath) {
                    self.reloadTableViewRows([indexPath])
                }
        }
        selectedIndexPath = indexPath
    }

 private func reloadTableViewRows(_ indexPaths: [IndexPath]) {
        DispatchQueue.main.async {
            self.myTableView.beginUpdates()
            self.myTableView.reloadRows(at: indexPaths, with: .automatic)
            self.myTableView.endUpdates()
        }
    }

Xcode console log(I am only getting this one liner) -

libc++abi.dylib: terminating with uncaught exception of type NSException

It crashes at self.myTableView.endUpdates() this line. If I remove begin and end updates then it crashes at self.myTableView.reloadRows(at: indexPaths, with: .automatic). Also for one of the row I show a popup on a button click and after then if I select my first row, it crashes!

Also I have collection view inside table view rows which I am hiding and showing. Even though its flow is set to horizontal, after multiple clicks once in a while I notice that collection view rows comes in vertical flow and then in next click it gets back to horizontal flow again. Not sure why this is happening but could this be issue?

Please help. I am trying to resolve this issue from last 2-3 hours :(

  • 1
    Show the crash log that is printed in the console. – PGDev Aug 09 '19 at 06:23
  • try the following. `tableView.reloadRows(at: [indexPaths], with: .automatic)` – chirag90 Aug 09 '19 at 06:27
  • @PGDev I have updated the crash log in the question – Richa Srivastava Aug 09 '19 at 06:33
  • @RichaSrivastava please check the console once again, there might be more than one line in the error log – Sahil Manchanda Aug 09 '19 at 06:43
  • Can you explain what is the problem statement that you're trying to solve. There might be another way to do that. – PGDev Aug 09 '19 at 06:45
  • @RichaSrivastava try removing scrollToRowAt after reloadRows – Shivam Gaur Aug 09 '19 at 06:48
  • @SahilManchanda Even I don't understand why it only gives one line of error. I have checked my console properly there is only one line of error. My exception breakpoint stops at reloadRow and then crashes. – Richa Srivastava Aug 09 '19 at 06:52
  • @PGDev I have 4 rows which shows and hide some data below the selected row. Its works fine Most of the time. But when I click second/third/fourth rows multiple times(like 13-14) times and then click on first row then sometime it crashes not always but it crashes most of the time after multiple clicks. – Richa Srivastava Aug 09 '19 at 06:56
  • @ShivamGaur I have tried that but then also it crashes. – Richa Srivastava Aug 09 '19 at 06:57
  • @RichaSrivastava You need to update your question to match the comment you have said regarding having 4 rows and how you are getting to crash. – chirag90 Aug 09 '19 at 06:59
  • @RichaSrivastava you might have done this but to be sure, do select the exception breakpoint ,(Steps -> Debug - BreakPoints - Create Exception BreakPoint) , it might give you more insight to the crash. – Shivam Gaur Aug 09 '19 at 07:14
  • @ShivamGaur Yes! I have done that. It stops at reloadRows line and then crashes with only one line of error – Richa Srivastava Aug 09 '19 at 07:18

1 Answers1

-1

Try This one i hope it will be work for you:

   UIView.setAnimationsEnabled(false)
   tableView.beginUpdates()
   tableView.reloadRows(at: [indexPath!], with: .none)
   tableView.endUpdates()
   UIView.setAnimationsEnabled(true)
nimesh surani
  • 177
  • 1
  • 13
  • Its still crashing but this time it took longer to reproduce the crash. after selecting between all the row for around 20 times it crashed – Richa Srivastava Aug 09 '19 at 07:14
  • I have collection view inside table view rows which I am hiding and showing. Even though its flow is set to horizontal, after multiple clicks once in a while I notice that collection view rows comes in vertical flow and then in next click it gets back to horizontal flow again. Not sure why this is happening but could this be issue? – Richa Srivastava Aug 09 '19 at 07:23