代码之家  ›  专栏  ›  技术社区  ›  rano

UITableView:以编程方式滚动内容视图

  •  0
  • rano  · 技术社区  · 16 年前

    嗨,我正在尝试转发从uiview接收到的触摸,uiview在uitableview前面。但是这样我就不能再让桌子滚动了( see here )

    所以现在我正在尝试以编程方式使TableView滚动,我正在查看 setContentOffset:animated: scrollRectToVisible:animated: 只有第一个成功。
    下面是我在一个类中的代码,该类是UITableView的子类:

    - (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
        NSLog(@"BEGTB");
        //previousXPan = 0.0;
    
        UITouch * touch = [touches anyObject];
        CGPoint tPoint = [touch locationInView:self]; 
        previousYPan = tPoint.y;
    
        [super touchesBegan:touches withEvent:event];
        //
        //[super touchesShouldBegin:touches withEvent:event inContentView:self];
        //[[self nextResponder] touchesBegan:touches withEvent:event];
    }
    
    - (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{
        UITouch * touch = [touches anyObject];
        CGPoint tPoint = [touch locationInView:self]; 
    
    
        NSLog(@"MOVTB");
        NSLog(@"BOUNDZ %f, %f, %f, %f", self.bounds.origin.x, self.bounds.origin.y, self.bounds.size.height, self.bounds.size.width);
        NSLog(@"CONTENT SIZE  %f, %f",  self.contentSize.height, self.contentSize.width);
    
        CGRect rc = [self bounds];
        NSLog(@"%f %f", rc.size.height, rc.size.width);
        CGRect newRect = CGRectMake(rc.origin.x, rc.origin.y + self.contentSize.height, self.contentSize.width, fabs(tPoint.y - previousYPan));
        NSLog(@"BOND RECT %f, %f, %f, %f", rc.origin.x, rc.origin.y, rc.size.height, rc.size.width);
        NSLog(@"NEW RECT %f, %f, %f, %f", newRect.origin.x, newRect.origin.y, newRect.size.height, newRect.size.width);
        //[self scrollRectToVisible:newRect animated:YES];
        NSLog(@"Content OFFSET %f",tPoint.y - previousYPan);
        [self setContentOffset:CGPointMake(rc.origin.x,(tPoint.y - previousYPan) *2.0 )animated:YES];
        previousYPan = tPoint.y;
        //[super touchesMoved:touches withEvent:event];
        //[[self nextResponder] touchesMoved:touches withEvent:event];
    }
    

    但结果是真正的滞后和马车。有更好的主意吗?

    1 回复  |  直到 16 年前
        1
  •  0
  •   rano    16 年前

    我几乎找到了一个合适的解决方案(它不像普通的滚动,而是…)。

    首先,我确定Y轴上表视图内容区域的最大和最小像素量(ContentSize的高度 当视图已完全加载时 )

    我检查移动增量完成,但不参考触摸在表视图中的位置!我必须在覆盖它的顶层uiview上检查它,因为当您更改表的内容偏移量时,您会动态地更改其维度,并且您可以结束拥有 加速度效应 .

    下面是一些代码:

    - (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{
        UITouch * touch = [touches anyObject];
    
        CGPoint tPoint = [touch locationInView:[viewController draggableAreaView]];
    
    
    
        CGRect rc = [self bounds];
    
    
        float totalOS = tPoint.y - previousYPan;
        if ((contentOffSetY >= minY && contentOffSetY <= maxY) ||
            (contentOffSetY < minY - 5 && totalOS < 0) ||
            (contentOffSetY > maxY + 5 && totalOS > 0))
        {
    
            if (totalOS > 0)
                totalOS += OFFSET;
            else if (totalOS < 0)
                totalOS -= OFFSET;
            [self setContentOffset:CGPointMake(rc.origin.x,self.contentOffset.y + totalOS)animated:NO];
    
        }
        else /*if (contentOffSetY < minY - 5 && totalOS < 0) */
        {
            [self resetOffset];
        }
        previousYPan = tPoint.y; 
    
    }
    
    - (void)resetOffset{
    
        CGRect rc = [self bounds];
        if(contentOffSetY < minY)
        {
            [self setContentOffset:CGPointMake(rc.origin.x, minY + 50)animated:YES];
        }
        else if (contentOffSetY > maxY)
        {
            [self setContentOffset:CGPointMake(rc.origin.x, maxY - 50)animated:YES];
        }
    }
    

    更多提示:

    • 这里,DraggalLeareView是顶部的uiView,从中我可以得到一个“绝对”位置。
    • 偏移量是定义为增量的常量 线性地 再冷却的速度(没有它 touchesMoved: 多次调用,每次只提供一个像素的相对运动)
    • , minY maxY 是预先计算的极限值(为了计算它们,我计算了表中所有单元格的最大高度和可见内容视图的最小高度)
    • 我增加了一些位移 米尼 梅西 为了使动画更清晰可见
    推荐文章