1. 程式人生 > >iOS 8自適應高度單元格問題

iOS 8自適應高度單元格問題

iOS 8 中通過UITableViewAutomaticDimension 常量支援自適應高度的單元格(iOS 7 就要麻煩得多)。但是在實際應用中,我們需要注意以下幾個問題:

1、 設定好模板單元格的自動佈局
模板單元格中,subviews的自動區域性必須要能夠把單元格撐滿。也就是說,iOS 必須能夠通過內容的自動佈局約束計算出 cell 的高。以下面的單元格為例:

cell中有上下兩個 Label,上面的Label只有一行文字(lines為1),所以高度在執行時不會改變,但下面的Label是多行文字(lines為0),執行時其高度會根據文字內容自動增長。
左圖中的自動佈局是正確的,因此執行時單元格能夠自適應高度。這是因為iOS能夠根據cell的contentView中的各個子View計算出cell的正常高度,計算方式為:
cell 高度 = 第1個Label的top+第1個Label高度+第2個Label的top+第2個Label高度(根據內容自動計算)+第2個Label的bottom

但是當我們將第2個Label的top約束(或者bottom約束)刪除,如右圖所示,我們已經把圖中紅框所示位置的約束刪除了,則iOS無法計算單元格的高度了。因為上述公式中的一個變數缺失。這樣執行時表格中的所有cell都是固定高度,cell之間會發生重疊,同時控制檯會報錯:

Warning once only: Detected a case where constraints ambiguously suggest a height of zero for a tableview cell’s content view. We’re considering the collapse unintentional and using standard height instead.

2、 在viewDidLoad中設定tableView

接下來在viewDidLoad中設定tableView:
tableView.rowHeight = UITableViewAutomaticDimension
self.tableView.estimatedRowHeight = 100;

第一句的作用如前面所述,是開啟iOS 8的單元格的自適應高度特性。第二句程式碼也是同樣的功能,estimatedRowHeight讓你提供一個預先估計cell的高度值,這個值根本可以亂設(只要不為0),但如果你不寫這句,或者將estimatedRowHeight屬性設定為0,則iOS 8的單元格自動高度特性也不會生效。

3、 heightForRowAtIndexPath方法和estimatedHeightForRowAtIndexPath方法
開啟了iOS 8 的單元格自動高度特性後,這兩個方法就不需要了,或者簡單地返回一個UITableViewAutomaticDimension常量:
override func tableView(tableView: UITableView, heightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat {
return UITableViewAutomaticDimension
}
override func tableView(tableView: UITableView, estimatedHeightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat {
return UITableViewAutomaticDimension
}
當然,完全刪除這兩個方法也沒有關係。