Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Swift 4: Unrecognized selector sent to instance when calling a function inside another class

For my application, I am working without storyboards. For that reason, I am trying to keep my ViewController clutter free by storing larger functions inside another class and calling them when needed.

For some reason, when I call my functions with #Selector I get a crash stating "Unrecognized selector sent to instance".

When I store my function inside the same ViewController as the #Selector it works just fine.

The Following Code Below Works

View Controller

class ViewController: UIViewController {

override func viewDidLoad() {
    super.viewDidLoad()

    view.addSubview(loginRegisterButton)


}

lazy var loginRegisterButton: UIButton = {
    let button = UIButton(type: .system)
    button.backgroundColor = Color.darkBlue
    button.setTitle("Register", for: .normal)
    button.translatesAutoresizingMaskIntoConstraints = false
    button.setTitleColor(UIColor.white, for: .normal)
    button.layer.cornerRadius = 5
    button.titleLabel?.font = UIFont.boldSystemFont(ofSize: 16)

    button.addTarget(self, action: #selector(LoginFunctions.handleLogin), for: .touchUpInside)

    return button
}()

    @objc func handleLogin() {
    print("Logging In!!!")
    }

}

What I am trying to achieve

The code below does not work

View Controller

class ViewController: UIViewController {

override func viewDidLoad() {
    super.viewDidLoad()

    view.addSubview(loginRegisterButton)


}

lazy var loginRegisterButton: UIButton = {
    let button = UIButton(type: .system)
    button.backgroundColor = Color.darkBlue
    button.setTitle("Register", for: .normal)
    button.translatesAutoresizingMaskIntoConstraints = false
    button.setTitleColor(UIColor.white, for: .normal)
    button.layer.cornerRadius = 5
    button.titleLabel?.font = UIFont.boldSystemFont(ofSize: 16)

    button.addTarget(self, action: #selector(LoginFunctions.handleLogin), for: .touchUpInside)

    return button
}()

}

LoginFunctions

import Foundation
import UIKit

class LoginFunctions {

@objc func handleLogin() {
    print("Logging In!!!")
}
}

I have been trying to debug this for days with no luck. Any help would be greatly appreciated. Thanks in advance!

like image 766
Chandler Long Avatar asked Mar 06 '23 22:03

Chandler Long


2 Answers

There's no reference to your LoginFunctions from your ViewController. And you pass self as the target to the button but self doesn't have a handleLogin method.

You need to hold and instance of LoginFunctions in your ViewController class. Then pass that reference as the target instead of self.

class ViewController: UIViewController {
    let functions = LoginFunctions()

    lazy var loginRegisterButton: UIButton = {
        let button = UIButton(type: .system)
        button.backgroundColor = Color.darkBlue
        button.setTitle("Register", for: .normal)
        button.translatesAutoresizingMaskIntoConstraints = false
        button.setTitleColor(UIColor.white, for: .normal)
        button.layer.cornerRadius = 5
        button.titleLabel?.font = UIFont.boldSystemFont(ofSize: 16)

        button.addTarget(functions, action: #selector(LoginFunctions.handleLogin), for: .touchUpInside)

        return button
    }()
}
like image 167
rmaddy Avatar answered Apr 27 '23 11:04

rmaddy


To add a target to a class it must contain the func in selector , you may try this to share method between viewControllers

extension UIViewController 
{
    @objc func handleLogin() {
         print("Logging In!!!")
    }

}
like image 25
Sh_Khan Avatar answered Apr 27 '23 09:04

Sh_Khan