UITableView查找Section标题的位置?

时间:2012-03-18 15:03:08

标签: iphone objective-c ios uitableview uigesturerecognizer

我试图在桌面视图上滑动时找出swipeGesture的位置。 在滑动动作中,我看到很多人这样做:

CGPoint location = [recognizer locationInView:tableView];
NSIndexPath* indexPath = [tableView indexPathForRowAtPoint:location];
UITableViewCell* cell = [tableView cellForRowAtIndexPath:indexPath];

但我的tableView由没有单元格的节标题组成。因此,索引路径方法返回nil。有没有办法找到Section标题的位置?他们没有这种方法,但indexPathForSectionAtPoint:之类的东西将是我正在寻找的东西。 如果有人知道如何做到这一点,将不胜感激。

谢谢,

3 个答案:

答案 0 :(得分:1)

您已拥有locationindexPath 现在,要获取单元格(及其数据),请使用indexPath.row,如您的示例所示 要获取该部分(包含或不包含单元格),请使用indexPath.section

如果点location下方没有行indexPathForRowAtPoint:将返回nil,那么这就是预期的行为。

章节标题并不是真正意义上的交互视图。相反,它们是标题。 UITableView旨在响应与其行的交互。

也许解决此问题的一种方法是更改​​您的数据结构,以便您在部分标题中显示的内容真正存在于表格视图行中。

另一种方法是使用节标题的UIView并让它响应滑动手势。 (确保使用super将手势传递到表格视图。)

答案 1 :(得分:1)

结束做类似的事情,但在表格部分标题上点击(而不是滑动)。

可能有更优雅的方法可以做到这一点,但我基本上将手势的view转换为tableView坐标空间。然后我遍历每个节标题的CGRect以查看它是否与手势原点相交。

func tableView(tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let cell = tableView.dequeueReusableCellWithIdentifier("header") as! HeaderCell
    let tapHeader = UITapGestureRecognizer(target: self, action: "tappedOnHeader:")
    tapHeader.delegate = self
    tapHeader.numberOfTapsRequired = 1
    tapHeader.numberOfTouchesRequired = 1
    cell.contentView.addGestureRecognizer(tapHeader)
    return cell
}

func tappedOnHeader(gesture:UIGestureRecognizer){
    if let cellContentView = gesture.view {
        let tappedPoint = cellContentView.convertPoint(cellContentView.bounds.origin, toView: tableView)
        for i in 0..<tableView.numberOfSections {
            let sectionHeaderArea = tableView.rectForHeaderInSection(i)
            if CGRectContainsPoint(sectionHeaderArea, tappedPoint) {
                print("tapped on section header:: \(i)")
            }
        }
    }
}

在另一个教程项目上创建一个git分支作为工作示例:

https://github.com/ThornTechPublic/HorizontalScrollingCollectionView/tree/sectionHeaderTap

答案 2 :(得分:-1)

//Sublcass a header footer view and in .h file declare this protocol
@protocol MyProtocol <NSObject>

-(void)userTappedView:(UITableViewHeaderFooterView *)view atPoint:(CGPoint)point;

@end

//in same .h file add this
@property (weak, nonatomic) id <MyProtocol> delegate;

//In same subclass .m file do this
-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {

    [super touchesEnded:touches withEvent:event];

    UITouch *touch = [[event allTouches] anyObject];
    CGPoint point = [touch locationInView:self];

    [self.delegate userTappedView:self atPoint:point];
}

//In controller containing tableview, conform to 'MyProtocol' like this
-(void)userTappedView:(UITableViewHeaderFooterView *)view atPoint:(CGPoint)point {

    NSNumber *value = [self sectionForUserSelectionInTableView:self.tableView
                                               atTouchLocation:point
                                            inHeaderFooterView:view];

    if (!value) {
        return;
    }

    NSUInteger tappedSection = value.integerValue;

}

-(NSNumber *)sectionForUserSelectionInTableView:(UITableView *)tableView
                                atTouchLocation:(CGPoint)location
                             inHeaderFooterView:(UITableViewHeaderFooterView *)view {

    CGPoint point = [tableView convertPoint:location
                                   fromView:view];

    for (NSInteger i = 0; i < [tableView numberOfSections]; i++) {
        CGRect rect = [tableView rectForHeaderInSection:i];
        if (CGRectContainsPoint(rect, point)) {
            return @(i);
        }
    }

    return nil;
}