Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Fit UIView height to its content with AutoLayout

I'm using iOS 6 AutoLayout feature with Masonry DSL to arrange views within UITableViewCell. This is the layout arrangements that I want to achieve:

Desired UITableViewCell layout

The containerView is a virtual container that should dynamically adapt its size to fit its content. With my current implementation, this is what I got instead:

Current layout arrangement result

It seems that containerView did get vertically centered correctly, but it has zero width and height, hence not showing up properly. How can I instruct containerView to fit its size to its content? Code snippets are attached below.

Thanks!

UITableViewCell initializer

- (id)initWithReuseIdentifier:(NSString *)reuseIdentifier
{
    if (self = [super initWithStyle:UITableViewCellStyleDefault reuseIdentifier:reuseIdentifier]) {
        self.titleLabel = [[UILabel alloc] init];
        self.titleLabel.font = [UIFont boldSystemFontOfSize:[UIFont smallSystemFontSize]];
        self.titleLabel.text = @"ノートタイトル";

        self.coverImage = [[UIView alloc] init];
        self.coverImage.backgroundColor = [UIColor carrotColor];

        self.avatarImage = [[UIView alloc] init];
        self.avatarImage.backgroundColor = [UIColor emerlandColor];

        self.authorLabel = [[UILabel alloc] init];
        self.authorLabel.font = [UIFont systemFontOfSize:[UIFont smallSystemFontSize]];
        self.authorLabel.text = @"著者の名前";

        self.containerView = [[UIView alloc] init];
        self.containerView.backgroundColor = [UIColor lightGrayColor];
        [self.containerView addSubview:self.titleLabel];
        [self.containerView addSubview:self.avatarImage];
        [self.containerView addSubview:self.authorLabel];

        [self.contentView addSubview:self.containerView];
        [self.contentView addSubview:self.coverImage];

        self.selectionStyle = UITableViewCellSelectionStyleNone;
        [self updateConstraintsIfNeeded];
    }

    return self;
}

UITableViewCell updateConstraints

- (void)updateConstraints
{
    [super updateConstraints];

    [self.coverImage mas_makeConstraints:^(MASConstraintMaker *make) {
        make.left.equalTo(self.contentView).with.offset(20);
        make.top.equalTo(self.contentView).with.offset(5);
        make.bottom.equalTo(self.contentView).with.offset(-5);

        make.width.equalTo(self.coverImage.mas_height).multipliedBy(0.75);
    }];

    [self.containerView mas_makeConstraints:^(MASConstraintMaker *make) {
        make.left.equalTo(self.coverImage.mas_right).with.offset(10);
        make.centerY.equalTo(self.contentView);
    }];

    [self.titleLabel mas_makeConstraints:^(MASConstraintMaker *make) {
        make.left.equalTo(self.containerView);
        make.top.equalTo(self.containerView);
    }];

    [self.avatarImage mas_makeConstraints:^(MASConstraintMaker *make) {
        make.top.equalTo(self.titleLabel.mas_bottom).with.offset(5);
        make.left.equalTo(self.titleLabel);

        make.width.equalTo(@20);
        make.height.equalTo(@20);
    }];

    [self.authorLabel mas_makeConstraints:^(MASConstraintMaker *make) {
        make.left.equalTo(self.avatarImage.mas_right).with.offset(5);
        make.centerY.equalTo(self.avatarImage);
    }];
}
like image 659
Andree Avatar asked Mar 13 '14 02:03

Andree


1 Answers

I found out the solution to my own question. Apparently, in order for containerView to resize itself dynamically, we have to make sure that each elements within are connected rigidly to each other and the edges of the superview (i.e. containerView). For example, in VFL it should be something like this: "V:|-10-[child1]-5-[child2]-5-|"

So in my case, I add a new constraint make.bottom.equalTo(self.containerView) to avatarImage and now the superview knows how to height itself!

like image 197
Andree Avatar answered Sep 28 '22 21:09

Andree