【问题标题】:How to fix 'Swift Protocols/Delegates setting UIImages - Fatal error: Unexpectedly found nil while implicitly unwrapping an Optional value'?如何修复“Swift Protocols/Delegates setting UIImages - Fatal error: Unexpectedly found nil while implicitly unwrapping an Optional value”?
【发布时间】:2019-07-04 05:19:03
【问题描述】:

我让用户在登录时选择背景图像。根据用户选择的图像选择,我想用用户选择的图像显示另一个视图控制器。我遵循 youtube 上的一些示例,但我收到“致命错误:在隐式展开可选值时意外发现 nil”并且图像未设置。

protocol SelectionImageDelegate {

    func setBackgroundImage(selectedImage: UIImage)
}


class SelectBackgroundViewController: UIViewController {

    // MARK: IBOutlets
    @IBOutlet weak var snowBackgroundImage: UIImageView!
    @IBOutlet weak var desertBackgroundImage: UIImageView!
    @IBOutlet weak var pathwayBackgroundImage: UIImageView!
    @IBOutlet weak var beachBackgroundImage: UIImageView!

    // MARK: Properties
    var imageSelectionDelegate: SelectionImageDelegate!


    // MARK: Life Cycle
    override func viewDidLoad() {
        super.viewDidLoad()
        self.imageSelectionDelegate = FootprintViewController()
        setButtonCorners()
    }

    override func viewWillAppear(_ animated: Bool) {

        snowBackgroundImage.center.x  -= view.bounds.width
        desertBackgroundImage.center.x -= view.bounds.width
        pathwayBackgroundImage.center.x -= view.bounds.width
        beachBackgroundImage.center.x -= view.bounds.width
    }


    @IBAction func didTappedSnowBackground(_ sender: Any) {
        print("tapped snow")
        imageSelectionDelegate.setBackgroundImage(selectedImage: UIImage(named: "Snow_Background")!)
        print("set image")
        let vc = (self.storyboard?.instantiateViewController(withIdentifier: "FootprintVC"))!
        self.presentViewController(vc)
    }


    @IBAction func didTappedDesertBackground(_ sender: Any) {
        imageSelectionDelegate.setBackgroundImage(selectedImage: UIImage(named: "Desert_Background")!)
        let vc = (self.storyboard?.instantiateViewController(withIdentifier: "FootprintVC"))!
        self.presentViewController(vc)
    }


    @IBAction func didTappedPathwayBackground(_ sender: Any) {
        imageSelectionDelegate.setBackgroundImage(selectedImage: UIImage(named: "Pathway_Background")!)
        let vc = (self.storyboard?.instantiateViewController(withIdentifier: "FootprintVC"))!
        self.presentViewController(vc)
    }


    @IBAction func didTappedBeachBackground(_ sender: Any) {
        imageSelectionDelegate.setBackgroundImage(selectedImage: UIImage(named: "Beach_Background")!)
        let vc = (self.storyboard?.instantiateViewController(withIdentifier: "FootprintVC"))!
        self.presentViewController(vc)
    }

}


class FootprintViewController: UIViewController {


    // MARK: IBOutlets
    @IBOutlet weak var backgroundImageView: UIImageView!
    @IBOutlet weak var emptyFootprintImageView: UIImageView!

    // MARK: Life Cycles
    override func viewDidLoad() {
        super.viewDidLoad()
    }

}

extension FootprintViewController: SelectionImageDelegate {

    func setBackgroundImage(selectedImage: UIImage) {
        backgroundImageView.image = selectedImage
    }
}

class FootprintViewController: UIViewController {


    // MARK: IBOutlets
    @IBOutlet weak var backgroundImageView: UIImageView!
    @IBOutlet weak var emptyFootprintImageView: UIImageView!

    // MARK: Life Cycles
    override func viewDidLoad() {
        super.viewDidLoad()
    }

}

extension FootprintViewController: SelectionImageDelegate {

    func setBackgroundImage(selectedImage: UIImage) {
        backgroundImageView.image = selectedImage
    }
}

【问题讨论】:

  • 您究竟从哪里得到异常?
  • 异常出现在imageSelectionDelegate.setBackgroundImage(selectedImage: UIImage(named: "Snow_Background")!, color: .red)

标签: swift uiimageview delegates uiimage protocols


【解决方案1】:

请尝试像这样在 SelectBackgroundViewController 中设置可选的 imageSelectionDelegate;

var imageSelectionDelegate: SelectionImageDelegate?

【讨论】:

  • 错误通过将其设置为可选但未设置,因为它是零。 :(
【解决方案2】:

“隐式解包”表示您正在尝试访问“隐式解包可选”值,该值不包含值,而是nil

在您的情况下,您正在处理两个选项:

  • 代理 imageSelectionDelegate 可能未设置。
  • UIImage(named: "Snow_Background") 可能会返回 nil

访问委托 - 如果nil 将导致Unexpectedly found nil while implicitly unwrapping an Optional value 错误,而访问图像 - 如果nil - 将导致Unexpectedly found nil while unwrapping an Optional value

因此,由于您观察到第一个错误,因此委托为 nil,这似乎很奇怪,因为您将其设置为 viewDidLoad

要进行更多调查,您可以向操作处理程序添加更多跟踪信息,以检查发生了什么:

@IBAction func didTappedSnowBackground(_ sender: Any) {
    print("tapped snow")

    guard imageSelectionDelegate != nil else {
        print ("delegate is not set")
        return
    }

    guard let bgImage = UIImage(named: "Snow_Background") else {
        print ("Snow_Background image does not exist")
        return
    }

    imageSelectionDelegate.setBackgroundImage(selectedImage: bgImage)
    print("set image")
    let vc = (self.storyboard?.instantiateViewController(withIdentifier: "FootprintVC"))!
    self.presentViewController(vc)
}

然后检查输出。

【讨论】:

  • 我收到“未设置代表”。
  • 请在 print 语句处设置断点(“delegate not set”)并显示调用堆栈。还要在viewDidLoad 处设置断点。这应该在打印断点之前到达
  • 如果我从 imageSelectionDelegate 中删除“弱”,则所选图像将被传递给 FootprintVC。但是,我仍然收到零错误。请看下文。非常感谢您的帮助。 extension FootprintViewController: SelectionImageDelegate { func setBackgroundImage(selectedImage: UIImage, color: UIColor) { backgroundImageView.image = selectedImage // 线程 1:致命错误:意外发现 nil,同时隐式展开可选值在这里找到 view.backgroundColor = color } }
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-06-15
  • 1970-01-01
  • 2020-09-05
相关资源
最近更新 更多