开发者

Dynamic table view cell height in iphone using xcode 4

开发者 https://www.devze.com 2023-04-11 14:49 出处:网络
I have view controller which contains post details & table view. The table cells are custom. I have placed uilabel,uibutton & uitextview on cell. This table cell contains comments & replie

I have view controller which contains post details & table view. The table cells are custom. I have placed uilabel,uibutton & uitextview on cell. This table cell contains comments & replies of the post. So the table cell height is dynamic. If comment has replies then cell's height correctly displayed. But if comment doesn't have reply then table cell height is calculated wrongly. I want table cell & table view height should dynamic according to the cell's contents. My view controller conatins another view known as "content view" on which I have placed post details & my table view. Following is my image that will give you idea about my view . Below image is to get idea of view only.

Dynamic table view cell height in iphone using xcode 4

Here is my code

#define TABLE_CELL_HEIGHT 200.0f
#define ADD_VIEW_HEIGHT 30.0f
#define FONT_SIZE 24.0f
#define CELL_CONTENT_WIDTH 720.0f
#define CELL_CONTENT_MARGIN 50.0f
#define SectionHeight 50.0f
#define LEFT_MARGIN 25
#define RIGHT_MARGIN 25
#define TOP_MARGIN 35
#define BOTTOM_MARGIN 50
#define BOTTOM_FOOTER_MARGIN 32
#define DOC_WIDTH 768
#define DOC_HEIGHT 910

- (void)viewDidLoad
{

    [super viewDidLoad];
    [self createUserInterface];
    [self createCommentUserInterface];

    self.contentView.backgroundColor = SET_BACKGROUND_IMAGE;
    self.view.backgroundColor = SET_BACKGROUND_IMAGE;
}



 - (void)viewWillAppear:(BOOL)animated
{  
    [super viewWillAppear:animated];

    [self displayCommentsForPhotoID:[post ID]];
    [self.commentsTableView reloadData];

    CGRect frame = self.commentsTableView.frame;
    frame.size.height = TABLE_CELL_HEIGHT*[commentsArray count];
    self.commentsTableView.frame = frame; 

    CGRect viewFrame = self.contentView.frame;
    viewFrame.size.height = viewFrame.size.height + (TABLE_CELL_HEIGHT*[commentsArray count]) + ADD_VIEW_HEIGHT;
    self.contentView.frame = viewFrame;

    [self.scrollView addSubview:self.contentView];
    self.scrollView.contentSize = self.contentView.bounds.size;  
 }


    -(void)createCommentUserInterface {

    UILabel *lblComments = [[UILabel alloc]initWithFrame:CGRectMake(20.0f, 570.0f, 150.0f, 30.0f)];
    [lblComments setBackgroundColor:[UIColor clearColor]];
    [lblComments setText:@"Comments"];
    [self.contentView addSubview:lblComments];

    UIButton *btnAddComment = [UIButton buttonWithType:UIButtonTypeRoundedRect];
    [btnAddComment addTarget:self 
                      action:@selector(btnAddCommentPressed)
            forControlEvents:UIControlEventTouchDown];

    [btnAddComment setBackgroundImage:[UIImage imageNamed:@"btn_addcomment.png"] forState:UIControlStateNormal];
    btnAddComment.frame = CGRectMake(20.0f, 610.0f, 140.0f, 40.0f);
    [self.contentView addSubview:btnAddComment];

    commentsTableView = [[UITableView alloc]initWithFrame:CGRectMake(20.0f, 660.0f, 280.0f, 600.0f) style:UITableViewStylePlain];
    commentsTableView.delegate = self;
    commentsTableView.dataSource = self;

    [self.contentView addSubview:commentsTableView];

}



    #pragma mark - Table view data source

