如何在表视图中正确设置动态标题视图?

时间:2018-01-21 16:53:54

标签: ios swift uitableview autolayout uitableviewsectionheader

我需要一个部分的标题视图为UIImageView,并且UILabel位于其下方。一旦创建,图像视图的高度就不会改变,但标签中的文本可能会因某些用户操作而改变。我需要动态更新整个标题视图的高度(使用AutoLayout,而不是更改框架)。

我一直在检查一些帖子,例如this one,但我尝试的解决方案对我不起作用。当我更改标签中的文本时,标题视图的高度不会更新。

也许我需要了解它从一开始就如何运作。首先,我想清楚这一点:

  1. UIView中提供标题视图作为tableView(_:viewForHeaderInSection:)的子类,并将其作为UITableViewHeaderFooterView的子类提供并将其注册到表视图之间有什么区别?

  2. 标题视图中的子视图需要哪些约束才能具有动态高度?

  3. 我应该如何动态更新标题视图的高度?

2 个答案:

答案 0 :(得分:0)

我相信这很简单:

  1. 设置tableView

    tableView.estimatedSectionHeaderHeight = 63
    tableView.sectionHeaderHeight = UITableViewAutomaticDimension
    
  2. 实现自定义节标题并在委托方法中返回:

    override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    
        switch section {
        case 0:
            return sectionHeader
    
        default:
            fatalError("Unreachable code")
        }
    }
    
  3. 最后,如果在显示标题时标题部分中的内容发生变化,则在更改之后,您必须告诉tableView使用以下内容重绘自身:

    // method in the tableViewController
    func refreshTableAfterCellExpansion() {
        self.tableView.beginUpdates()
        self.tableView.setNeedsLayout()
        self.tableView.endUpdates()
    }
    

答案 1 :(得分:0)

您可能想要使用如下所示的功能。调整属性以适合您用于标签的字体和字体大小:

func handleEstimatedFrameForText(_ text: String) -> CGRect {
    let size = CGSize(width: 200, height: 1000)
    let options = NSStringDrawingOptions.usesFontLeading.union(.usesLineFragmentOrigin)
    return NSString(string: text).boundingRect(with: size, options: options, attributes: [NSAttributedStringKey.font: UIFont(name: "AvenirNext-Medium", size: 16) as Any], context: nil)
}

当您使用该方法设置标题的大小时,您希望使用此函数来获取文本添加后UILabel的高度,然后添加和填充类型{{ {1}}身高等。

在设置标题大小的方法中

UIImageView

您可能希望向 var height: CGFloat = 0 let headerMessage = messages[indexPath.item] if let labelText = headerMessage.text { let headerImageViewHeight: CGFloat = 80 /* ADD IN YOUR UIIMAGEVIEW HEIGHT */ height = self.handleEstimatedFrameForText(labelText).height + headerImageViewHeight return CGSize(width: view.frame.width, height: height) } else { return CGSize(width: view.frame.width, height: 200) /* DEFAULT SIZE */ } 添加额外的几个像素,因为某些字体需要额外的12个像素左右才能在所有设备上工作。试错。