我目前正在开发一个带有单个视图的iPhone应用程序,它有多个UITextField用于输入 . 键盘显示时,它覆盖底部文本字段 . 所以我添加了相应的 textFieldDidBeginEditing:
方法,以便向上移动视图,效果很好:
- (void)textFieldDidBeginEditing:(UITextField *)textField {
if ( ( textField != inputAmount ) && ( textField != inputAge ) ) {
NSTimeInterval animationDuration = 0.300000011920929;
CGRect frame = self.view.frame;
frame.origin.y -= kOFFSET_FOR_KEYBOARD;
frame.size.height += kOFFSET_FOR_KEYBOARD;
[UIView beginAnimations:@"ResizeForKeyboard" context:nil];
[UIView setAnimationDuration:animationDuration];
self.view.frame = frame;
[UIView commitAnimations];
}
}
如果消息源是键盘显示时可见的文本字段之一,则此方法检查,如果不是,则向上移动视图 .
我还添加了 textFieldDidEndEnditing:
方法,它再次向下移动视图(并根据更改的输入更新一些模型对象):
- (void)textFieldDidEndEditing:(UITextField *)textField {
if ( ( textField != inputMenge ) && ( textField != inputAlter ) ) {
NSTimeInterval animationDuration = 0.300000011920929;
CGRect frame = self.view.frame;
frame.origin.y += kOFFSET_FOR_KEYBOARD;
frame.size.height -= kOFFSET_FOR_KEYBOARD;
[UIView beginAnimations:@"ResizeForKeyboard" context:nil];
[UIView setAnimationDuration:animationDuration];
self.view.frame = frame;
[UIView commitAnimations];
}
// Additional Code
}
但是,这个解决方案有一个简单的缺陷:当我完成编辑其中一个“隐藏”文本字段并触摸另一个文本字段时,键盘消失,视图向下移动,视图再次向上移动,键盘重新出现 .
是否有可能防止键盘在两个编辑(“隐藏”文本字段)之间消失和重新出现 - 这样当所选文本字段从键盘隐藏的文本字段变为不隐藏的字段时,视图才会移动)?
6 回答
此解决方案基于ComSubVie的解决方案 .
好处:
它支持设备旋转 - 适用于所有方向;
它不会对动画持续时间和曲线的值进行硬编码,而是从键盘通知中读取它们;
它利用
UIKeyboardWillShowNotification
而不是UIKeyboardDidShowNotification
来同步键盘动画和自定义动作;它不使用已弃用的
UIKeyboardBoundsUserInfoKey
;由于按下国际键,它处理键盘调整大小;
通过取消注册键盘事件来修复内存泄漏;
所有键盘处理代码都封装在一个单独的类中 -
KBKeyboardHandler
;灵活性 -
KBKeyboardHandler
课程可以轻松扩展/修改,以更好地满足特定需求;限制:
适用于iOS 4及更高版本,需要进行少量修改才能支持旧版本;
适用于具有单个
UIWindow
的应用程序 . 如果使用多个UIWindows,则可能需要修改retrieveFrameFromNotification:
方法 .用法:
在项目中包含KBKeyboardHandler.h,KBKeyboardHandler.m和KBKeyboardHandlerDelegate.h . 在视图控制器中实现
KBKeyboardHandlerDelegate
协议 - 它由单个方法组成,当键盘显示,隐藏或其大小发生变化时,将调用该方法 . 实例化KBKeyboardHandler
并设置其委托(通常为self) . 请参见下面的示例MyViewController
.KBKeyboardHandler.h :
KBKeyboardHandler.m :
KBKeyboardHandlerDelegate.h :
示例 MyViewController.h :
示例 MyViewController.m :
更新:修复了iOS 7警告,感谢@weienv .
我刚刚解决了这个问题 . 该解决方案是
UIKeyboardDidShowNotification
和UIKeyboardDidHideNotification
观察者与上述textFieldDidBeginEditing:
和textFieldDidEndEditing:
方法的组合 .您需要三个附加变量,一个用于存储当前选定的UITextField(我已命名为activeField),一个用于指示当前视图是否已移动,另一个用于指示是否显示键盘 .
这就是两个
UITextField
委托方法现在的样子:加载视图时,将创建以下两个观察者:
相应的方法实现如下:
此代码现在按预期工作 . 键盘仅在按下“完成”按钮时被解除,否则它将保持可见状态并且视图不会移动 .
另外需要注意的是,我认为可以通过询问
NSNotification
对象来动态获取animationDuration
,因为我已经使用了类似的解决方案,但是没有让它工作(它现在就是这样) .此视图控制器必须是
UITextView
Delegate,您必须在viewdidload
中设置self.textview.delegate = self
非常简单的解决方案,适用于所有屏幕尺寸
首先,您必须将UITextFields嵌入到UIScrollView中 . 在我的例子中,我有几个UITextFields和一个UITextView .
然后你必须从UITextFieldDelegate,UITextViewDelegate继承 .
class SettingsVC: UIViewController, UITextFieldDelegate, UITextViewDelegate
将textfield和textview的委托分配给self .
fullNameTextField.delegate = self usernameTextField.delegate = self websiteTextField.delegate = self profileDescription.delegate = self
然后使用此代码:
简而言之,您订阅了UIKeyboardDidShow通知 . 当您点击textField或显示textView键盘时,您可以轻触键盘的输入元素的框架和框架 . 将它们转换为viewController的坐标系并将输入元素的最低点与键盘的最高点进行比较 . 如果element的下半部分低于键盘的最高值,则将containerScrollView的偏移量设置为它们之间的差值 .