代码之家  ›  专栏  ›  技术社区  ›  Ben Zotto sberry

如何以编程方式强制在UIScrollView中停止滚动?

  •  68
  • Ben Zotto sberry  · 技术社区  · 14 年前

    answer given here 不适合我。

    我有一个UIScrollView(不是一个表视图,只是一个自定义的东西),当用户执行某些操作时,我想消除视图中的任何滚动(拖动或减速)。我试过这样做,例如:

    [scrollView scrollRectToVisible:CGRectInset([scrollView bounds], 10, 10) animated:NO];
    

    可以 让滚动停止,如果我给一个矩形,这是肯定的 外部 当前可见的边界,但在视图的contentSize内。这似乎阻止了预期的观点。。。但也会导致它跳转到其他位置。我也许可以在页边空白处做一点小游戏来让它正常工作,但是有人知道一个干净的方法来停止正在运行的滚动视图吗?

    9 回复  |  直到 8 年前
        1
  •  109
  •   nrj    13 年前

    任何滚动操作的通用解决方案如下:

    - (void)killScroll 
    {
        CGPoint offset = scrollView.contentOffset;
        offset.x -= 1.0;
        offset.y -= 1.0;
        [scrollView setContentOffset:offset animated:NO];
        offset.x += 1.0;
        offset.y += 1.0;
        [scrollView setContentOffset:offset animated:NO];
    }
    

    [编辑]从iOS 4.3(可能更早)开始,这似乎也能起作用

    - (void)killScroll 
    {
        CGPoint offset = scrollView.contentOffset;
        [scrollView setContentOffset:offset animated:NO];
    }
    
        2
  •  93
  •   calimarkus    5 年前

    [scrollView setContentOffset:offset animated:NO] 不一样 作为 [scrollView setContentOffset:offset]

    • [滚动视图设置内容]ffset:offset animated:否] 实际上停止任何正在运行的动画。
    • 不会停止任何正在运行的动画。
    • scrollView.contentOffset = offset :不停止任何正在运行的动画。

    这在任何地方都没有记录,但这是iOS 6.1上测试的行为;iOS 7.1-可能也是以前的版本。

    解决方案 停止正在运行的动画/减速非常简单:

    [scrollView setContentOffset:scrollView.contentOffset animated:NO];
    

    基本上就是刘大卫在编辑后的回答中所说的。但我想说清楚,这两个API是

    Swift 3:

    scrollView.setContentOffset(scrollView.contentOffset, animated:false)
    
        3
  •  68
  •   Community CDub    8 年前

    David Lui's accepted answer above 不适合我。这就是我最后要做的:

    - (void)killScroll {
        self.scrollView.scrollEnabled = NO;
        self.scrollView.scrollEnabled = YES;
    }
    

    值得一提的是,我使用的是ios6.0iphone模拟器。

        4
  •  22
  •   Community CDub    4 年前

    这是我对滚动视图和所有其他相关子类所做的:

    - (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset
     {
        *targetContentOffset = scrollView.contentOffset;
     }
    

    这设置了 targetContentOffset scrollView 的当前偏移量,从而使滚动停止,因为它已到达目标。 contentOffset .

    斯威夫特

    func scrollViewWillEndDragging(_ scrollView: UIScrollView, withVelocity velocity: CGPoint, targetContentOffset: UnsafeMutablePointer<CGPoint>) {
        targetContentOffset.pointee = scrollView.contentOffset
    }
    
        5
  •  20
  •   budiDino    8 年前

    停止滚动 敏捷的

    scrollView.setContentOffset(scrollView.contentOffset, animated: false)
    
        6
  •  16
  •   Xatian    10 年前

    事实上。。。最“现代”的方式是-->

    scrollview.panGestureRecognizer.enabled = false;
    scrollview.panGestureRecognizer.enabled = true;
    

    这将停用手势识别器,该识别器只负责滚动一小会儿,这将终止当前的触摸。用户需要抬起手指并将其放回原位才能再次开始滚动。

    编辑:这实际上只是终止用户当前的拖动,但如果scrollview当前处于这种状态,则不会立即停止减速。要做到这一点,公认的答案编辑几乎是最好的方式xD

    [scrollview setContentOffset: scrollview.contentOffset animated:false];
    
        7
  •  5
  •   mvds    14 年前

    最干净的方法是对UIScrollView进行子类化,并提供自己的setContentOffset方法。这会传递信息, 只有 如果你还没打开电源 freeze 布尔属性。

    BOOL freeze; // and the @property, @synthesize lines..
    
    -(void)setContentOffset:(CGPoint)offset
    {
        if ( !freeze ) [super setContentOffset:offset];
    }
    

    然后,冻结:

    scrollView.freeze = YES;
    
        8
  •  4
  •   Community CDub    8 年前

    Deactivate UIScrollView decelerating

    -(void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView{
        [scrollView setContentOffset:scrollView.contentOffset animated:YES];
    }
    
        9
  •  3
  •   Brownsoo Han    5 年前

    禁用仅滚动用户交互(雨燕)

    scrollView.isScrollEnabled = false
    

    拖动后在滚动动画期间禁用(雨燕)

    var scrollingByVelocity = false
    
    func scrollViewWillBeginDecelerating(_ scrollView: UIScrollView) {
        if !scrollingByVelocity {
            scrollView.setContentOffset(scrollView.contentOffset, animated: false)
        }
    }
    
        10
  •  1
  •   Lakhdeep Singh    4 年前

    SWift 5号+

    extension UIScrollView  {
        
        func stopDecelerating() {
            let contentOffset = self.contentOffset
            self.setContentOffset(contentOffset, animated: false)
        }
    }
    

    使用

        myScrollView.stopDecelerating()
        // your stuff
    
        11
  •  0
  •   Kalerfu    8 年前

    我在collectionview中尝试了以下方法:

    self.collectionView.collectionViewLayout.finalizeCollectionViewUpdates()

        12
  •  0
  •   StefanLdhl    5 年前

    这对我来说很管用

       func killScroll() {
        self.scrollView.isScrollEnabled = false;
        self.scrollView.isScrollEnabled = true;
    }
    

    ... 作为扩展:

    extension UIScrollView {
        func killScroll() {
            self.isScrollEnabled = false;
            self.isScrollEnabled = true;
    
        }
    }
    
        13
  •  0
  •   Daniel Williams    5 年前

    我只想在scrollview中的某个UIView是滑动过程中触摸的来源时禁用滚动。要将UIView移到UIScrollView之外,需要进行相当多的重构,因为我们有一个复杂的视图层次结构。

    cancelsTouchesInView 它阻止了UIScrollView的泛感觉激活。

    这是一个有点'黑客',但这是一个超级容易的变化,如果你使用的是一个锡伯或故事板,所有你需要做的是拖动鼠标的手势到子视图的问题。