Search code examples
swiftdelegatesprotocolsxcode11unwrap

Error while working with delegate in swift


I am working in XCode 11 and I am trying to use a delegate in my code. However, it gives me an error: Unexpectedly found nil while implicitly unwrapping an Optional value

I've worked with protocols and delegates before and I have never encountered this problem. Can someone please help me to figure out what might be the issue? Thanks in advance.

Here is my code:

class RedScreenVC: UIViewController {

    var delegate: NavDelegate!

    var redView = UIView(frame: CGRect(x: 0, y: 0, width: UIScreen.main.bounds.size.width, height: UIScreen.main.bounds.size.height))

    var navigateButton: UIButton = {
        let button = UIButton(frame: CGRect(x: 200, y: 350, width: 150, height: 50))
        button.setTitle("Navigate", for: .normal)
        button.addTarget(self, action: #selector(buttonAction), for: .touchUpInside)
        button.backgroundColor = .blue
        return button
    }()

    @objc func buttonAction(){
        if self.redView.backgroundColor == .gray {
            self.redView.backgroundColor = .systemPink
        }
    }

    override func viewDidLoad() {
        navigateButton.layer.cornerRadius = 25
        redView.backgroundColor = UIColor.gray

        delegate.navigate(text: "Navigation Success", isShown: true)

        view.addSubview(redView)

        view.addSubview(navigateButton)
    }
}

And here is the protocol for the delegate which I've created:

protocol NavDelegate {
    func navigate(text: String, isShown: Bool)
}

Solution

  • You need to to assign delegate value from prepare function. Or you can assign delegate with initialize RedScreenVC(self) from your ViewController if u don't want to use storyboard/xib.

    import UIKit
    
    class ViewController: UIViewController, NavDelegate {
        func navigate(text: String, isShown: Bool) {
            print("text: \(text) isShown: \(isShown)")
        }
    
    
        override func viewDidLoad() {
            super.viewDidLoad()
            // Do any additional setup after loading the view.
    
            let common = SHService()
            common.printMe(printString: "Hello World")
        }
    
        override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
            if (segue.identifier == "RedScreenVC") {
                let RedScreenVC = segue.destination as? RedScreenVC
                RedScreenVC?.delegate = self
            }
        }
    
        @IBAction func nextPageButtonEventLustener(_ sender: Any) {
            performSegue(withIdentifier: "RedScreenVC", sender: sender)
        }
    }
    
    
    
    import UIKit
    
    protocol NavDelegate {
        func navigate(text: String, isShown: Bool)
    }
    class RedScreenVC: UIViewController {
    
         weak var delegate: NavDelegate?
    
        var redView = UIView(frame: CGRect(x: 0, y: 0, width: UIScreen.main.bounds.size.width, height: UIScreen.main.bounds.size.height))
    
        var navigateButton: UIButton = {
            let button = UIButton(frame: CGRect(x: 200, y: 350, width: 150, height: 50))
            button.setTitle("Navigate", for: .normal)
            button.addTarget(self, action: #selector(buttonAction), for: .touchUpInside)
            button.backgroundColor = .blue
            return button
        }()
    
        @objc func buttonAction(){
            if self.redView.backgroundColor == .gray {
                self.redView.backgroundColor = .systemPink
            }
          self.delegate.navigate(text:"", isShown: true)
    
        }
    
        override func viewDidLoad() {
            navigateButton.layer.cornerRadius = 25
            redView.backgroundColor = UIColor.gray
    
            delegate.navigate(text: "Navigation Success", isShown: true)
    
            view.addSubview(redView)
    
            view.addSubview(navigateButton)
        }
    
    }