0

I am using collectionview in UITableViewCell and I need to change height of collectionview to show all content. As a result, I monitor content size of collectionview, update that height and reload cell.

[self.cvTag addObserver:self forKeyPath:@"contentSize" options:NSKeyValueObservingOptionNew context:nil];

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary  *)change context:(void *)context
{
    float newHeight = self.cvTag.collectionViewLayout.collectionViewContentSize.height;

    if (self.verticalConstraintTag.constant != newHeight) {
        self.verticalConstraintTag.constant = newHeight;

        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, 1 * NSEC_PER_SEC), dispatch_get_main_queue(), ^{
            dispatch_async(dispatch_get_main_queue(), ^{
                if (self.reloadBlock)
                self.reloadBlock();

                self.reloadBlock = nil;
            });
        });
    }
}

This is where I set my data in cell

- (void)setData:(Attachment *)attachment andReload:(void (^)(void))reloadAction {
    self.reloadBlock = reloadAction;
    [super setData:attachment];
    [self setUpTag];
}

This is how I create cell.

DocumentDetailCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];

if (!cell)
    cell = [DocumentDetailCell loadFromNib];

[cell setW:CGRectGetWidth(self.view.frame)];
DocumentsCollection *dc = self.documents[indexPath.section - 1];
[cell setTag:indexPath.row];
[cell setSelectionStyle:UITableViewCellSelectionStyleNone];
[cell setData:dc.attachments[indexPath.row] andReload:^{

    [tableView reloadData];
}];
[cell hideOrUnhideSeparator:(indexPath.row ==  dc.attachments.count - 1)];
return cell;

The problem is that after I reload, that content size of collection view change again! As a result, it become a loop and it never end. I have tried with reloadRow and beginUpdate/EndUpdate. It is not quite okay too. How shall I do?

KSR
  • 1,699
  • 15
  • 22
Khant Thu Linn
  • 5,905
  • 7
  • 52
  • 120
  • Consider calculating the size of the content instead? I did this with a [tableView and multiple labels](http://stackoverflow.com/questions/41439786/aligning-multiple-runtime-generated-uilabels-in-a-uitableview) worked quite well, but maybe you need to think more since you use collectionView and not label – Ben Ong Jan 11 '17 at 02:58
  • Thanks. Look like I might need to try that. – Khant Thu Linn Jan 11 '17 at 02:59
  • But I totally don't understand why it loop. Is there a way to break that loop? – Khant Thu Linn Jan 11 '17 at 03:00
  • When you call `reloadData`, the `tableView` will call its `delegate` for `rowAtIndexPath`. So calling `reloadData` inside `rowAtIndexPath` basically triggers an infinite recursion – Ben Ong Jan 11 '17 at 03:03
  • The problem is why observer for "contentSize" keep calling after I reloadData. I thought it should stop already since all are layout properly. – Khant Thu Linn Jan 11 '17 at 03:05
  • Have you tried logging your `contentSize`? It may actually have changed with each reload since I do not know how UITableView` and `UICollectionView` actually calculates that value – Ben Ong Jan 11 '17 at 03:08
  • I also came across this post on [Resizing UITableView to fit content](http://stackoverflow.com/questions/2595118/resizing-uitableview-to-fit-content?noredirect=1&lq=1) , might help – Ben Ong Jan 11 '17 at 03:09

0 Answers0