使用垂直滚动检测UIScrollView中的水平滑动

问题描述:

我有一个UIScrollView,高度约为600像素,宽度约为320。所以我允许用户垂直滚动。使用垂直滚动检测UIScrollView中的水平滑动

我也试图捕获视图上的水平滑动。问题似乎是,当用户在一些意外的垂直移动时水平滑动时,UIScrollView滚动和我的touchesEnded委托方法永远不会被调用。

这里是我的代码:

- (void)touchesEnded: (NSSet *)touches withEvent: (UIEvent *)event 
{ 
    UITouch *touch = [touches anyObject]; 
    CGPoint currentPosition = [touch locationInView:self]; 

    if (currentPosition.x + 35 < gestureStartPoint.x) 
    { 
     NSLog(@"Right"); 
    }  
    else if (currentPosition.x - 35 > gestureStartPoint.x) 
    { 
     NSLog(@"Left"); 
    }  
    else if (!self.dragging) 
    { 
     [self.nextResponder touchesEnded: touches withEvent:event]; 
    } 

    [super touchesEnded: touches withEvent: event]; 
} 

有谁知道我怎么能得到即使有垂直拖拽参与这个工作?

UIScrollView试图根据触摸开始后立即移动的情况来确定哪些触摸要通过其内容,哪些触摸是滚动。基本上,如果触摸看起来像是一个滚动马上,它处理该手势,内容永远不会看到它;否则,手势会通过(第一次触摸的延迟非常短)。

根据我的经验,我已经能够在UIScrollView的内容中捕获横向滑动来处理垂直滚动 - 它基本上只对我默认有效。我通过将contentSize设置为与滚动视图的宽度frame相同,这是足以告知UIScrollView它不会处理水平滚动的信息。

虽然这听起来像是你在默认行为方面有问题。一个硬件问题是,在笔记本电脑的触控板上模拟手指刷卡非常困难。如果我是你,我会用鼠标或者最好在设备上测试默认的UIScrollView设置。我发现这些输入方法在输送滑动方面效果更好。

如果不工作,这里是从苹果公司的UIScrollView文档非常中肯的段落:

由于滚动视图没有滚动条,它必须知道触摸是否预示意图滚动与一个意图追踪内容中的子视图。为了做出这个决定,它通过启动一个定时器暂时拦截一个触发事件,并且在定时器触发之前,看看触摸手指是否进行任何移动。如果时间没有发生重大变化,则滚动视图将跟踪事件发送到内容视图的触摸子视图。如果用户在计时器过去之前拖动手指足够远,则滚动视图取消子视图中的任何跟踪并执行滚动本身。子类可以覆盖touchesShouldBegin:withEvent:inContentView:,pagingEnabledtouchesShouldCancelInContentView:方法(由滚动视图调用)以影响滚动视图处理滚动手势的方式。

总之,您可以尝试通过继承UIScrollView并重写建议的方法来尝试他们的建议。

+1

Tyler, 感谢您的回复。我可以检测到水平的“滑动”,但只有当它们在Y中变化非常小时。如果我在y轴上粗略移动了+5像素,看起来ScrollView接管并开始垂直滚动。这并不现实,因为它需要我尝试几次(在设备上)才能在Y轴上进行这种小改动。你有没有经历类似的行为? – tuzzolotron 2009-10-04 03:11:41

如果@ Tyler的方法不起作用,请尝试将视图放在UIScrollView的正上方,并处理该视图的touchesBegan中的任何水平滑动,并将垂直滑动传递给下一个响应者。你可能会有点模糊,并处理任何水平移动比水平移动更多的水平移动,并将更纯净的垂直滑动传递给UISCrollView(通过nextResponder)。

+0

我试过这个,但没有能够在视图中得到任何接触... – tuzzolotron 2009-10-04 03:09:11

+0

新视图是没有得到任何接触?它是上面的滚动视图的一个孩子,还是一个兄弟姐妹?它是否设置为接受用户交互? – mahboudz 2009-10-05 07:25:47