跟踪 UITableViewCell 子视图的坐标 [英] Track coordinates of UITableViewCell subview

查看:27
本文介绍了跟踪 UITableViewCell 子视图的坐标的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想在 UITableviewCell 的子视图到达屏幕上的某个点时触发一个事件,例如当它的 origin.y 达到 44 点时.知道它到达那个点时是向上还是向下滚动也是很好的.我在子视图的框架上玩 KVO 但这似乎固定在单元格上所以没有改变.这个任务可以吗?

I would like to fire an event when the subview of a UITableviewCell reaches a certain point on the screen, say for example when its origin.y reaches 44 points. It would also be nice to know if it was being scrolled up or down when it reached that point. I was playing with KVO on the frame of the subview but this seems fixed to the cell so no changes with that. Is this task possible?

推荐答案

UITableViewCell 的垂直位置由其 frame 属性定义,该属性表示该单元格在其超视图 UITableView 中的位置和大小.通常,每次 UITableView 从其委托中请求单元格以获取特定索引路径时,单元格的 frame 属性仅更改一次.就是这样,UITableView 获取一个单元格,将其放置在自身中,并且该单元格只是保持不变,直到存储在 UITableView 的 bounds 属性中的矩形不再包含存储在 frame 属性中的矩形那个细胞.在这种情况下,UITableView 将该单元格标记为隐藏并将其放入可重用单元格池中.

Vertical position of UITableViewCell is defined by its frame property, which represents position and size of that cell within its superview, UITableView. Typically, the frame property of the cell is changing only once for every time that UITableView requests a cell from its delegate for specific index path. That's it, UITableView gets a cell, places it in itself and that cell just lays there unchanged until rectangle stored in bounds property of UITableView ceases to include rectangle stored in the frame property of that cell. In that case UITableView marks that cell as hidden and places it into the pool of reusable cells.

由于滚动的过程本质上不是子视图的重新定位——它只是移动 UITableView 的 bounds 视口的一种奇怪的错觉——不断观察 UITableViewCell 的属性是没有意义的.

Since the process of scrolling in essence is not a repositioning of subviews – it is merely a curious illusion of shifting a bounds viewport of UITableView – constant observing of UITableViewCell's properties are pointless.

此外,UITableViewCell 的子视图的 frame 属性还表示该子视图在其容器 UITableViewCell 中的位置和大小.滚动时也不会改变.

Moreover, the frame property of subview of UITableViewCell also represents a position and size of that subview within its container, UITableViewCell. It is also will not change on scroll.

需要观察 UITableView bounds 属性的变化,顺便也用 contentOffset 表示.UITableView 恰好是 UIScrollView 的一个子类,所以你可以使用它的委托方法,比如 -scrollViewDidScroll:,就像这个简单的例子:

You need to observe changes in UITableView bounds property, which is also represented by contentOffset by the way. UITableView happens to be a subclass of UIScrollView, so you can use its delegate methods, such as -scrollViewDidScroll:, like in this simple example:

- (void)scrollViewDidScroll:(UIScrollView *)scrollView
{
    UITableView *tableView = (UITableView *)scrollView;

    // current position
    CGFloat currentY = tableView.bounds.origin.y;

    // current inset
    CGFloat currentInset = tableView.contentInset.top;

    // trigger line position
    CGFloat triggerY = currentInset + currentY + kYourTriggerPosition;

    // nice visual mark
    UIView *line = [tableView viewWithTag:88];

    if (!line) {
        line = [[UIView alloc] initWithFrame:CGRectZero];
        line.tag = 88;
        line.backgroundColor = [UIColor redColor];
        [tableView addSubview:line];
    }

    line.frame = CGRectMake(0, triggerY, tableView.bounds.size.width, 1);

    // determine scroll direction
    BOOL scrollingUp = currentY > self.previousY;

    // all visible cells
    NSArray *visibleCells = tableView.visibleCells;

    [visibleCells enumerateObjectsUsingBlock:^(UITableViewCell *cell, NSUInteger idx, BOOL *stop) {

        // subview
        UIView *subview = [cell viewWithTag:kYourSubviewTag];

        // subview frame rect in UITableView bounds
        CGRect subviewRect = [subview convertRect:subview.frame toView:tableView];

        // trigger line within subview?
        BOOL triggered = (CGRectGetMinY(subviewRect) <= triggerY) && (CGRectGetMaxY(subviewRect) >= triggerY);

        if (triggered) {
            NSIndexPath *indexPath = [tableView indexPathForCell:cell];
            NSLog(@"moving %@, triggered for cell at [%2d:%2d]", @[@"down", @"up"][scrollingUp], indexPath.section, indexPath.row);
            [tableView selectRowAtIndexPath:indexPath animated:NO scrollPosition:UITableViewScrollPositionNone];
        }
    }];

    // save current position for future use
    self.previousY = currentY;
}

这篇关于跟踪 UITableViewCell 子视图的坐标的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