这是键盘模糊内容的有效解决方法

时间:2013-01-02 23:30:49

标签: ios

我有一个Tableview,用户可以在textField中输入值作为自定义单元格之一

Apple有一些关于如何通过重新定位视图而不是键盘的垂直尺寸(Here)来调整视图内容的文档,但它依赖于将该视图放入UIScrollView。我不能用tableview来做这件事。

我可以重新设计应用程序,以便使用常用的导航控制器在单独的详细视图中完成输入,但我宁愿用户不必执行额外的触摸(并且可以将其运送到另一个屏幕)可能。我喜欢这样做的想法“就在我们身边”

所以我的解决方法是在底部有一些额外的tableview单元格包含%20左右,正常使用不应该记录奇怪,因为它们只关注可见的内容。 我必须将空格存储在我的数据源数组中,然后按降序排序,但这没关系

问题是,这是一种好的做法吗?甚至更可能的是,是否可以反对Apple的HIG足以拒绝?

3 个答案:

答案 0 :(得分:2)

UITableView是UIScrollView的子类,因此应该能够调整内容并滚动视图插入内容,就像您链接的示例一样。

答案 1 :(得分:2)

我解决这个问题的方法是继承UITableView。这就是我所做的:

// AOTableView.h file

typedef enum
{
    AOKeyboardStateUnknown = 0,
    AOKeyboardStateShowing,
    AOKeyboardStateHidden
} AOKeyboardState;

#import <UIKit/UIKit.h>
#import "AOKeyboardState.h"

@interface AOTableView : UITableView
@property (nonatomic) BOOL observeKeyboardNotifications;
@property (nonatomic) AOKeyboardState keyboardState;
@end


// AOTableView.m file

#import "AOTableView.h"

@interface AOTableView(Private)
@property (nonatomic) CGRect frame0;
- (void)setup;
- (void)keyboardWillShow:(NSNotification *)notification;
- (void)keyboardWillHide:(NSNotification *)notification;
@end

@implementation AOTableView

#pragma mark - Object lifecycle

- (void)awakeFromNib
{       
    [self setup];
}

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];

    if (self)
    {
        [self setup];
    }
    return self;
}

- (void)setup
{
    self.contentSize = self.frame.size;
    self.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;

    _keyboardState = AOKeyboardStateUnknown;
    _frame0 = self.frame;
    _observeKeyboardNotifications = NO;
}

- (void)dealloc
{
    [[NSNotificationCenter defaultCenter] removeObserver:self];
}

#pragma mark - Custom setters

- (void)setObserveKeyboardNotifications:(BOOL)observeKeyboardNotifications
{
    if (_observeKeyboardNotifications == observeKeyboardNotifications)
        return;

    _observeKeyboardNotifications = observeKeyboardNotifications;

    if (_observeKeyboardNotifications)
    {
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyboardWillShow:) name:UIKeyboardWillShowNotification object:nil];
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyboardWillHide:) name:UIKeyboardWillHideNotification object:nil];
    }
    else
    {
         [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardWillShowNotification object:nil];
        [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardWillHideNotification object:nil];
    }
}

#pragma mark - UIKeyboard Notifications

- (void)keyboardWillShow:(NSNotification *)notification
{
    if (self.keyboardState == AOKeyboardStateShowing)
        return;

    self.frame0 = self.frame;
    self.keyboardState = AOKeyboardStateShowing;

    NSDictionary* info = [notification userInfo];
    CGRect keyboardFrame = CGRectZero;
    [[info objectForKey:UIKeyboardFrameEndUserInfoKey] getValue:&keyboardFrame];

    CGRect frame = self.frame0;    
    frame.size.height = CGRectGetMinY(keyboardFrame) - CGRectGetMinY(frame);
    self.frame = frame;

    [self scrollToRowAtIndexPath:self.indexPathForSelectedRow atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
    [self deselectRowAtIndexPath:self.indexPathForSelectedRow animated:NO];
}

- (void)keyboardWillHide:(NSNotification *)notification
{
    if (self.keyboardState == AOKeyboardStateHidden)
        return;

    self.keyboardState = AOKeyboardStateHidden;
    self.frame = self.frame0;
}
@end

创建(或从IBOutlet加载视图)后,调用此方法告诉类开始侦听键盘通知:

[tableViewInstance setObserveKeyboardNotifications:YES];

每当用户点击一个单元格时,它就会成为self.indexPathForSelectedRow单元格......所以它会自动滚动到AOTableView个实例。

为了实现这一点,我必须关闭单元格内userInteraction上的UITextField(否则,设备可能会对用户是否点击单元格或在文本字段上)。相反,当用户选择具有文本字段的单元格时,我告诉文本字段成为第一响应者,如下所示:

[cell.textField becomeFirstResponder];

我希望这会有所帮助。

答案 2 :(得分:1)

你不需要额外的细胞或任何花哨的东西。

由于您的文本字段位于表格视图单元格内,因此您可以使用以下内容:

- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
    UITableViewCell *cell = (UITableViewCell *)textField.superview.superview;
    NSIndexPath *indexPath = [self.tableView indexPathForCell:cell];
    [self.tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
    return YES;
}

这意味着每次文本字段成为第一响应者时键盘都会正确滚动。这利用了表视图是滚动视图的子类。

请注意,这假定:

  • 您的(表格)视图控制器是文本字段'委托。
  • 您的文本字段是单元格内容视图的子视图,而不是单元格本身。
    • 如果文本字段是单元格的子视图,则上述方法的第一行应仅引用一个超级视图(即textField.superview)。