UITableViewCell具有复杂的布局,可变的行高和自动布局

时间:2013-10-25 08:53:40

标签: ios objective-c ipad uitableview autolayout

我正在处理一个处理纵向和横向方向的iPad应用程序。 我有一个tableview显示具有复杂(?)布局的单元格,它可以有不同的高度。

以下是纵向应该是什么样子的屏幕截图(= 768 pts witdh,应该会产生435点的高度) Portrait simulation

以下是横向视图的截图(= 1024 pts宽度,应该会产生526 pts的高度) Landscape simulation

为了简化布局,我们只保留第一张图片。

布局

我有1张图像应该保持其比例,同时增加/减少设备旋转:      在肖像= 256宽* 342高度      在横向= 341,333宽* 456高度 我有黄色视图(应该有8个点的边距和每个方向16个点的填充),包含标题(蓝色)和潜在的多行文本内容(粉红色)。 笔记:       - 粉红色标签可能完全是空的。       - 黄色视图将被纹理化,这就是为什么需要它,它不仅仅是一个解决问题的额外视图。

内容视图(UITableViewCell的子级)约束

V:|-(0)-[UIImageView]   (Names: '|':UITableViewCellContentView)>",   // Top margin (0 pts) of the image
H:|-(0)-[UIImageView]   (Names: '|':UITableViewCellContentView)>",   // Left margin (0 pts) of the image
V:[UIImageView]-(8)-[UIView]>",     // Vertical space (8 pts) between the image and the yellow view (i.e. top margin of the yellow view)
H:|-(8)-[UIView]   (Names: '|':UITableViewCellContentView)>",   // Left margin (8 pts) of the yellow view
H:[UIView]-(8)-|   (Names: '|':UITableViewCellContentView)>",   // Right margin (8 pts) of the yellow view
V:[UIView]-(8)-|   (Names: '|':UITableViewCellContentView)>",   // Bottom margin (8 pts) of the yellow view

黄色视图约束

V:|-(16)-[UILabel:Blue]   (Names: '|':Yellow View )>",   // Top margin (16 pts) of the blue label (i.e. top padding of the yellow view)
H:|-(16)-[UILabel:Blue]   (Names: '|':Yellow View )>",   // Left margin (16 pts) of the blue label
V:[UILabel:Blue]-(>=16)-|   (Names: '|':Yellow View )>",   // Bottom margin (>= 16 pts) of the blue label
H:[UILabel:Blue]-(NSSpace(8))-[UILabel:Pink]>",   // Horizontal space between blue and pink labels
V:[UILabel:Pink]-(16)-|   (Names: '|':Yellow View )>",   // Top margin (16 pts) of the pink label
H:[UILabel:Pink]-(16)-|   (Names: '|':Yellow View )>",   // Right margin (16 pts) of the pink label
V:|-(16)-[UILabel:Pink]   (Names: '|':Yellow View )>",   // Bottom margin (16 pts) of the pink label

约束说明

  • 在Interface Builder中,我为图像设置了一个占位符固有大小为256宽* 342高度(我们稍后会看到我根据设备方向动态设置实际大小约束)
  • 蓝色标签的水平内容压缩优先级为751
  • 图像的垂直拥抱优先级为1
  • 黄色视图和粉红色标签的垂直拥抱优先级为1000

Interface Builder测试

如果我增加单元格高度,图像会变形并且高度会增加,而底部白色的黄色视图会变形。所以一切都很好(因为我们无法在IB中设置比例约束来模仿图像的保持率增长。)

代码

available on GitHub

结果

如果我以纵向方式启动应用程序,则单元格非常完美。粉红色标签显示在2行上,每个尺寸和间距都得到充分尊重/计算! 如果然后我旋转到横向,图像不会增长,而是黄色视图和粉红色标签正在增长...这是一个截图: Landscape version when rotating from portrait

现在如果我在横向上启动应用程序,细胞也是完美的。图像尺寸合适(351点宽(圆形值)* 456点高)等... 如果然后我旋转到肖像它会使应用程序崩溃...使用以下输出:

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:0xa3d9dd0 V:|-(0)-[UIImageView]   (Names: '|':UITableViewCellContentView )>",
    "<NSLayoutConstraint:0xa3d9e00 V:[UIView]-(8)-|   (Names: '|':UITableViewCellContentView )>",
    "<NSLayoutConstraint:0xa3d9e60 V:[UIImageView]-(8)-[UIView]>",
    "<NSLayoutConstraint:0xa3dd9b0 V:[UIImageView(456)]>",
    "<NSAutoresizingMaskLayoutConstraint:0xa3de670 h=--& v=--& V:[UITableViewCellContentView(431)]>"
)

Will attempt to recover by breaking constraint 
<NSLayoutConstraint:0xa3dd9b0 V:[UIImageView(456)]>

注意:UIView是黄色视图

非常感谢你的帮助(或者至少阅读; - )

PS:我昨天在开发论坛上发布了相同的问题,并会在此发布任何进展。 DevForum discussion link

1 个答案:

答案 0 :(得分:1)

我下载了您的示例项目并运行它。您似乎在代码中有一些问题,但到目前为止最明显的一个问题是当自动旋转发生时您没有在表视图上调用reloadData - 这是为了让表视图重新计算所必需的单元格高度(并根据更改重新布置每个可见单元格)。

将以下方法添加到ARJProcedureListViewController.m文件中:

- (void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration
{
    [super willRotateToInterfaceOrientation:toInterfaceOrientation duration:duration];

    [self.tableView reloadData];
}

我看到约束冲突仍然记录在控制台上,这意味着至少有一个约束是错误的(你可能过度约束了某些视图)。