ios 在 UITableViewCell 中编辑 UITextField 时禁用 UITableView 的自动滚动
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/9637089/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Disabling automatic scrolling of UITableView when editing UITextField inside UITableViewCell
提问by animal_chin
I'm using custom UITableViewCell
s inside my UITableView
. Each of these UITableViewCell
s is pretty high and contains a UITextField
at the top.
我UITableViewCell
在我的UITableView
. 这些UITableViewCell
s 中的每一个都非常高,并且UITextField
在顶部包含一个。
When a user taps the UITextField
in order to edit it, a keyboard appears and the UITableView
scrolls automatically so that the cell is at the top of the screen.
当用户点击UITextField
以进行编辑时,会出现一个键盘并UITableView
自动滚动以使单元格位于屏幕顶部。
The problem is that this scrolls the UITableView
to the bottom of the UITableViewCell
, not the top. When the UITableViewCell
is high and edited the UITextField
is at the top so you can't see the UITextField
. I know how to scroll the UITableView
programmatically, but I just don't know how to disable this automatic scrolling so that I can scroll the UITableView
on my own. How can I do this?
问题是这会将 滚动UITableView
到 的底部,而UITableViewCell
不是顶部。当UITableViewCell
为高并编辑UITextField
时 位于顶部,因此您看不到UITextField
. 我知道如何以UITableView
编程方式滚动,但我只是不知道如何禁用这种自动滚动,以便我可以UITableView
自己滚动。我怎样才能做到这一点?
回答by Dominic Sander
The autoscroll-behavior is located in the UITableViewController
functionality.
自动滚动行为位于UITableViewController
功能中。
To disable the automatic scrolling I found two ways:
要禁用自动滚动,我找到了两种方法:
- Use instead of the
UITableViewController
simply aUIViewController
- set the datasource and delegate on your own. - Override the
viewWillAppear
method and don't call[super viewWillAppear: animated]
- 使用而不是
UITableViewController
简单的 aUIViewController
- 自行设置数据源和委托。 - 覆盖
viewWillAppear
方法,不要调用[super viewWillAppear: animated]
With both solution you disable not only the Autoscroll, but also some other nice but not essential features, that are described in the overview of Apple′s class reference:
使用这两种解决方案,您不仅可以禁用 Autoscroll,还可以禁用其他一些不错但不是必需的功能,这些功能在 Apple 的类参考概述中有所描述:
https://developer.apple.com/documentation/uikit/uitableviewcontroller
https://developer.apple.com/documentation/uikit/uitableviewcontroller
回答by william-yang
Define properties for your UITableViewController
:
为您定义属性UITableViewController
:
@property (nonatomic) BOOL scrollDisabled;
@property (nonatomic) CGFloat lastContentOffsetY;
Before you call becomeFirstResponder
:
在您致电之前becomeFirstResponder
:
// Save the table view's y content offset
lastContentOffsetY = tableViewController.tableView.contentOffset.y;
// Enable scrollDisabled
scrollDisabled = YES;
Add the following code to your table view controller:
将以下代码添加到您的表视图控制器:
-(void)scrollViewDidScroll:(UIScrollView *)scrollView
{
if (self.scrollDisabled) {
[self.tableView setContentOffset:CGPointMake(0, lastContentOffsetY)];
}
...
}
After you call resignFirstResponder
, set scrollDisabled = NO
.
调用后resignFirstResponder
,设置scrollDisabled = NO
。
回答by arturgrigor
You can do the following:
您可以执行以下操作:
- (void)registerForKeyboardNotifications
{
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(keyboardWillShow:)
name:UIKeyboardWillShowNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(keyboardDidShow:)
name:UIKeyboardDidShowNotification object:nil];
}
- (void)unregisterForKeyboardNotifications
{
[[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardWillShowNotification object:nil];
[[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardDidShowNotification object:nil];
}
- (void)keyboardWillShow:(NSNotification *)notification
{
self.tableView.scrollEnabled = NO;
}
- (void)keyboardDidShow:(NSNotification *)notification
{
double delayInSeconds = 0.3;
dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(delayInSeconds * NSEC_PER_SEC));
dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
self.tableView.scrollEnabled = YES;
});
}
Then implement this UIScrollViewDelegate method
然后实现这个 UIScrollViewDelegate 方法
- (void)scrollViewDidScroll:(UIScrollView *)scrollView
{
if (! self.tableView.scrollEnabled)
[self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForItem:0 inSection:0] atScrollPosition:UITableViewScrollPositionTop animated:NO];
}
!!! But be warned, that if the user taps in a location in the UITextField that will be covered by the Keyboard, then it won't scroll.
!!!但请注意,如果用户点击 UITextField 中将被键盘覆盖的位置,则它不会滚动。
From my point of view, the best thing to do is to make sure that all the cells from top to then one with the UITextField included, will be visible when then Keyboard will show.
从我的角度来看,最好的办法是确保从顶部到包含 UITextField 的所有单元格在显示键盘时都可见。
回答by juanelomx
The best way is to subclass UITableView
and then override setContentOffset(_ contentOffset: CGPoint, animated: Bool)
and not to call super.setContentOffset(_ contentOffset: CGPoint, animated: Bool)
. In this method is where the view controller is doing the automatic scroll.
最好的方法是子类化UITableView
然后覆盖setContentOffset(_ contentOffset: CGPoint, animated: Bool)
而不是调用super.setContentOffset(_ contentOffset: CGPoint, animated: Bool)
. 在此方法中,视图控制器正在执行自动滚动。
override func setContentOffset(_ contentOffset: CGPoint, animated: Bool)
{
//Do nothing
}
回答by infinite-loop
The issue for me was not so much that it scrolled but that it took the text view being edited off the screen.
对我来说,问题不在于它滚动,而是将正在编辑的文本视图从屏幕上移开。
So instead of preventing the scrolling, I just rescroll the tableview to where I want when the editing is triggered, like this:
因此,我没有阻止滚动,而是在触发编辑时将 tableview 重新滚动到我想要的位置,如下所示:
public func textViewShouldBeginEditing(textView: UITextView) -> Bool {
dispatch_async(dispatch_get_main_queue()) {
tableViewController.tableView.scrollToRowAtIndexPath(self.indexPath!, atScrollPosition: UITableViewScrollPosition.Middle, animated: true)
}
return true
}
回答by Ke Yang
Unfortunately, overriding -viewWillAppear: doesn't work for me in iOS 8.
不幸的是,在 iOS 8 中覆盖 -viewWillAppear: 对我不起作用。
Here is my solution (as in UITableViewController implementation):
这是我的解决方案(如 UITableViewController 实现):
- (void)viewDidLoad {
[super viewDidLoad];
[[NSNotificationCenter defaultCenter] removeObserver:self.tableView name:UIKeyboardWillShowNotification object:nil];
[[NSNotificationCenter defaultCenter] removeObserver:self.tableView name:UIKeyboardWillHideNotification object:nil];
}
Since the auto-scrolling behaviour is invoked by UIKeyboard's show/hide notifications, so just NOT observe them.
由于自动滚动行为是由 UIKeyboard 的显示/隐藏通知调用的,所以不要观察它们。
回答by Servus7
You could disable the automatic content inset adjustment like so:
您可以禁用自动内容插入调整,如下所示:
tableView.contentInsetAdjustmentBehavior = .never
回答by cocoakomali
Did you try to set "scrollsToTop" - tableview's property to NO. By default it is YES.
您是否尝试将“scrollsToTop” - tableview 的属性设置为 NO。默认情况下是 YES。
回答by DHShah01
You can try doing the following:
您可以尝试执行以下操作:
self.tableView.scrollEnabled = NO;
This should disable the scrollview in the tableview.
这应该禁用 tableview 中的滚动视图。