我在故事板中创建了一个UITableViewCell,并使用自动布局来定位所有内容,希望让iOS 8自动为我确定单元格高度。我的单元格有两个标签,其中一个是多行标签,首选宽度为自动。
作为参考,单元格的高度为208,但高度设置为“默认”。表格视图的行高设置为208。
在视图中加载,我运行以下代码:
self.tableView.estimatedRowHeight = 100;
self.tableView.rowHeight = UITableViewAutomaticDimension;
这在我第一次显示单元格时工作正常,一切正常显示。问题是如果一个单元被重用,它会不正确地拉伸。基于this post,我注意到我可能需要在cellForIndexPath中运行以下代码:
[cell setNeedsUpdateConstraints];
[cell updateConstraintsIfNeeded];
然而,当我添加该代码时,我收到消息:
Unable to simultaneously satisfy constraints.
Probably at least one of the constraints in the following list is one
you don't want. Try this: (1) look at each constraint and try to figure
out which you don't expect; (2) find the code that added the unwanted
constraint or constraints and fix it. (Note: If you're seeing
NSAutoresizingMaskLayoutConstraints that you don't understand, refer
to the documentation for the UIView property
translatesAutoresizingMaskIntoConstraints)
(
[...]
"<NSLayoutConstraint:0x7fd108dd1ce0 UITableViewCellContentView:0x7fd108d03d00.height ==>"
)
在这种特殊情况下,我注意到我的<tableViewCell>
没有<rect>
标记,这就是它输出height==
的原因。 (有关<rect>
标记下方的详情...)
<rect>
代码这似乎与<rect>
中<tableViewCell>
标记的奇怪行为有关。具体来说,它可能存在也可能不存在,如果确实存在,其高度可能会设置为奇怪的值,这可能会引起问题。
以下是我注意到的一些奇怪行为......
<tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" id="VVy-eG-5ZD">
<autoresizingMask key="autoresizingMask"/>
<tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="VVy-eG-5ZD" id="o4d-7b-psa">
<autoresizingMask key="autoresizingMask"/>
</tableViewCellContentView>
</tableViewCell>
在“大小”检查器中将“默认”显示为行高。
注意没有<rect>
标记。
<tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" id="SxR-MB-xdu">
<rect key="frame" x="0.0" y="0.0" width="600" height="44"/>
<autoresizingMask key="autoresizingMask"/>
<tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="SxR-MB-xdu" id="JDB-Ys-OoE">
<autoresizingMask key="autoresizingMask"/>
</tableViewCellContentView>
</tableViewCell>
在“大小”检查器中将“默认”显示为行高。
注意如何有一个<rect>
标签,并选择44作为其高度。 44恰好是Size Inspector中表视图的行高的默认值。
细胞在视觉上变得更大,但它们的xml不受影响。
作为参考,以下是TABLE VIEW的xml之前的样子:
<tableView key="view" clipsSubviews="YES" contentMode="scaleToFill" alwaysBounceVertical="YES" dataMode="prototypes" style="plain" separatorStyle="default" rowHeight="44" sectionHeaderHeight="22" sectionFooterHeight="22" id="qea-mf-mRA">
<rect key="frame" x="0.0" y="0.0" width="600" height="600"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
......以下是它的样子:
<tableView key="view" clipsSubviews="YES" contentMode="scaleToFill" alwaysBounceVertical="YES" dataMode="prototypes" style="plain" separatorStyle="default" rowHeight="100" sectionHeaderHeight="22" sectionFooterHeight="22" id="qea-mf-mRA">
<rect key="frame" x="0.0" y="0.0" width="600" height="600"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
唯一改变的是来自rowHeight="100"
的{{1}}。
即使表格视图的行高现在为100,我们仍然会在rowHeight="44"
标记中获得44高度:
<rect>
这会为<tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" id="wcV-YB-1eG">
<rect key="frame" x="0.0" y="0.0" width="600" height="44"/>
<autoresizingMask key="autoresizingMask"/>
<tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="wcV-YB-1eG" id="xM8-zX-Nrh">
<autoresizingMask key="autoresizingMask"/>
</tableViewCellContentView>
</tableViewCell>
标记添加新的rowHeight="55"
属性,但保持<tableViewCell>
不变:
<rect>
如果你在Size Inspector中查看Row Height属性,它现在显示为55,而不是“Default”。
这会创建一个<tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" rowHeight="55" id="wcV-YB-1eG">
<rect key="frame" x="0.0" y="0.0" width="600" height="44"/>
<autoresizingMask key="autoresizingMask"/>
<tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="wcV-YB-1eG" id="xM8-zX-Nrh">
<autoresizingMask key="autoresizingMask"/>
</tableViewCellContentView>
</tableViewCell>
标记:
<rect>
注意即使故事板使用大小类,因此一切都是600宽度,它仍然选择320宽度。另请注意,无论我们选择为iPhone还是Universal创建模板,我们都会得到相同的结果。
是否已创建<tableViewCell contentMode="scaleToFill" selectionStyle="blue" accessoryType="disclosureIndicator" hidesAccessoryWhenEditing="NO" indentationLevel="1" indentationWidth="0.0" reuseIdentifier="Cell" textLabel="2pz-XF-uhl" style="IBUITableViewCellStyleDefault" id="m0d-ak-lc9">
<rect key="frame" x="0.0" y="86" width="320" height="44"/>
<autoresizingMask key="autoresizingMask"/>
代码?
对于我的原始单元格,这是手动更改rect标记时发生的情况:
<rect>
标记输出:
<rect>
Unable to simultaneously satisfy constraints ...
"<NSLayoutConstraint:0x7fb51430b220 UITableViewCellContentView:0x7fb514309340.height ==>"
设置为较小的高度如果我将值设置为1到65之间的任何值,我会收到以下错误消息。
在这个测试中,我使用了:
<rect>
输出:
<rect key="frame" x="0.0" y="0.0" width="600" height="44"/>
Unable to simultaneously satisfy constraints ...
"<NSLayoutConstraint:0x7fe3104ce760 UITableViewCellContentView:0x7fe3104e00d0.height == 44>"
设置为较大的高度如果我将rect设置为65以上,它就不会向控制台输出任何内容。
在这个测试中,我使用了:
<rect>
除了不输出约束警告外,一切看起来都是正确的。
我将创建一个示例项目,很快就会显示这些问题。
答案 0 :(得分:0)
在完成动画时尝试添加:
[cell setNeedsUpdateConstraints];
[cell updateConstraintsIfNeeded];
[cell layoutIfNeeded];