我有很多控件散布在表中的许多表格单元格中,我想知道是否有一种更简便的方法来关闭键盘,而不必遍历所有控件并将它们全部放弃为第一响应者。我想问题是..我怎样才能使当前的第一响应键盘?
[[[UIApplication sharedApplication] keyWindow] endEditing:YES];
我有很多控件散布在表中的许多表格单元格中,我想知道是否有一种更简便的方法来关闭键盘,而不必遍历所有控件并将它们全部放弃为第一响应者。我想问题是..我怎样才能使当前的第一响应键盘?
[[[UIApplication sharedApplication] keyWindow] endEditing:YES];
Answers:
尝试:
[self.view endEditing:YES];
[self.view endEditing:YES];
因为在Objective-C中BOOL值为YES / NO。
您可以使用强制当前正在编辑的视图退出其第一响应者状态[view endEditing:YES]
。这将隐藏键盘。
与不同-[UIResponder resignFirstResponder]
,-[UIView endEditing:]
将在子视图中搜索以找到当前的第一响应者。因此,您可以将其发送到顶级视图(例如self.view
在中UIViewController
),它将做正确的事情。
(此答案先前包含了其他一些解决方案,这些解决方案也可以使用,但比必需的解决方案更为复杂。为了避免混淆,我删除了它们。)
[self.view endEditing:YES];
回答是好。
[UIView endediting:]
工作。在我开发的一个应用程序中,在UINavigationViewController中添加了一个搜索框,如果您只是调用[self.view endEditing:YES]
,作为self
视图控制器,则此方法将不起作用,而是直接在添加了搜索框的视图范围中调用此方法,例如:[self.mySearchBoxView endEditing:YES]
。
您可以将零目标操作发送到应用程序,它会随时辞职第一响应者,而不必担心当前哪个视图具有第一响应者状态。
目标C:
[[UIApplication sharedApplication] sendAction:@selector(resignFirstResponder) to:nil from:nil forEvent:nil];
Swift 3.0:
UIApplication.shared.sendAction(#selector(resignFirstResponder), to: nil, from: nil, for: nil)
在Mac OS X上,菜单命令通常没有针对性的操作,这在iOS上很有用。
老实说,我对这里提出的任何解决方案都不感到疯狂。我确实找到了一种使用TapGestureRecognizer的好方法,我认为这是问题的核心:单击键盘以外的任何东西时,请关闭键盘。
在viewDidLoad中,注册以接收键盘通知并创建UITapGestureRecognizer:
NSNotificationCenter *nc = [NSNotificationCenter defaultCenter];
[nc addObserver:self selector:@selector(keyboardWillShow:) name:
UIKeyboardWillShowNotification object:nil];
[nc addObserver:self selector:@selector(keyboardWillHide:) name:
UIKeyboardWillHideNotification object:nil];
tapRecognizer = [[UITapGestureRecognizer alloc] initWithTarget:self
action:@selector(didTapAnywhere:)];
添加键盘显示/隐藏响应器。您可以在其中添加和删除TapGestureRecognizer到UIView,点击时应关闭键盘。注意:您不必将其添加到所有子视图或控件中。
-(void) keyboardWillShow:(NSNotification *) note {
[self.view addGestureRecognizer:tapRecognizer];
}
-(void) keyboardWillHide:(NSNotification *) note
{
[self.view removeGestureRecognizer:tapRecognizer];
}
TapGestureRecognizer会在您点击时调用您的函数,您可以像这样关闭键盘:
-(void)didTapAnywhere: (UITapGestureRecognizer*) recognizer {
[textField resignFirstResponder];
}
此解决方案的优点在于,它仅过滤Taps,而不刷卡。因此,如果您在键盘上方滚动内容,滑动仍将滚动并保持键盘显示。通过在键盘移开后移除手势识别器,可以正常处理以后在视图上的点击。
这是一种通过在一个地方添加代码来使键盘return
在任何文本字段中击中时都消失的解决方案(因此不必为每个文本字段添加处理程序):
考虑这种情况:
我有viewcontroller
两个文本字段(用户名和密码)。和viewcontroller
实施UITextFieldDelegate
协议
我在viewDidLoad中做到这一点
- (void)viewDidLoad
{
[super viewDidLoad];
username.delegate = self;
password.delegate = self;
}
并且viewcontroller将可选方法实现为
- (BOOL)textFieldShouldReturn:(UITextField *)textField
{
[textField resignFirstResponder];
return YES;
}
不论您处于哪个文本字段,只要我return
按键盘,它就会被关闭!
在您的情况下,只要将所有文本字段的委托设置为self并实施 textFieldShouldReturn
更好的方法是让某些“窃取”第一响应者身份。
由于UIApplication是UIResponder的子类,因此您可以尝试:
[[UIApplication sharedApplication] becomeFirstResponder]
[[UIApplication sharedApplication] resignFirstResponder]
失败的话,创建一个尺寸为零的新UITextField,将其添加到某处的视图中并执行类似的操作(随后是辞职)。
将其隐藏在一些实用程序类中。
+ (void)dismissKeyboard {
[self globalResignFirstResponder];
}
+ (void) globalResignFirstResponder {
UIWindow * window = [[UIApplication sharedApplication] keyWindow];
for (UIView * view in [window subviews]){
[self globalResignFirstResponderRec:view];
}
}
+ (void) globalResignFirstResponderRec:(UIView*) view {
if ([view respondsToSelector:@selector(resignFirstResponder)]){
[view resignFirstResponder];
}
for (UIView * subview in [view subviews]){
[self globalResignFirstResponderRec:subview];
}
}
@尼古拉斯·莱利(Nicholas Riley)和@肯德尔·赫尔姆斯特(Kendall Helmstetter)盖恩(Genn)&@cannyboy:
绝对辉煌!
谢谢。
考虑到您的建议以及该线程中其他人的建议,这就是我所做的:
使用时的外观:
[[self appDelegate] dismissKeyboard];
(注意:我添加了appDelegate作为NSObject的补充,因此我可以在任何地方使用任何东西)
幕后的样子:
- (void)dismissKeyboard
{
UITextField *tempTextField = [[[UITextField alloc] initWithFrame:CGRectZero] autorelease];
tempTextField.enabled = NO;
[myRootViewController.view addSubview:tempTextField];
[tempTextField becomeFirstResponder];
[tempTextField resignFirstResponder];
[tempTextField removeFromSuperview];
}
编辑
修改我的回答包括在内tempTextField.enabled = NO;
。如果您在整个应用程序中都依赖这些通知,则禁用文本字段将阻止UIKeyboardWillShowNotification
并UIKeyboardWillHideNotification
发送键盘通知。
这是我在代码中使用的内容。它就像一个魅力!
在yourviewcontroller.h中添加:
@property (nonatomic) UITapGestureRecognizer *tapRecognizer;
现在在.m文件中,将其添加到您的ViewDidLoad函数中:
- (void)viewDidLoad {
//Keyboard stuff
tapRecognizer = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(didTapAnywhere:)];
tapRecognizer.cancelsTouchesInView = NO;
[self.view addGestureRecognizer:tapRecognizer];
}
另外,在.m文件中添加以下功能:
- (void)handleSingleTap:(UITapGestureRecognizer *) sender
{
[self.view endEditing:YES];
}
在视图控制器的头文件中,添加<UITextFieldDelegate>
到控制器接口的定义,以使其符合UITextField委托协议...
@interface someViewController : UIViewController <UITextFieldDelegate>
...在控制器的实现文件(.m)中,添加以下方法,如果您已经具有viewDidLoad方法,则在其中添加代码...
- (void)viewDidLoad
{
// Do any additional setup after loading the view, typically from a nib.
self.yourTextBox.delegate = self;
}
...然后,将yourTextBox链接到您的实际文本字段
- (BOOL)textFieldShouldReturn:(UITextField *)theTextField
{
if (theTextField == yourTextBox) {
[theTextField resignFirstResponder];
}
return YES;
}
您应该将发送endEditing:
到工作窗口的子类UIView
[[UIApplication sharedApplication].windows.firstObject endEditing:NO];
从UITableView和UIScrollView消除键盘的最佳方法是:
tableView.keyboardDismissMode = UIScrollViewKeyboardDismissModeOnDrag
杰里米(Jeremy)的答案对我而言并不奏效,因为我在选项卡视图中有一个导航堆栈,在其顶部有一个模式对话框。我现在正在使用以下产品,它正在为我工作,但是您的行驶里程可能会有所不同。
// dismiss keyboard (mostly macro)
[[UIApplication sharedApplication].delegate dismissKeyboard]; // call this in your to app dismiss the keybaord
// --- dismiss keyboard (in indexAppDelegate.h) (mostly macro)
- (void)dismissKeyboard;
// --- dismiss keyboard (in indexAppDelegate.m) (mostly macro)
// do this from anywhere to dismiss the keybard
- (void)dismissKeyboard { // from: http://stackoverflow.com/questions/741185/easy-way-to-dismiss-keyboard
UITextField *tempTextField = [[UITextField alloc] initWithFrame:CGRectZero];
UIViewController *myRootViewController = <#viewController#>; // for simple apps (INPUT: viewController is whatever your root controller is called. Probably is a way to determine this progragrammatically)
UIViewController *uivc;
if (myRootViewController.navigationController != nil) { // for when there is a nav stack
uivc = myRootViewController.navigationController;
} else {
uivc = myRootViewController;
}
if (uivc.modalViewController != nil) { // for when there is something modal
uivc = uivc.modalViewController;
}
[uivc.view addSubview:tempTextField];
[tempTextField becomeFirstResponder];
[tempTextField resignFirstResponder];
[tempTextField removeFromSuperview];
[tempTextField release];
}
子类化您的文本字段...以及文本视图
在子类中放置此代码。
-(void)conformsToKeyboardDismissNotification{
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(dismissKeyBoard) name:KEYBOARD_DISMISS object:nil];
}
-(void)deConformsToKeyboardDismissNotification{
[[NSNotificationCenter defaultCenter] removeObserver:self name:KEYBOARD_DISMISS object:nil];
}
- (void)dealloc{
[[NSNotificationCenter defaultCenter] removeObserver:self];
[self resignFirstResponder];
}
在文本字段委托中(类似于textview委托)
-(void)textFieldDidBeginEditing:(JCPTextField *)textField{
[textField conformsToKeyboardDismissNotification];
}
- (void)textFieldDidEndEditing:(JCPTextField *)textField{
[textField deConformsToKeyboardDismissNotification];
}
全部设置好了。现在只需从代码中的任何位置发布通知即可。它将退出任何键盘。
要在弹出键盘后关闭键盘,有2种情况,
当UITextField 在UIScrollView内时
当UITextField 在UIScrollView之外时
2.当UITextField在UIScrollView外部时,覆盖UIViewController子类中的方法
您还必须为所有UITextView添加委托
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
[self.view endEditing:YES];
}
要创建IBAction,请按ctrl键并单击UITapGesture并将其拖动到viewcontroller的.h文件中。
在这里,我将tappedEvent命名为我的动作名称
- (IBAction)tappedEvent:(id)sender {
[self.view endEditing:YES]; }
给定的上述信息来自以下链接,如果您不了解上述数据,请参阅更多信息或与我联系。
http://samwize.com/2014/03/27/dismiss-keyboard-when-tap-outside-a-uitextfield-slash-uitextview/
您可以递归地遍历子视图,存储所有UITextField的数组,然后遍历它们并将其全部签名。
这并不是一个很好的解决方案,特别是如果您有很多子视图时,但是对于简单的应用程序,它应该可以解决问题。
我以更复杂但更高效的方式解决了这个问题,但是使用单例/管理器作为应用程序的动画引擎,并且每当文本字段成为响应者时,我都会将其分配给静态对象,这样可以得到基于某些其他事件而被清扫(辞职)……对于我来说,在段落中几乎无法解释。
有创造力,发现问题后,我只花了10分钟就为我的应用程序思考了一下。
我最近需要使用一种更健壮的方法:
- (void) dismissKeyboard {
NSArray *windows = [UIApplication sharedApplication].windows;
for(UIWindow *window in windows) [window endEditing:true];
// Or if you're only working with one UIWindow:
[[UIApplication sharedApplication].keyWindow endEditing:true];
}
我发现其他一些“全局”方法不起作用(例如,UIWebView
&WKWebView
拒绝辞职)。
迅速地:
self.view.endEditing(true)
简便的方法是调用方法
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
if(![txtfld resignFirstResponder])
{
[txtfld resignFirstResponder];
}
else
{
}
[super touchesBegan:touches withEvent:event];
}
您必须使用以下方法之一,
[self.view endEditing:YES];
要么
[self.textField resignFirstResponder];