我可以覆盖滚动视图的自动行为以滚动到第一个响应者吗?

mor*_*tar 9 iphone uiscrollview first-responder

我在UIScrollView中有一个UITextField(深层次).我正在观看UIKeyboardDidShowNotification,并在手动更改第一个响应者时调用相同的代码(我可能会更改为不同的文本字段而不会暂时隐藏键盘).在该代码中,我scrollRectToVisible:animated:用来确保UITextField可见.

我有一个非常头疼的调试为什么这很有趣,但我现在意识到UIScrollView会自动确保第一个响应者在其范围内.我正在更改UIScrollView的框架,以便它们都不会隐藏在键盘后面.

但是,我的代码可能比它们的代码更聪明,因为我不仅要显示UITextField,还要显示一些附近的相关视图.如果它们合适,我会尝试展示这些观点; 如果不是,我尽可能多地展示它们,但至少要确保UITextField可见.所以我想保留我的自定义代码.

自动行为会干扰我的代码.我看到的是滚动视图轻轻向上滚动,以便我的内容的底部边缘可见,然后它快照到我的代码告诉它的位置.

反正有没有阻止UIScrollView执行其将第一个响应者滚动到视图中的默认功能?

更多信息

在阅读文档时,我读到他们建议更改滚动视图的contentInset而不是框架.我改变了这一点并消除了一些不可预测的行为,但它没有解决这个特殊问题.

我认为发布所有代码并不一定有用.但这是关键的召唤和当时重要属性的价值.我将为CGRects编写4元组; 我的意思是(x,y,宽度,高度).

[scrollView scrollRectToVisible:(116.2, 71.2, 60, 243) animated:YES];
Run Code Online (Sandbox Code Playgroud)

scrollView.bounds ==(0,12,320,361)

scrollView.contentInset == UIEdgeInsetsMake(0,0,118,0)

textField.frame ==(112.2,222.6,24,24)

转换为scrollView的直接子视图的坐标==(134.2,244.6,24,24)

转换为scrollView的坐标==(134.2,244.6,24,24)

因此,滚动视图底部边缘实际上在y == 243处,因为插入.

请求的矩形扩展到y == 314.2.

文本字段扩展到y == 268.6.

两者都是出界的.scrollRectToVisible试图解决其中一个问题.标准UIScrollView/UITextField行为正在尝试修复另一个.他们没有提出完全相同的解决方案.

Abe*_*ant 5

我没有测试这种特殊情况,但是我设法通过子类化scrollview并覆盖setContentOffset:和setContentOffset:animated:来阻止scrollview在顶部和底部弹跳.scrollview在每次滚动动作时调用它,所以我很确定在滚动到文本字段时会调用它们.

您可以使用委托方法textFieldDidBeginEditing:来确定何时允许滚动.

在代码中:

- (void)textFieldDidBeginEditing:(UITextField *)textField
{
    self.blockingTextViewScroll = YES;
}

-(void)setContentOffset:(CGPoint)contentOffset
{
    if(self.blockingTextViewScroll)
    {
        self.blockingTextViewScroll = NO;
    }
    else
    {
        [super setContentOffset:contentOffset];
    }
}


-(void)setContentOffset:(CGPoint)contentOffset animated:(BOOL)animated
{
    if(self.blockingTextViewScroll)
    {
        self.blockingTextViewScroll = NO;
    }
    else
    {
        [super setContentOffset:contentOffset animated:animated];
    }
}
Run Code Online (Sandbox Code Playgroud)

如果您当前的滚动行为与setContentOffset:override一起使用,只需将其放在else块中(或者最好放在您从else块调用的方法中).