2010-01-18 12 views
0

J'ai créé un UITableViewController qui calcule la hauteur de chaque ligne en fonction de la quantité de texte qu'il contient. Le code pour calculer la hauteur de ligne ressemble à ceci:UITableView a une image d'arrière-plan «moche» pour les lignes de hauteur dynamique

- (CGFloat)tableView:(UITableView*)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath { 
    CGSize constraint = CGSizeMake(CELL_CONTENT_WIDTH - (CELL_CONTENT_MARGIN * 2), 20000.0f); 
    Message *message = [[[[SessionData sharedSessionData] sessions] objectAtIndex:[indexPath section]] objectAtIndex:[indexPath row]]; 
    CGSize size = [[message text] sizeWithFont:[UIFont systemFontOfSize:FONT_SIZE] constrainedToSize:constraint lineBreakMode:UILineBreakModeWordWrap]; 

    return size.height + (CELL_CONTENT_MARGIN * 2) + 38; 
} 

Comme vous pouvez le remarquer, j'utiliser une classe séparée comme UITableViewDatasource appelé SessionData. Dans la classe SessionData, je dessine les lignes. Chaque rangée a une image supérieure, une image centrale (répétée en fonction de la hauteur de la rangée) et une image du bas. Mon problème est le suivant: l'image du centre est dessiné un peu plus sombre que les images du bas et du haut. Je suppose que cela a quelque chose à voir avec la nature répétitive de l'image, car les images du haut et du bas sont bien dessinées. Le code suivant fait partie de mon [tableView: cellForRowAtIndexPath:] message:

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

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

    // other stuff here, most likely not related to my issue ... 

    Message *message = [[sessions objectAtIndex:[indexPath section]] objectAtIndex:[indexPath row]];  
    CGSize constraint = CGSizeMake(CELL_CONTENT_WIDTH - (CELL_CONTENT_MARGIN * 2), 20000.0f); 
    CGSize size = [[message text] sizeWithFont:[UIFont systemFontOfSize:FONT_SIZE] constrainedToSize:constraint lineBreakMode:UILineBreakModeWordWrap]; 

    [label setText:[message text]]; 
    [label setFrame:CGRectMake(CELL_CONTENT_MARGIN, CELL_CONTENT_MARGIN - 5.0f, CELL_CONTENT_WIDTH - (CELL_CONTENT_MARGIN * 2), size.height)]; 
    [label setBackgroundColor:[UIColor clearColor]]; 

    viewTop = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"im1 top.png"]]; 
    viewMid = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"im1 mid.png"]]; 
    viewBot = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"im1 bot.png"]];  

    [viewTop setFrame:CGRectMake(0.0, 0.0, 300.0, 17.0)]; 
    [viewMid setFrame:CGRectMake(0.0, 17.0, 300.0, size.height - 10)]; 
    [viewBot setFrame:CGRectMake(0.0, 17.0 + size.height - 10, 300.0, 31.0)]; 

    [viewTop setBackgroundColor:[UIColor clearColor]]; 
    [viewMid setBackgroundColor:[UIColor clearColor]]; 
    [viewBot setBackgroundColor:[UIColor clearColor]]; 

    [cell.backgroundView setBackgroundColor:[UIColor clearColor]]; 

    [((UIImageView *)cell.backgroundView) addSubview:viewTop]; 
    [((UIImageView *)cell.backgroundView) addSubview:viewMid]; 
    [((UIImageView *)cell.backgroundView) addSubview:viewBot]; 

    [[cell backgroundView] addSubview:label]; 

    return cell; 
} 

Je suppose que je devrais créer un containerView avec la taille totale (largeur, hauteur) pour le haut, centre et bas imageViews et ajoutez le containerView à la cellule, mais cela n'a pas semblé fonctionner. Quelqu'un at-il une idée sur la façon de résoudre ce problème? REMARQUE: Mon UITableViewController a un dégradé en tant qu'image d'arrière-plan. Ainsi, les images du haut/du centre/du bas sont dessinées au-dessus du dégradé d'arrière-plan. Peut-être que cela fait aussi partie du problème.

Répondre

0

Merci pour vos suggestions Michael. Je pourrais en effet résoudre mes problèmes graphiques en utilisant le code suivant:

[bubbleView setImage:[bubble stretchableImageWithLeftCapWidth:165 topCapHeight:30]]; 

Au lieu d'utiliser 3 images séparées pour créer des bulles de chat Je peux maintenant utiliser 1 image et il étend avec élégance.Une suggestion très intéressante :)

Même si je ne semblais pas avoir beaucoup de problèmes de vitesse, j'ai réécrit mon code partiellement comme vous l'avez suggéré, principalement en construisant la partie principale des cellules dans la partie initialiseur de cellules du code. J'ai remarqué une amélioration mineure de la vitesse, peut-être plus visible sur un appareil (par rapport au simulateur).

Actuellement, je dessine toujours mes images en utilisant ImageView (comme vous pouvez le constater), je regarderai [UIImage drawInRect:] chaque fois que j'ai besoin de plus de vitesse dans le rendu.

Merci pour vos suggestions, très appréciées.

+1

Votre bienvenue! Oui, je suggère de tester régulièrement sur un appareil. Le simulateur est extrêmement rapide car il a toute la mémoire de votre mac et la puissance du processeur. Si vous avez un bon nombre de lignes, je pense que vous verrez des cadences d'images lentes lors du défilement sur l'appareil (par exemple, par exemple l'application de messagerie texte ou l'application iPod). Au début, je passais beaucoup de temps à utiliser le simulateur et quand j'ai finalement testé sur l'appareil, tout était ** extrêmement ** lent, et j'ai dû réécrire tout mon code de vue de table! (Accordé je les ai utilisés fortement!) Mais j'ai appris ma leçon! Bonne chance! –

1

Quelques petites choses à noter ici. Tout d'abord, il y a beaucoup de traitement qui se passe dans vos cellules, ce qui provoque de très mauvaises performances de défilement sur l'appareil. Vous devriez faire une meilleure utilisation des cellules requeuing et effectuer la plupart de la configuration cellulaire qui est commune à toutes les cellules ici:

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; 
    if (cell == nil) { 
     cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease]; 
     // Do cell layout in here! 
    } 

C'est la cellule façon et leurs sous-vues peuvent être réutilisées au lieu de recréés chaque fois qu'une cellule apparaît à l'écran (utilisez les propriétés tag et viewWithTag: méthodes de vues). En second lieu, vous pouvez regarder stretchable images. Troisièmement, vous remarquerez de bien meilleures performances en dessinant manuellement des cellules. Créez une vue personnalisée (que vous ajoutez à la vue de contenu), remplacez drawRect:, dessinez des images sur eux en utilisant UIImage méthode drawInRect:. Cela va accélérer les choses de manière significative! Dessinez tout ce que vous pouvez parce que la mise en page subview est cher! De même, assurez-vous de ne pas utiliser de transparence UIView (notamment UIImageView, UILabel, etc ...) si possible, réglez opaque = YES et définissez les couleurs d'arrière-plan. Il est préférable de dessiner du texte en drawRect:, en utilisant la méthode drawInRect: de NSString qui donnera l'apparence d'un UILabel transparent.

Cependant, si vous avez TRES peu de cellules, comme < 4 ou quelque chose, alors peut-être que la méthode de dessin est trop. Cependant, il est toujours très conseillé!

Espérons que cela aide!