Reusing UITableViewCell with GCD
grand-central-dispatch, ios, iphone, uitableview
Solution
what i've done is added an `NSOperation` ivar to the cell. the operation is responsible for getting, loading, and creating the image. when completed, it pings the cell. when/if the cell is dequeued, the operation is cancelled and destroyed if it has not finished. the operation test for cancellation when in `-main`. after the image is passed to the cell, the cell drops the operation and uses the image.
Problem
I'm using Grand Central Dispatch to load images of a `UITableViewCell` asynchronously. This works well except in some border cases in which the cell is reused, and a previous block loads the wrong image. My current code looks like this: ``` - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static NSString *CellIdentifier = @"Cell"; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; if (!cell) { cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease]; } NSString *imagePath = [self imagePathForIndexPath:indexPath]; dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0ul); dispatch_async(queue, ^{ UIImage *image = [UIImage imageWithContentsOfFile:imagePath]; dispatch_sync(dispatch_get_main_queue(), ^{ cell.imageView.image = image; [cell setNeedsLayout]; }); }); return cell; } ``` As far as I know GCD queues cannot be stopped. How can this border case be prevented then? Or should I be using something else instead of GCD to solve this problem?