我正在尝试构造一个 UIDatePicker,其高度与通过 keyboardDiDShow
通知观察到的用户键盘的高度相同。
键盘显示后,使用NotificationCenter Observer观察keyboardHeight。 UIDatePicker 在自定义 TableViewCell awakeFromNib()
函数中初始化。问题在于,只有在键盘确实显示调用 awakeFromNib()
之后发生的情况后,才能观察到 KeyboardHeight。有没有办法在初始化后更新 UIDatePicker 高度?
TableViewController
观察者:
`NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillShow), name: UIResponder.keyboardDidShowNotification , object: nil)`
键盘高度:
@objc func keyboardWillShow(notification: Notification) -> CGFloat {
NSLog("Keyboard appeared")
if let keyboardSize = (notification.userInfo[UIResponder.keyboardFrameEndUserInfoKey] as? NSValue)?.cgRectValue {
let heigth = keyboardSize.height
keyboardHeight = heigth
print(keyboardHeight)
return heigth
}
return 0
TableViewCell
UIDatePicker 初始化:
let picker = UIDatePicker()
let tableView = ItemsTableViewController()
override func awakeFromNib() {
// Initialization
super.awakeFromNib()
// UIDatePicker features
picker.minimumDate = Calendar.current.date(byAdding: DateComponents(), to: Date())
picker.datePickerMode = .date
picker.addTarget(self, action: #selector(pickerValueToText(_:)), for: .valueChanged)
// Size
let screenWidth = UIScreen.main.bounds.width
let size = CGSize(width: screenWidth, height: tableView.keyboardHeight)
let frame = CGRect(origin: CGPoint(x: 0, y: 0), size: size)
picker.frame = frame
// Add toolbar to picker
let toolbar = UIToolbar()
toolbar.sizeToFit()
let flexibleSpace = UIBarButtonItem(barButtonSystemItem: .flexibleSpace, target: nil, action: nil)
let doneButton = UIBarButtonItem(title: "Next", style: .done, target: self, action: #selector(doneClicked))
toolbar.setItems([flexibleSpace, doneButton], animated: true)
dateTextField.inputAccessoryView = toolbar
结果是 UIDatePicker 创建时高度为 0,因为创建选择器时键盘尚未显示。
最佳答案
为了直接回答您的问题,有一种方法可以更新选择器的高度。您只需要能够从 keyboardWillShow
实现中引用选择器即可:
cell.picker.frame.height=keyboardSize.height
编辑:
刚刚意识到您可能正在界面构建器(xib 或 Storyboard)中编写单元格,这意味着您已经在使用自动布局。仅仅设置选择器的高度在这里并不能解决问题。您必须在界面构建器中为选择器的高度添加 NSLayoutConstraint,并设置其 constant
属性以在键盘出现后匹配键盘的高度。像这样的东西:
cell.datePickerHeightConstraint.constant = KeyboardSize.height
我仍然认为您应该考虑使用下面提到的解决方案。
<小时/>但是,在我看来,您并没有采用最简单的方法。最简单的方法是将选择器设置为 dateTextField
的 inputView
。这样,选择器就会而不是显示键盘。将您的 awakeFromNib
实现更改为:
override func awakeFromNib() {
// Initialization
super.awakeFromNib()
// UIDatePicker features
picker.minimumDate = Calendar.current.date(byAdding: DateComponents(), to: Date())
picker.datePickerMode = .date
picker.addTarget(self, action: #selector(pickerValueToText(_:)), for: .valueChanged)
// Add toolbar to picker
let toolbar = UIToolbar()
toolbar.sizeToFit()
let flexibleSpace = UIBarButtonItem(barButtonSystemItem: .flexibleSpace, target: nil, action: nil)
let doneButton = UIBarButtonItem(title: "Next", style: .done, target: self, action: #selector(doneClicked))
toolbar.setItems([flexibleSpace, doneButton], animated: true)
dateTextField.inputAccessoryView = toolbar
dateTextField.inputView = picker
此外,如果您有兴趣以现代方式编写 UI 代码,您应该使用自动布局而不是直接设置 UIView
的框架:https://developer.apple.com/library/archive/documentation/UserExperience/Conceptual/AutolayoutPG/index.html
编辑2:
在 UIInputView
子类中嵌入 UIDatePicker
可以匹配键盘高度:
class DatePickerInputView: UIInputView {
let datePicker = UIDatePicker()
var height: CGFloat = 320 {
didSet {
heightConstraint?.constant = height
}
}
private var heightConstraint: NSLayoutConstraint?
override var inputViewStyle: UIInputView.Style {
get { return .default }
}
override var allowsSelfSizing: Bool {
get { return true }
set {}
}
init() {
super.init(frame: .zero, inputViewStyle: .default)
addSubview(datePicker)
translatesAutoresizingMaskIntoConstraints = false
datePicker.translatesAutoresizingMaskIntoConstraints = false
let heightConstraint = datePicker.heightAnchor.constraint(equalToConstant: height)
NSLayoutConstraint.activate([
datePicker.topAnchor.constraint(equalTo: topAnchor),
datePicker.bottomAnchor.constraint(equalTo: bottomAnchor),
datePicker.leadingAnchor.constraint(equalTo: leadingAnchor),
datePicker.trailingAnchor.constraint(equalTo: trailingAnchor),
heightConstraint
])
self.heightConstraint = heightConstraint
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
然后更改 keyboardWillShow
中的高度:
datePicker.height = keyboardSize.height
这是采用这种方法的存储库:https://github.com/AleksanderMaj/DatePickerInputView
关于ios - 在 iPhone X(及更高版本)上启动与键盘大小相同的 UIDatePicker,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53997195/