问题
处理表单的时候,一定会碰到的就是输入控件被键盘遮住的问题,如图:
实例
左边是普通表单,中间是2B表单,右边是文艺表单.
分析
处理这种问题无非就是2个步骤:
- 键盘弹出时,缩小
UITableView
的frame
- 滚动
UITableView
,让当前输入的控件可见
代码写出来就是这几步
- 捕获键盘事件
- 计算键盘高度并调整
UITableView
的frame
- 获取当前正在输入的控件
- 计算其在
UITableView
中的位置,并滚动到其位置让其可见
那么如何一步一步的来实现这些步骤呢?
捕获键盘事件
捕获键盘事件
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
|
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(actionKeyboardShow:) name:UIKeyboardDidShowNotification object:nil]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(actionKeyboardHide:) name:UIKeyboardWillHideNotification object:nil];
- (void)actionKeyboardShow:(NSNotification *)notification { [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidShowNotification object:nil]; [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidChangeFrameNotification object:nil]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(actionKeyboardShow:) name:UIKeyboardDidChangeFrameNotification object:nil];
}
- (void)actionKeyboardHide:(NSNotification *)notification { [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidChangeFrameNotification object:nil]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(actionKeyboardShow:) name:UIKeyboardDidShowNotification object:nil]; }
|
计算键盘高度并调整UITableView
的frame
计算键盘高度并调整UITableView的frame
1 2 3 4 5 6 7 8 9 10 11 12 13
|
- (void)actionKeyboardShow:(NSNotification *)notification { CGSize keyboardSize = [[[notification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue].size self.tableView.frame = CGRectMake(0, 0, 320, self.view.h-keyboardSize.height);
[[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidShowNotification object:nil]; [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidChangeFrameNotification object:nil]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(actionKeyboardShow:) name:UIKeyboardDidChangeFrameNotification object:nil];
}
|
获取当前正在输入的控件
这里得说一句,普通程序员一般是这样来获取的
UIView的Category
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
|
- (UIView *) getFirstResponder { if (self.isFirstResponder) { return self; }
for (UIView *subView in self.subviews) { UIView *firstResponder = [subView getFirstResponder]; if (firstResponder != nil) { return firstResponder; } }
return nil; }
|
虽然没错,但是文艺程序员应该这样来获取
UIResponder的Category
1 2 3 4 5 6 7 8 9 10 11
|
static __weak id currentFirstResponder;
+(id)currentFirstResponder { currentFirstResponder = nil; [[UIApplication sharedApplication] sendAction:@selector(findFirstResponder:) to:nil from:nil forEvent:nil]; return currentFirstResponder; }
-(void)findFirstResponder:(id)sender { currentFirstResponder = self; }
|
同理,有时候我们需要让键盘消失,那么也有三种做法可以选择
1 2 3 4 5
|
[someView resignFirstResponder];
[self.view endEditing:YES];
[[UIApplication sharedApplication] sendAction:@selector(resignFirstResponder) to:nil from:nil forEvent:nil];
|
如何选择呢? It’s up to U.
计算其在UITableView
中的位置,并滚动到其位置让其可见
计算其在UITableView中的位置,并滚动到其位置让其可见
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
|
- (void)actionKeyboardShow:(NSNotification *)notification { CGSize keyboardSize = [[[notification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue].size; self.tableView.frame = CGRectMake(0, 0, 320, self.view.h-keyboardSize.height);
UIView *v = [UIResponder currentFirstResponder];
if ( v ) { while ( ![v isKindOfClass:[UITableViewCell class]]) { v = v.superview; }
UITableViewCell *cell = (UITableViewCell*)v;
[self.tableView scrollToRowAtIndexPath:[self.tableView indexPathForRowAtPoint:cell.center] atScrollPosition:UITableViewScrollPositionBottom animated:YES]; }
[[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidShowNotification object:nil]; [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidChangeFrameNotification object:nil]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(actionKeyboardShow:) name:UIKeyboardDidChangeFrameNotification object:nil];
}
|