UITableView:根据屏幕大小设置表格标题视图高度

Ala*_*din 9 objective-c uitableview ios autolayout

我有一个表视图,其中包含通过同一xib中的接口构建器创建的表头视图.我想根据屏幕大小设置标题的高度,例如屏幕高度的50%.

这是我在iPhone 4s上获得的静态高度:

iPhone 4s中的Tableview标题

这就是我在iPhone 6上得到的:

iPhone 6中的Tableview标题

请注意,标头的内容是静态的.

我无法使用自动布局设置标题的约束.我试图根据表视图的高度设置高度约束,但在界面构建器中似乎不可能.控制拖动不起作用.我无法将标题从标题拖到表格视图甚至标题本身.

在此输入图像描述

如何根据屏幕尺寸设置标题的高度?

hen*_*nes 9

遗憾的是,无法使用自动布局调整表标题视图的大小.您可以对标题内的元素使用自动布局,但必须通过显式设置其框架来指定标题的大小.如果标题的高度是静态的并且在编译时已知,则可以使用IB.但是,如果高度是动态的或取决于设备(如您的情况),则必须在代码中设置它.

一个非常灵活的解决方案是创建自定义子类UITableView并在layoutSubviews方法中调整标题的框架.这样,在调整表视图大小时,会自动调整标题的大小.但是,您必须小心,只有在实际需要更改时才重新应用标头的帧以避免无限循环.

这是Objective-C中的样子:

@interface MyTableView : UITableView
@end

@implementation MyTableView : UITableView

- (void)layoutSubviews {
    [super layoutSubviews];

    if (self.tableHeaderView) {
        UIView *header = self.tableHeaderView;
        CGRect rect = CGRectMake(0, 0, self.bounds.size.width,
                                 self.bounds.size.height / 2);

        // Only adjust frame if needed to avoid infinite loop
        if (!CGRectEqualToRect(self.tableHeaderView.frame, rect)) {
            header.frame = rect;

            // This will apply the new header size and trigger another
            // call of layoutSubviews
            self.tableHeaderView = header;
        }
    }
}

@end
Run Code Online (Sandbox Code Playgroud)

Swift版本看起来像这样:

class MyTableView: UITableView {

    override func layoutSubviews() {
        super.layoutSubviews()

        if let header = tableHeaderView {
            let rect = CGRectMake(0, 0, bounds.size.width, bounds.size.height / 2)

            // Only adjust frame if needed to avoid infinite loop
            if !CGRectEqualToRect(header.frame, rect) {
                header.frame = rect

                // This will apply the new header size and trigger 
                // another call of layoutSubviews
                tableHeaderView = header
            }
        }
    }

}
Run Code Online (Sandbox Code Playgroud)

请注意,上面的代码段使用表视图的边界而不是屏幕大小来计算标题大小.

更新:请注意,有时layoutIfNeeded在设置tableHeaderView属性后需要额外调用.我遇到了一个问题,在标题视图上方绘制了节标题而没有调用layoutIfNeeded.