-(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView  
{
    // Return the number of sections.
    return 1;
}

-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section  
{
    return [self.commentsArray count];
}



 - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    UITableViewCell *cell;

    cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];

    cell = nil;


    if (cell == nil) {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
    }

    [tableView setSeparatorColor:[UIColor darkGrayColor]];
    [cell setSelectionStyle:UITableViewCellSelectionStyleNone];
    cell.backgroundColor = [UIColor whiteColor];
    userComment = [commentsArray objectAtIndex:[indexPath row]];

    UILabel *lblSubmittedBy = [[UILabel alloc]initWithFrame:CGRectMake(10.0f, 5.0f, 100.0f, 30.0f)];
    [lblSubmittedBy setText:@"Submitted by"];
    [cell addSubview:lblSubmittedBy];

    UIButton *btnUserName = [UIButton buttonWithType:UIButtonTypeCustom];
    btnUserName.frame = CGRectMake(120.0f, 5.0f, 150.0f, 30.0f);
    [btnUserName setContentHorizontalAlignment:UIControlContentHorizontalAlignmentLeft];
    [btnUserName setBackgroundColor:[UIColor clearColor]];
    [btnUserName setTitleColor:[UIColor cyanColor] forState:UIControlStateNormal];
    [btnUserName addTarget:self action:@selector(showUserProfileForUserComment:) forControlEvents:UIControlEventTouchUpInside];
    [btnUserName setUserInteractionEnabled:YES];
    [cell addSubview:btnUserName];

    UILabel *lblOnDate = [[UILabel alloc]initWithFrame:CGRectMake(10.0f, 40.0f, 20.0f, 30.0f)];
    [lblOnDate setText:@"on"];
    [cell addSubview:lblOnDate];

    UILabel *lblDate = [[UILabel alloc]initWithFrame:CGRectMake(35.0f, 40.0f, 200.0f, 30.0f)];
    [cell addSubview:lblDate];

    UITextView *txtVwComments = [[UITextView alloc]initWithFrame:CGRectMake(5.0f, 75.0f, 265.0f, 70.0f)];
    txtVwComments.backgroundColor = cell.backgroundColor;
    [txtVwComments setFont:[UIFont fontWithName:@"Helvetica" size:17.0f]];
    [txtVwComments setEditable:NO];
    [cell addSubview:txtVwComments];

    [txtVwComments setText:[userComment Comment]];

    CGRect frame = txtVwComments.frame;
    frame.size.height = txtVwComments.contentSize.height;
    CGFloat height = frame.size.height;

    NSLog(@"Value of height => %f",height);
    txtVwComments.frame = frame;

    CGFloat ht1 = height + 20.0f + 75.0f;
    UIButton *btnUpVote = [[UIButton alloc]initWithFrame:CGRectMake(10.0f, ht1 + 10.0f, 16.0f, 16.0f)];
    [btnUpVote setBackgroundColor:[UIColor clearColor]];
    [btnUpVote setBackgroundImage:[UIImage imageNamed:@"thumb_up.png"] forState:UIControlStateNormal];
    [btnUpVote addTarget:self 
                      action:@selector(btnUpVotePressed:)
            forControlEvents:UIControlEventTouchDown];
    [btnUpVote setTag:[userComment ID]];
    [cell addSubview:btnUpVote];
    NSLog(@"Value of ht1 => %f",ht1);

    lblUpVoteCount = [[UILabel alloc]initWithFrame:CGRectMake(36.0f, ht1 , 30.0f, 30.0f)];
    [lblUpVoteCount setTag:[userComment ID]];
    [cell addSubview:lblUpVoteCount];

    UIButton *btnDownVote = [[UIButton alloc]initWithFrame:CGRectMake(90.0f, ht1 + 10.0f , 16.0f, 16.0f)];
    [btnDownVote setBackgroundColor:[UIColor clearColor]];
    [btnDownVote setBackgroundImage:[UIImage imageNamed:@"thumb_down.png"] forState:UIControlStateNormal];
    [btnDownVote addTarget:self 
                    action:@selector(btnDownVotePressed:)
            forControlEvents:UIControlEventTouchDown];
    [btnDownVote setTag:[userComment ID]];
    [cell addSubview:btnDownVote];

    lblDownVoteCount = [[UILabel alloc]initWithFrame:CGRectMake(116.0f, ht1 , 40.0f, 30.0f)];
    [lblDownVoteCount setTag:[userComment ID]];
    [cell addSubview:lblDownVoteCount];

    UIButton *btnReply = [UIButton开发者_JAVA技巧 buttonWithType:UIButtonTypeRoundedRect];
    btnReply.frame = CGRectMake(180.0f, ht1, 60.0f, 30.0f);
    [btnReply setBackgroundColor:[UIColor clearColor]];
    [btnReply setBackgroundImage:[UIImage imageNamed:@"btn_reply.png"] forState:UIControlStateNormal];
    [btnReply addTarget:self action:@selector(btnReplyPressed:) forControlEvents:UIControlEventTouchDown];
    [btnReply setTag:[userComment ID]];
    [cell addSubview:btnReply];

    float y = ht1 + 40.0f;
    for (int i=0; i < [userComment.replyArray count]; i++) {

        if ([userComment.replyArray objectAtIndex:i] != nil) {

            UITextView *txtVwReply = [[UITextView alloc]initWithFrame:CGRectMake(40.0f, y , 220.0,60.0f)];
            [txtVwReply setUserInteractionEnabled:NO];
            [txtVwReply setFont:[UIFont fontWithName:@"Helvetica" size:14.0f]];
            [cell addSubview:txtVwReply];

        commentReply = [userComment.replyArray objectAtIndex:i];

            NSLog(@"userComment.replyArray => %@",userComment.replyArray);
            NSLog(@"commReply object => %@",commentReply);

            strReply = [NSString stringWithFormat:@"Submitted by %@ \n on %@\n %@",[commentReply ReplyUsername],[commentReply ReplyDateAdded],[commentReply ReplyComment]]; 
            NSLog(@"strReply => %@",strReply);
            [txtVwReply setText:strReply];
            [txtVwReply release];
            y = y +80;
        }
    }

    [btnUserName setTitle:[userComment Username] forState:UIControlStateNormal];

    [lblDate setText:[userComment DateAdded]];
    [lblUpVoteCount setText:[NSString stringWithFormat:@"%i",[userComment UpVotes]]];
    [lblDownVoteCount setText:[NSString stringWithFormat:@"%i",[userComment DownVotes]]];

    [lblSubmittedBy release];
    [lblOnDate release];
    [lblDate release];
    [txtVwComments release];
    [btnUpVote release];
    [lblUpVoteCount release];
    [btnDownVote release];
    [lblDownVoteCount release];

    return cell;
}

