日常开发中,经常会遇到输入框被键盘遮盖的问题, 本次思路是 将键盘处理相关代码封装成一个 单利的工具类, 通过监听系统的键盘相关通知来 获取键盘信息,实现被遮盖视图的上移操作,上代码:
import Foundation
class KeyBoderHandleTool: NSObject {
//可能会被遮盖的 view
private var keyBoderHandleView :UIView?
//可能会被遮盖的view 的遮盖高度
private var keyBoderHandleHeigt :CGFloat = 0.0
private let disposeBag = DisposeBag()
//单利对象
private static var sharedTool :KeyBoderHandleTool?
//获取单利对象
class func getSharedKeyBoderTool() ->KeyBoderHandleTool{
guard let instance = sharedTool else {
sharedTool = KeyBoderHandleTool()
return sharedTool!
}
return instance
}
//销毁单利对象
class func destroy() {
sharedTool = nil
}
// 私有化init 初始方法
private override init() {}
//监听键盘弹出
/// 处理键盘 遮盖问题
///
/// - Parameters:
/// - handleView: 需要处理的视图
/// - offsetY: 如果是 可滑动的view 就传入 y 轴上的偏移量
func handleKeyBoderAction(handleView :UIView, offsetY :CGFloat?){
if keyBoderHandleView != nil {
//更换遮盖view
self.keyBoderHandleView = handleView
return
}
print("开始了****************")
self.keyBoderHandleView = handleView
//监听键盘出现
weak var weakSelf = self
NotificationCenter.default.addObserver(forName: UIResponder.keyboardDidShowNotification, object: nil, queue: OperationQueue.main) { (notification) in
let info = notification.userInfo
//键盘动画时间
let duration = (info?[UIResponder.keyboardAnimationDurationUserInfoKey] as! NSNumber).doubleValue
//键盘坐标尺寸
let keyBoderRect = (info?[UIResponder.keyboardFrameEndUserInfoKey] as! NSValue).cgRectValue
//获取键盘被遮盖部分的高度
let keyBoderHeight = keyBoderRect.size.height //获取键盘高度
let boundHeight = UIScreen.main.bounds.size.height //屏幕高度
let viewMaxY :CGFloat = offsetY == nil ? weakSelf!.keyBoderHandleView!.frame.maxY : (weakSelf!.keyBoderHandleView!.frame.maxY-offsetY!)
//需要处理的 view 的绝对 Y 坐标
//计算出被遮盖部分的高度
weakSelf!.keyBoderHandleHeigt = viewMaxY - (boundHeight-keyBoderHeight)
if weakSelf!.keyBoderHandleHeigt <= 0 {
return
}
//将其父视图 上移被遮盖的高度
if let superView = weakSelf!.keyBoderHandleView!.superview {
UIView.animate(withDuration: duration, animations: {
weakSelf!.keyBoderHandleView!.superview!.frame = CGRect.init(x: superView.frame.origin.x, y: superView.frame.origin.y - weakSelf!.keyBoderHandleHeigt, width: superView.bounds.size.width, height: superView.bounds.size.height)
})
}
print("打印数据--消失--\(weakSelf!.keyBoderHandleHeigt)----\(weakSelf!.keyBoderHandleView!.tag)")
}
NotificationCenter.default.addObserver(forName: UIResponder.keyboardWillHideNotification, object: nil, queue: OperationQueue.main) { (notification) in
let info = notification.userInfo
if weakSelf!.keyBoderHandleHeigt <= 0{
return
}
//键盘动画时间
let duration = (info?[UIResponder.keyboardAnimationDurationUserInfoKey] as! NSNumber).doubleValue
//将高度还原
if let superView = weakSelf!.keyBoderHandleView!.superview {
UIView.animate(withDuration: duration, animations: {
weakSelf!.keyBoderHandleView!.superview!.frame = CGRect.init(x: superView.frame.origin.x, y: superView.frame.origin.y + weakSelf!.keyBoderHandleHeigt, width: superView.bounds.size.width, height: superView.bounds.size.height)
})
}
print("打印数据--消失--\(weakSelf!.keyBoderHandleHeigt)----\(weakSelf!.keyBoderHandleView!.tag)")
}
}
deinit {
NotificationCenter.default.removeObserver(self, name: UIResponder.keyboardWillHideNotification, object: nil)
NotificationCenter.default.removeObserver(self, name: UIResponder.keyboardDidShowNotification, object: nil)
}
}
使用时, 只需要直接调用:
KeyBoderHandleTool.getSharedKeyBoderTool().handleKeyBoderAction(handleView: textField, offsetY: nil)
当输入框在 可滑动控件上时,记得传入 y 轴上的 offset,否则传nil
注意点:
1:在 确定不需要再监听的情况下可以 调用 工具类中的 销毁方法
2: 发生界面跳转等情况时,请先将键盘隐藏(self.view.endEditing(true))