I am trying to set NSLayoutConstraint
within each of my custom cells (inherited from UITableViewCell
), rather than specifying them in a UIViewController
to avoid cluttering it by exposing the constraints for each cell type.
The problem is that I could not find an appropriate part of the cell's lifecycle to create the layout constraints (I tried layoutSubviews()
and awakeFromNib()
), but they all get called too early in the cell's lifecycle, when its superview
has not been defined yet - it results in this error:
Constraint must contain a first layout item
Since UITableViewCell
does not have the viewDidLoad()
method like the UIViewController
, how is it possible to define the layout constraints within the cell?
layoutSubviews()
of the custom UITableViewCell
:
- (void) layoutSubviews {
self.translatesAutoresizingMaskIntoConstraints = false;
[[NSLayoutConstraint constraintWithItem: self.attributeNameLabel
attribute: NSLayoutAttributeLeading
relatedBy: NSLayoutRelationEqual
toItem: self.contentView
attribute: NSLayoutAttributeLeading
multiplier: 1
constant: 3] setActive:true];
[[NSLayoutConstraint constraintWithItem: self.attributeNameLabel
attribute: NSLayoutAttributeTop
relatedBy: NSLayoutRelationEqual
toItem: self.contentView
attribute: NSLayoutAttributeTop
multiplier: 1
constant: 3] setActive:true];
[[NSLayoutConstraint constraintWithItem: self.attributeNameLabel
attribute: NSLayoutAttributeRight
relatedBy: NSLayoutRelationEqual
toItem: self.contentView
attribute: NSLayoutAttributeRight
multiplier: 1
constant: 3] setActive:true];
[[NSLayoutConstraint constraintWithItem: self.attributeNameLabel
attribute: NSLayoutAttributeBottom
relatedBy: NSLayoutRelationEqual
toItem: self.contentView
attribute: NSLayoutAttributeBottom
multiplier: 1
constant: 3] setActive:true];
}
Example initialization in UIViewController
:
- (UITableViewCell *)tableView:(UITableView *)view cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell;
if (indexPath.row % 2 == 0) {
cell = [[CustomCell1 alloc] init];
} else if (indexPath.row % 2 == 1) {
cell = [[CustomCell2 alloc] init];
} else if (...) {
...
}
return cell;
}