Reputation: 21
hi my problem is when i scroll UITableView
cell images changing actually these images are on webserver and i and downloading it using asyncdownloading . i had added a UIImageView
on UITableViewCell
. images display succesfully on UITableViewCell
but when i scroll tableview images changes this is the code
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"DefaultCell"];
searchobjectval =[self.arrSearchResult objectAtIndex:indexPath.row];
if(cell == nil)
{
cell =[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"DefaultCell"];
}
UILabel *areaLbl = (UILabel *)[cell viewWithTag:1];
UILabel *postTitle = (UILabel *)[cell viewWithTag:2];
UILabel *roomCost = (UILabel *)[cell viewWithTag:3];
UILabel *description = (UILabel *)[cell viewWithTag:4];
areaLbl.text =searchobjectval.location;
postTitle.text = searchobjectval.title;
roomCost.text = searchobjectval.roomCost;
description.text =searchobjectval.description;
[tableView setSeparatorColor:[UIColor blueColor]];
UIView *myView = [[UIView alloc] init];
if (indexPath.row % 2)
{
UIColor* clr = [UIColor colorWithRed:0.4f green:0.6f blue:0.8f alpha:1];
myView.backgroundColor = clr;
}
else
{
myView.backgroundColor = [UIColor whiteColor];
}
cell.backgroundView = myView;
NSLog(@" search object image %@",searchobjectval.imgLink);
// Pass along the URL to the image (or change it if you are loading there locally)
[AsyncImagesDownloading processImageDataWithURLString:[NSString stringWithFormat: @"http://192.95.48.72/bedspace/new_arrivals_img/%@",searchobjectval.idVal ] andBlock:^(NSData *imageData)
{
if (self.view.window)
{
UIImage *image = [UIImage imageWithData:imageData];
UIImageView *imgVw = (UIImageView *)[cell viewWithTag:10];
imgVw.image = image;
}
}];
return cell;
}
Upvotes: 2
Views: 2066
Reputation: 176
This basically happens when a request hasn't completed but you have scrolled to a different cell. The UITableView, on account of reusing the cells would consider it the same cell and would render the image on the cell being shown.
Here's the article https://medium.com/@bipolarbear/uitableview-with-images-from-api-8902ba507bff
Disclaimer: I wrote this blog
Upvotes: 0
Reputation: 2644
dequeueReusableCellWithIdentifier takes a UITableViewCell object from the queue. the cell's content is not cleared when taken from the queue so this cell might display a "wrong" image until your download has finished and your UIImageView's image is overwritten. try setting the image property to nil after dequeing the cell so that nothing's being displayed until new data has been loaded.
((UIImageView *)[cell viewWithTag:10]).image = nil;
Upvotes: 0
Reputation: 144
For memory management purposes UITableView reusing its cells UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"DefaultCell"];
and it load cell content when scrolling up or down. If you dont fetch data to an element of the cell then you will have the last value fetched in the last use of the cell when you scroll back to it.
In your case :
// Pass along the URL to the image (or change it if you are loading there locally)
[AsyncImagesDownloading processImageDataWithURLString:[NSString stringWithFormat: @"http://192.95.48.72/bedspace/new_arrivals_img/%@",searchobjectval.idVal ] andBlock:^(NSData *imageData)
{
if (self.view.window)
{
UIImage *image = [UIImage imageWithData:imageData];
UIImageView *imgVw = (UIImageView *)[cell viewWithTag:10];
imgVw.image = image;
}
}];
So when !self.view.window
you will have the image of th last use of the cell (if clause returns TRUE) and it will be changing while scrolling. What you need to do is :
// Pass along the URL to the image (or change it if you are loading there locally)
[AsyncImagesDownloading processImageDataWithURLString:[NSString stringWithFormat: @"http://192.95.48.72/bedspace/new_arrivals_img/%@",searchobjectval.idVal ] andBlock:^(NSData *imageData)
{
if (self.view.window)
{
UIImage *image = [UIImage imageWithData:imageData];
UIImageView *imgVw = (UIImageView *)[cell viewWithTag:10];
imgVw.image = image;
} else {
UIImage *image = [UIImage imageNamed:@"placeHolder.png"];
UIImageView *imgVw = (UIImageView *)[cell viewWithTag:10];
imgVw.image = image;
}
}];
Hope this was clear an useful :)
Upvotes: 2
Reputation: 443
You can try one better approach given by apple for image loader and text loader which will make tableview scrolling faster link is below
http://developer.apple.com/library/ios/#samplecode/LazyTableImages/Introduction/Intro.html
Upvotes: 0
Reputation: 2916
Why don't use the cell and the IB doing this cell.yourImageView=[UIImage imageWithData:imageData];
? I think this answer is useful https://stackoverflow.com/a/3634414/2000162
Upvotes: 0
Reputation: 7416
You should store the image as a property on searchobjectval
and set it on the image view in cellForRowAtIndexPath
. When your async loading completes, check if the destination cell for the image is visible, if so reload it. If the cell isn't visible, you can simply wait for it to become visible again and then cellForRowAtIndexPath
will take of setting it for you.
Remember, if these images are big and self.arrSearchResult
exists for a long time, you should also put some logic in there to clear the images from memory if it begins to run low.
Upvotes: 0