在UILabel上添加Closure动作

时间:2017-10-27 10:10:13

标签: ios swift closures uilabel uigesturerecognizer

我想在用户点按UILabel时添加一个闭包:

class ActionLabel: UILabel {
    typealias DidTapLabel = (ActionLabel) -> ()

    private let tapGestureRecognizer = UITapGestureRecognizer(target: self, action: #selector(didTouchUpInside(sender:)))

    var didTouchUpInside: DidTapLabel? {
        didSet {
            if didTouchUpInside != nil {
                self.addGestureRecognizer(tapGestureRecognizer)
                self.isUserInteractionEnabled = true
            } else {
                self.removeGestureRecognizer(tapGestureRecognizer)
                self.isUserInteractionEnabled = false
            }
        }
    }

    // MARK: - Actions
    @objc func didTouchUpInside(sender: ActionLabel) {
        if let handler = didTouchUpInside {
            handler(self)
        }
    }
}

用法:

    label.didTouchUpInside = { [weak self] sender in
        guard let strongSelf = self else {return}
        print(strongSelf)
    }

但似乎不起作用

2 个答案:

答案 0 :(得分:3)

您无法通过引用self来初始化手势识别器,因为此时未完成初始化。打印手势识别器阵列会显示target未设置

的信息
addGestureRecognizer(tapGestureRecognizer)
print("\(gestureRecognizers)")

输出(查看行尾)

Optional([<UITapGestureRecognizer: 0x6000001f9600; state = Possible; view = <asdfefe.ActionLabel 0x7fd714a03ea0>; target= <(action=didTouchUpInside:, target=<(null) 0x0>)>>])

因此,要解决此问题,请在初始化调用中初始化手势识别器

private var tapGestureRecognizer:UITapGestureRecognizer!

override init(frame: CGRect) {
    super.init(frame: frame)
    tapGestureRecognizer = UITapGestureRecognizer(target: self, action: #selector(didTouchUpInside))
}

希望有所帮助:)

答案 1 :(得分:2)

您的代码无效的原因是:

private let tapGestureRecognizer = UITapGestureRecognizer(target: self, action: #selector(touchAction))

tartget:self 是一个点,当ActionLabel初始化时,它将首先加载你的本地变量或常量,这样你就会获得一个空目标,因为自己现在没有初始化,当您点按视图时,它不会调用触摸操作。

好的解决方案是:

var didTouchUpInside: DidTapLabel? {
    didSet {
        if didTouchUpInside != nil {
            self.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(touchAction)))
            self.isUserInteractionEnabled = true
        } else {
            if let tapGestureRecognizer = self.gestureRecognizers?[0] as? UITapGestureRecognizer {
                self.removeGestureRecognizer(tapGestureRecognizer)
            }
            self.isUserInteractionEnabled = false
        }
    }
}