EXC_BAD_INSTRUCTION When Passing UICollectionView

2020-01-29 03:47发布

问题:

I have a UICollectionView that I am populating based on Firebase data. I have created custom cells that populate the UICollectionView:

import UIKit
import Material

class PollCell: CollectionViewCell {

var key: String? {
get {
return self.key
}
}
@IBOutlet weak var imageView: UIImageView!
@IBOutlet weak var pollQuestion: UILabel!

public required init?(coder aDecoder: NSCoder) {
    super.init(coder: aDecoder)

    }
}

I am attempting to access the pollQuestion variable of the clicked cell in the UICollectionView and pass it to another ViewController:

     override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
    if segue.identifier == "toPoll" {
    let pollViewController = segue.destination as! PollController
        if let cell = sender as? PollCell {
            pollViewController.passLabel.text = cell.pollQuestion.text
        }
    }
}

PollController:

import UIKit

class PollController: UIViewController {

@IBOutlet weak var passLabel: UILabel!

override func viewDidLoad() {
    super.viewDidLoad()

    // Do any additional setup after loading the view.
}

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
    // Dispose of any resources that can be recreated.
  }

}

UPDATE: I have revised the code and am now receiving the error

The app is crashing at runtime, and I am trying to resolve:

回答1:

The crash occurs because the outlet passLabel is not connected yet when prepare(for segue is called.

You have to declare a (temporary) variable in PollController and set the label in viewDidLoad

class PollController: UIViewController {

    @IBOutlet weak var passLabel: UILabel!

    var pass = ""

    override func viewDidLoad() {
        super.viewDidLoad()
        passLabel.text = pass
    }

...

In prepare(for segue set the variable rather than the text property of the label:

let pollViewController = segue.destination as! PollController
    if let cell = sender as? PollCell {
        pollViewController.pass = cell.pollQuestion.text
    }
}

Note: It's not recommended to gather information from the view (cell). Get the index path and read the information from the model (data source array).



回答2:

Instead of calling cellForItem, which gives you a new cell, you should use the cell that is passed to you as sender.

if let cell = sender as? PollCell {
    pollViewController.passLabel.text = cell.pollQuestion.text
}