Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

UITableView separator flickering during app switching

PS: I can post a small video but it seems unnecessary.

Create a sample project using Xcode 6.4 (currently using 6E35b). Create a simple UITableViewController subclass and render it using either a storyboard or programmatically.

Try app-switching. It appears that the tableview separator flickers whenever the app goes in background or foreground. It doesn't flickr while scrolling, etc.

To see it better, use:

self.tableView.backgroundColor = [UIColor whiteColor];
self.tableView.rowHeight = 75.0f
self.tableView.separatorColor = self.view.tintColor;

I am unsure why this is happening. I have referred to iPhone 6/6 Plus: UITableView separator flickering and different thickness but the default projects always have a launch screen IB file.

You can see the issue in the default settings app on iOS. For the most part, this doesn't become an issue unless you are rendering images and suddenly the white separator lines flickr.

EDIT 1: The biggest issue for me is that even if I use:

self.tableView.separatorStyle = UITableViewCellSeparatorStyleNone;

the separator is rendered momentarily and then disappears; exactly the same as in other cases. See EDIT 2 for more details.

EDIT 2 (07/04/15, 8.46PM): I wish to provide some more examples here. The flickering behavior that I was observing was much more prominent with custom table view cells (i.e. where you have a freedom of rendering your own image views with custom property settings, etc).

Another observation is that the specific flickering behavior (i.e. in the case where separatorStyle == UITableViewCellSeparatorStyleNone) is not noticeable with text only cells. It is primarily noticeable in cases where images are rendered in table view cells.

  1. Here is an example of a table view cell:

    @interface BTableViewCell ()
    
    @property (nonatomic, strong, readwrite) UIImageView *mainImageView;
    
    @end
    
    @implementation BTableViewCell
    
    - (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
    {
        self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
        if (self)
        {
            [self commonInit];
        }
        return self;
    }
    
    - (id)initWithCoder:(NSCoder *)aDecoder
    {
        self = [super initWithCoder:aDecoder];
        if (self)
        {
            [self commonInit];
        }
        return self;
    }
    
    - (void)commonInit
    {
        // Initialize Avatar Image
        self.mainImageView = [[UIImageView alloc] init];
        _mainImageView.translatesAutoresizingMaskIntoConstraints = NO;
        _mainImageView.layer.masksToBounds = YES;
        [self.contentView addSubview:_mainImageView];
    
        [self configureConstraintsForImageView];
    }
    
    - (void)configureConstraintsForImageView
    {
        [self.contentView addConstraint:[NSLayoutConstraint constraintWithItem:_mainImageView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:self.contentView attribute:NSLayoutAttributeHeight multiplier:1 constant:0]];
        [self.contentView addConstraint:[NSLayoutConstraint constraintWithItem:_mainImageView attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:self.contentView attribute:NSLayoutAttributeWidth multiplier:1 constant:0]];
    }
    
    @end
    
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
        BTableViewCell*cell = [tableView dequeueReusableCellWithIdentifier:@"CellIdentifier"];
    
        NSString *imagePath = [[NSBundle mainBundle] pathForResource:@"image" ofType:@"jpeg"];
        UIImage* image = [UIImage imageWithContentsOfFile:imagePath];
        cell.mainImageView.image = image; //ignore unoptimized load
        return cell;
    }
    
  2. The flickering almost goes away if masksToBounds property is false. I am not sure why this would be the case or if this is the intended way.

  3. Instead of using a custom table view cell, use the default UITableViewCell class.

    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
        UITableViewCell*cell = [tableView dequeueReusableCellWithIdentifier:@"CellIdentifier"];
    
        NSString *imagePath = [[NSBundle mainBundle] pathForResource:@"image" ofType:@"jpeg"];
        UIImage* image = [UIImage imageWithContentsOfFile:imagePath];
        cell.backgroundView = [[UIImageView alloc] initWithImage:image];
        return cell;
    }
    

It's worth noticing that the flickering behavior for #2 and #3 is more or less the same. It is much more subtle as compared to the one in #1, but still noticeable.

like image 281
p0lAris Avatar asked Jul 04 '15 21:07

p0lAris


1 Answers

Add

Renders with edge antialiasing: YES

In your app plist

like image 98
hariszaman Avatar answered Nov 06 '22 22:11

hariszaman