如何解雇UIKeyboardTypeNumberPad? [英] How to dismiss UIKeyboardTypeNumberPad?

查看:106
本文介绍了如何解雇UIKeyboardTypeNumberPad?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试隐藏数字键盘,但我不想实现按钮。

I'm trying to hide the number pad, but I do not want to implement a button.

当用户点击文本字段之外时,有没有办法解除数字键盘?

Is there a way to dismiss the number pad when the user taps outside the textfield?

推荐答案

这是你读过它并说你很容易......的问题之一。然后你去做它并使它变得非常复杂。然后意识到它不必那么复杂。

This is one of those questions where you read it and say "That's easy you just..". And then you go to do it and make it super complicated. And then realize it doesn't have to be that complicated.

我想出的答案,我相信它会帮助别人,是使用一个不可见的 UIView ,它永远不会互动但会对其他观点产生影响,也可能不像你想象的那样。

The answer I've come up with, and I'm sure it will help someone else, Is to use an invisible UIView that never interacts but acts on other views and maybe not in the way you'd think.

关于解除 UIKeyboardTypeNumberPad 键盘问题的典型答案是添加一个带有按钮的栏,作为 inputAccessoryView 解雇键盘。如果一个酒吧和按钮是不受欢迎的,一般你只是在背景上听取触摸事件而你的好处就去了,但这个问题是关于一个tableview,这使得这更加困难。

The typical answer to a question about dismissing the UIKeyboardTypeNumberPad keyboard is to add a bar that has a button as the inputAccessoryView to dismiss the keyboard. If a bar and button are undesirable generally you just listen for touch events on the background and your good to go but this question is about a tableview and that makes this much harder.

但是这个 inputAccessoryView 功能仍然很棒。它允许您定义在显示键盘时显示的 UIView UIView 子类。更重要的是,由于文本字段显示键盘, inputAccessoryView 成为第一响应者。

But this inputAccessoryView feature is still awesome. It allows you to define a UIView or UIView subclass to be displayed when the keyboard is shown. More importantly when the keyboard is shown due to a textfield for which it is the inputAccessoryView becoming first responder.

I可以yammer,但首先是一些轻量级的代码实际上在测试中表现非常好。

I could yammer on but first here is some code for a lightweight class that actually performs very well in testing.

NJ_KeyboardDismisser.h的内容是:

#import <UIKit/UIKit.h>

    // For some reason neither inputView or inputAccessoryView are IBOutlets, so we cheat.
@interface UITextField (WhyDoIHaveToDoThisApple)
@property (readwrite, retain) IBOutlet UIView *inputAccessoryView;
@end

@interface NJ_KeyboardDismisser : UIView
@property (nonatomic, weak) IBOutlet UIView *mainView;
-(id)initWithMainView:(UIView *)view; // convienience method for code
@end

NJ_KeyboardDismisser.m 是:

#import "NJ_KeyboardDismisser.h"
@implementation NJ_KeyboardDismisser {
    UITapGestureRecognizer *_tapGR;
}
@synthesize mainView = _mainView;
-(void)setMainView:(UIView *)view{
    if (_tapGR) [_tapGR.view removeGestureRecognizer:_tapGR];
    _mainView = view;
    _tapGR = [[UITapGestureRecognizer alloc] initWithTarget:_mainView action:@selector(endEditing:)];
}
-(id)initWithMainView:(UIView *)view{
    if ((self = [super initWithFrame:CGRectMake(0, 0, 0, 0)])){
        self.mainView = view;
    }
    return self;
}
-(void)didMoveToWindow{ // When the accessory view presents this delegate method will be called
    [super didMoveToWindow];
    if (self.window){ // If there is a window one of the textfields, for which this view is inputAccessoryView, is first responder.
        [self.mainView addGestureRecognizer:_tapGR];
    }
    else { // If there is no window the textfield is no longer first responder
        [self.mainView removeGestureRecognizer:_tapGR];
    }
}
@end

您可能会认出 endEditing:方法,如Cosique所述,它是一个UIView扩展方法,要求嵌套文本字段的视图辞职。听起来方便吗?它是。通过在tableview上调用它包含的文本字段,第一个响应者。由于此技术适用于所有 UIView s,因此无需人为限制此插座仅限 UITableView s只是 UIView * mainView

You may recognize the endEditing: method, as mentioned by Cosique, it is a UIView extension method that asks a views nested textfield to resign. Sound handy? It is. By calling it on the tableview the textfield it contains resigns first responder. Since this technique works on all UIViews there is no need to artificially limit this outlet to only UITableViews so the outlet is just UIView *mainView.

这里最后的移动部分是 UITapGestureRecognizer 。我们不想全职添加这个识别器,因为担心搞砸了tableview的工作。所以我们利用 UIView 的委托方法 didMoveToWindow 。我们没有对窗口做任何事情,我们只是查看是否在一个窗口;如果我们是其中一个文本字段是第一响应者,如果不是那么它不是。我们相应地添加和删除我们的手势识别器。

The final moving part here is the UITapGestureRecognizer. We don't want to add this recognizer full time for fear of screwing up the tableview's workings. So we take advantage of UIView's delegate method didMoveToWindow. We don't really do anything with the window we just check to see if we are in one; If we are then one of our textfields is first responder, if not then it's not. We add and remove our gesture recognizer accordingly.

好的直截了当,但你如何使用它?好吧,如果在代码中实例化你可以这样做,在 tableView:cellForRowAtIndexPath:

Okay straightforward enough, but how do you use it? Well if instantiating in code you could do it like this, in tableView:cellForRowAtIndexPath::

if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"Cell"];
    UITextField *field = [[UITextField alloc] initWithFrame:CGRectMake(20, 6, 100, 31)];
    [cell.contentView addSubview:field];
    field.keyboardType = UIKeyboardTypeNumberPad;
    field.inputAccessoryView = [[NJ_KeyboardDismisser alloc] initWithMainView:self.view];
}

如果你在故事板中使用静态单元格,那么技术就不同了(显然)。首先拖出​​一个通用的 NSObject 并将其放在视图下方的深灰色条带中(其他对象,如视图控制器)。然后将此新对象的类更改为 NJ_KeyboardDismisser 。然后将Keyboard Dismisser的 mainView 属性连接到该视图(通常是tableview)。然后将 inputAccessoryView 属性从该场景中任何每个文本字段连接到Keyboard Dismisser。

If you are using static cells in a storyboard then the technique is different (obviously). First drag out a generic NSObject and place it in the dark grey strip below the view (where the other objects such as the view controller are). Then change this new object's class to be NJ_KeyboardDismisser. Then connect the "Keyboard Dismisser"'s mainView property to that view (generally a tableview). Then connect the inputAccessoryView property from any each text field in that scene you wish to the "Keyboard Dismisser".

试一试! tableview正常运行。 Apple的水龙头识别器非常智能,可以忽略桌面上的滑动,因此您可以滚动。它还会忽略文本字段中的触摸,因此您可以编辑和选择其他文本字段。但是在文本区域外点击并且键盘不见了。

Give it a try! The tableview acts normally. Apple's tap recognizer is smart enough to ignore the swipes on the table, so you can scroll. It also ignores touches in the textfields so you can edit and select other textfields. But tap outside a textfield and the keyboard is gone.

注意:此类的使用不仅限于tableviews。如果要在常规视图中使用它,只需将 mainView 属性设置为与视图控制器的视图相同。

Note: This class's use is not limited to tableviews. If you want to use it on a regular view, just set the mainView property to be the same as the view controller's view.

这篇关于如何解雇UIKeyboardTypeNumberPad?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