#pragma mark - Table view delegate

-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
   //  I don't want this event
}  

-(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{

    if ([commentsArray count]>0) {


        userComment = [commentsArray objectAtIndex:indexPath.row];
        NSString *strComment =userComment.Comment;
        NSLog(@"strComment : - %@",strComment);


        CGFloat replyHeight = 50.0f;
        if([userComment.replyArray count]>0) {
            for (int i=0; i < [userComment.replyArray count]; i++) {
                commentReply = [userComment.replyArray objectAtIndex:i];
                NSString *strCommentReply = commentReply.ReplyComment;
                NSLog(@"strCommentReply => %@",strCommentReply);

                [strCommentReply stringByAppendingFormat:@"\n %@",strCommentReply];
                replyHeight = replyHeight + 50;
            }
        }

        CGSize constraint = CGSizeMake(CELL_CONTENT_WIDTH - (CELL_CONTENT_MARGIN * 2), 20000.0f);

        CGSize sizeComment = [strComment sizeWithFont:[UIFont systemFontOfSize:FONT_SIZE] constrainedToSize:constraint lineBreakMode:UILineBreakModeWordWrap];

        CGFloat height = MAX(sizeComment.height + replyHeight, 44.0f);

        NSLog(@"height %f",height);

        NSLog(@"height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT => %f",height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT);
        NSLog(@"TABLE_CELL_HEIGHT - %f",height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT);

        return height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT;


    }

    NSLog(@"TABLE_CELL_HEIGHT - %f",TABLE_CELL_HEIGHT);

    return TABLE_CELL_HEIGHT;
}

Please guide me with this issue. Thanks

CODE UPDATE

  - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{  

// Code for placing UI components on the cell .Same as above code

    float y = ht1 + 40.0f;

    for (int i=0; i < [userComment.replyArray count]; i++) {

        if ([userComment.replyArray objectAtIndex:i] != nil) {

            UITextView *txtVwReply = [[UITextView alloc]initWithFrame:CGRectMake(40.0f, y , 220.0,0.0f)];
            [txtVwReply setUserInteractionEnabled:NO];
            [txtVwReply setFont:[UIFont fontWithName:@"Helvetica" size:14.0f]];
            [cell addSubview:txtVwReply];

            commentReply = [userComment.replyArray objectAtIndex:i];

            NSLog(@"userComment.replyArray => %@",userComment.replyArray);
            NSLog(@"commReply object => %@",commentReply);

            strReply = [NSString stringWithFormat:@"Submitted by %@ \n on %@\n %@",[commentReply ReplyUsername],[commentReply ReplyDateAdded],[commentReply ReplyComment]]; 
            NSLog(@"strReply => %@",strReply);

            [txtVwReply setText:strReply];

            CGRect frame = txtVwReply.frame;
            frame.size.height = txtVwReply.contentSize.height;
            CGFloat height = frame.size.height;

            NSLog(@"Value of height => %f",height);
            txtVwReply.frame = frame;

            y = y + 80;

            [txtVwReply release];

        }
    }
}


- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{

    if ([commentsArray count]>0) {

        userComment = [commentsArray objectAtIndex:indexPath.row];
        NSString *strComment =userComment.Comment;
        NSLog(@"strComment : - %@",strComment);

        CGFloat replyHeight = 135.0f;
        if([userComment.replyArray count]>0) {
            for (int i=0; i < [userComment.replyArray count]; i++) {
                commentReply = [userComment.replyArray objectAtIndex:i];
                NSString *strCommentReply = commentReply.ReplyComment;
                NSLog(@"strCommentReply => %@",strCommentReply);
                // Append all the reply & then use to determine hight
                [strCommentReply stringByAppendingFormat:@"\n %@",strCommentReply];
                replyHeight = replyHeight + 100.0f;
            }
        }

        CGSize constraint = CGSizeMake(CELL_CONTENT_WIDTH - (CELL_CONTENT_MARGIN * 2), 20000.0f);

        CGSize sizeComment = [strComment sizeWithFont:[UIFont systemFontOfSize:FONT_SIZE] constrainedToSize:constraint lineBreakMode:UILineBreakModeWordWrap];

        CGFloat height = MAX(sizeComment.height + replyHeight + 40.0f, 44.0f);

        NSLog(@"height %f",height);

        NSLog(@"height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT => %f",height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT);
        NSLog(@"TABLE_CELL_HEIGHT - %f",height + (CELL_CONTENT_MARGIN ) + TABLE_CELL_HEIGHT);


        return height;
        }

    NSLog(@"TABLE_CELL_HEIGHT - %f",TABLE_CELL_HEIGHT);

    return TABLE_CELL_HEIGHT;
}


I don't see where you have implemented the tableview delegate method:

 -(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath 

that is where I would figure to test your content and provide the size of the cell.


It looks to me that your calculations are incorrect. If I follow it properly, I'd guess that with a few replies it only happens to come out close to the correct size. Too many comments and it will be too small, with no comments your cell height would be oversized. This is because you are basically calculating your overall row height as:

50.0 (initial value for replyHeight) + commentHeight + (50.0 x replyArray.count)

that will be 50 + the height of your comments if there are no replies (note that will never be less than 44 so your MAX will never return less). You then add the constants TCM And CCH for a total of 300 + the height of the comments.

In your cellForRowAtIndexPath it appears that you would need only 135.0 + the height of the comment for a comment alone. So if you have no replies you will have a row nearly twice the size necessary. The reason it would look correct with a few replies is that you are using 80.0 for each reply but you are only adding 50.0 to the row height. It gets 30 points closer each time, then in about 4 or 5 iterations would even out. Any more and it would start to be too small.

I think that if you initialize replyHeight at 135.0 and change the incrementation of replyHeight to 80 rather than 50.0 the calculation should be closer. I could be off some as it is hard to follow in this browser. Then remove the two variables TABLE_CONTENT_MARGIN and TABLE_CELL_HEIGHT from the return value. A return value of 135 + commentHeight + (80 x replyArray.count) should be correct. You do not need to iterate through the comments since you are not using the string for anything that I can see. You may need that T_C_M as well, but you should see that easy enough when you play with it.


temparray is your array you used for loading cells in cellForRowAtIndexPath

(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
    NSString *str = [temparray objectAtIndex:indexPath.row];    
    If (str. length > 50) {
        return  85;
    }
    else {
        return 60;
    }
}
0

精彩评论

暂无评论...
验证码 换一张
取 消