swift代理详解和使用

2,709 阅读1分钟

前言

代理是一种设计模式。它允许类(Swift中的结构体)将自身负责的功能委托给其他的类型的实例示例。多用于反向传值问题等

应用

反向传值应用,这个和objective_c的写法类似,如果熟悉oc的同学对此不会陌生

1.创建ViewController

class ViewController: UIViewController,SecondDelegate {

    var showLabel:UILabel?
    override func viewDidLoad() {
        super.viewDidLoad()
        self.view.backgroundColor = .white
        configUI()
    }
    
    func configUI() {
        showLabel = UILabel(frame: CGRect(x: 0, y: 100, width: 320, height: 40))
        showLabel?.textAlignment = .center
        showLabel?.text = "firstVc"
        view.addSubview(showLabel!)
        
        let pushButton = UIButton(type: .custom)
        pushButton.frame = CGRect(x: 150, y: 200, width: 60, height: 40)
        pushButton.setTitle("跳转", for: .normal)
        pushButton.backgroundColor = .systemPink
        pushButton.addTarget(self, action: #selector(pushBtnClick), for: .touchUpInside)
        view.addSubview(pushButton)
        
    }
    
    @objc func pushBtnClick() {
        let svc = SecondViewController()
        svc.delegate = self
        self.navigationController?.pushViewController(svc, animated: true)
    }
    
    @objc func saveName(_ nameStr: String) {
        showLabel?.text = nameStr
    }
}

2.secondViewController

protocol SecondDelegate:NSObjectProtocol {
    func saveName(_ nameStr: String)
}
class SecondViewController: UIViewController {

    weak var delegate: SecondDelegate?
    override func viewDidLoad() {
        super.viewDidLoad()
        self.view.backgroundColor = .white
    }
    
    override func viewWillDisappear(_ animated: Bool) {
        if self.delegate != nil && (self.delegate?.responds(to: Selector.init(("saveName:"))))! {
            self.delegate?.saveName("secondVc")
        }
    }
}

Swift中Delegate细节注意

一、需要用weak修饰代理(weak var SecondDelegate?) weak修饰声明的属性避免循环引用的问题(类似OC中的weak修饰)

二、代理方法的判断(respondsToSelector()在Swift中的使用) 原因是在OC的代码中, 用respondsToSelector()方法来判断是否实现了方法。 而在Swift中需要使用 (self.delegate?.responds(to: Selector.init(("saveName:"))))! 的方式判断是否实现这个方法。

在在代理执行的类中需要使用@objc 修饰saveName方法。(@objc 关键字来达到,Objective-C中使用#selector中使用)

block后面的文章会讲到