流霞地

为iOS点击增加触控反馈

iOS 10增加了触控反馈的类UIFeedbackGenerator及其子类,使得触控反馈不再只能使用私有的sound id。 这里不再赘述触控反馈本身,而是提出一种通用的办法为比如UIButton增加触控反馈。示例代码FeedbackDemo在Github。 UIApplication类有一个方法:

func sendAction(_ action: Selector, to target: Any?, from sender: Any?, for event: UIEvent?) -> Bool

其注释如下:

Normally, this method is invoked by a UIControl object that the user has touched. The default implementation dispatches the action method to the given target object or, if no target is specified, to the first responder. Subclasses may override this method to perform special dispatching of action messages.

所以可以在这个方法里处理所有Button的事件:

override func sendAction(_ action: Selector, to target: Any?, from sender: Any?, for event: UIEvent?) -> Bool {
   let sent = super.sendAction(action, to: target, from: sender, for: event)
   if sent, let object = sender as? Feedbackable, object.fb_on {
      object.fb_vibrate()
   }
   return sent
}

Feedbackable定义如下:

public protocol Feedbackable {
    var fb_style: UIImpactFeedbackGenerator.FeedbackStyle { get set }
    var fb_on: Bool { get set }
    func fb_vibrate();
    func fb_prepare();
}

extension Feedbackable where Self: UIView {
...
}

extension UIButton: Feedbackable {
}

可以通过设置fb_on控制只在某一种情况下开启反馈,在另一种情况下关闭反馈,这是市面上大部分app里“点赞”的处理方式。 具体实现参见FeedbackDemo