问题描述
我有一个聊天应用程序,可以在表格视图中显示消息。当我调用键盘时,我想:
@objc private func keyboardWillShow(notification: NSNotification) {
if let userInfo = notification.userInfo {
let keyBoardFrame = (userInfo[UIResponder.keyboardFrameEndUserInfoKey] as? NSValue)?.cgRectValue
let keyboardViewEndFrame = view.convert(keyBoardFrame!,from: view.window)
let keyboardHeight = keyboardViewEndFrame.height
tableView.scrollToBottom() { indexPath in
let rectofCell = self.tableView.rectForRow(at: indexPath)
let lastCellFrame = self.tableView.convert(rectofCell,from: self.view.window)
if lastCellFrame.origin.y + lastCellFrame.size.height > keyboardViewEndFrame.origin.y {
let overlap = lastCellFrame.origin.y + lastCellFrame.size.height - keyboardViewEndFrame.origin.y
self.tableView.frame.origin.y = -overlap
}
}
}
}
extension UITableView {
func scrollToBottom(animated: Bool = true,completion: ((IndexPath) -> Void)? = nil) {
let sections = self.numberOfSections
let rows = self.numberOfRows(inSection: sections - 1)
if (rows > 0){
let indexPath = IndexPath(row: rows - 1,section: sections - 1)
self.scrollToRow(at: indexPath,at: .bottom,animated: true)
completion?(indexPath)
}
}
}
rectOfCell
的值显示 (0.0,5305.333518981934,375.0,67.33333587646484)
和转换后的值 (0.0,9920.000185648601,67.33333587646484)
,并且表格视图消失在屏幕之外。
如果最后一条消息与键盘的最终位置重叠,我只想向上移动表格视图。例如,当键盘被调用时(当表视图已经在底部或不在底部时),如果键盘的外观没有覆盖消息(即,有只有一条消息)。
解决方法
您不需要为这样的事情管理 tableView.frame
。您只需要确保当键盘出现时,tableView 从底部添加必要的 contentInset 值,以便用户仍然可以在键盘仍在屏幕上的情况下看到 tableView 中的所有内容。
你只需要这个 -
// when keyboard appears
let insets = UIEdgeInsets(top: 0,left: 0,bottom: keyboardHeight,right: 0)
tableView.contentInset = insets
tableView.scrollIndicatorInsets = insets
// when keyboard disappears
let insets: UIEdgeInsets = .zero
tableView.contentInset = insets
tableView.scrollIndicatorInsets = insets