I want to first create imageview onto the scroll view.there i set placeholder image or give Background color of imageview.so all image view are display.
- (void)LoadDataInScrollView
{
dispatch_queue_t imageQueue = dispatch_queue_create("Image Queue",NULL);
//totalImageGetDict into count total Number of object and generate imageview.
for (int ivalue = 0; ivalue < [totalImageGetDict count]; ivalue++)
{
dispatch_async(imageQueue, ^{
//define x value
CGFloat xOrigin =ivalue *ascrollView.frame.size.width+50;
imageView = [[UIImageView alloc] init];
imageView.tag = ivalue;
[imageView setBackgroundColor:[UIColor whiteColor]];
imageView.frame = CGRectMake(xOrigin-40,imgYpos, ascrollView.frame.size.width-20, scrollViewHight);
//then here first i set already downloaded image.it's comes from another class. getImageLoadDict into images are already downloaded**
if ([getImageLoadDict objectForKey:[NSNumber numberWithInteger:ivalue]]!= nil)
{
//dispatch_async(dispatch_get_main_queue(), ^{
[imageView setImage:[getImageLoadDict objectForKey:[NSNumber numberWithInteger:ivalue]]];
//});
}
else
{
//totalImageGetDict into remaining images object and asynchronously download here.
STVisionPhoto *photoObj = [totalImageGetDict objectForKey:[NSNumber numberWithInteger:ivalue]];
UIImage *newimage = [photoObj image];
dispatch_async(dispatch_get_main_queue(), ^{
[imageView setImage:newimage];
});
}
[ascrollView addSubview:imageView];
});
}
}
You can use SDWebImage to do it.It is pretty easy to use
Edit :
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
UIImage * image = [UIImage imageWithData:[NSData dataWithContentsOfURL:your url]];
dispatch_async(dispatch_get_main_queue(), ^{
[imgview setImage:image];
});
});
You can try this if you don't want to use any library
Try to use this code:
UIImageView *imgView = [[UIImageView alloc] init];
imgView.frame = CGRectMake(12.5, 12.5, 80, 80);
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
UIImage *profileImage;
profileImage = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:YOUR_URL_STRING]]];
dispatch_async(dispatch_get_main_queue(), ^{
imgView.image = profileImage;
});
});
[cell.contentView addSubview:imgView];
(void)loadImg:(NSString *)url img :(UIImageView *)imgView{
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:url]];
__weak UIImageView *imageV = imgView;
[imgView setImageWithURLRequest:request placeholderImage:[UIImage imageNamed:#"songRecDef"] success:^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) {
imageV.image = image;
[imageV setNeedsLayout];
NSLog(#"%#",response);
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) {
[imageV setImage:[UIImage imageNamed:#"songRecDef"]];
NSLog(#"%#",error);
}];
}
Related
I have got a productImageArray that contains url as elements of the array.
I'm trying to load those urls in my image view.
Following is the way as of how I'm loading it.
UIActivityIndicatorView *spinner=[[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray];
spinner.center=CGPointMake(160.0,240.0 );
spinner.hidesWhenStopped=YES;
[self.view addSubview:spinner];
[spinner startAnimating];
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0ul);
dispatch_async(queue, ^{
NSData *storeImageData = [NSData dataWithContentsOfURL:[NSURL URLWithString:productImageArray[indexPath.row]]];
self.productImage.image = [UIImage imageWithData:storeImageData];
dispatch_sync(dispatch_get_main_queue(), ^{
[spinner stopAnimating];
});
});
The problem is that,
Only the last cell of my tableview loads the image whereas the remaining cell does not load the image from the url
Is there any other better way of loading the image from url directly into my UIImage using native methods?
When I use the following code, each cell of my tableview loads the image data but still it freezes the User interface till the data is loaded completely
NSData *storeImageData = [NSData dataWithContentsOfURL:[NSURL URLWithString:productImageArray[indexPath.row]]];
self.productImage.image = [UIImage imageWithData:storeImageData];
#Anbu.Karthik answer is right.
But, maybe the simplest solution is to use something like SDWebImage no? This library will handle this issue and much more (cache, error management, proper tableview cells handling, ...).
I think you should, at least, take a few minutes to look at it: https://github.com/rs/SDWebImage
Edit:
If you use SDWebImage, and UIActivityIndicator-for-SDWebImage, you can replace your entire code by this:
[self.productImage setImageWithURL:[NSURL URLWithString:productImageArray[indexPath.row]]
usingActivityIndicatorStyle:UIActivityIndicatorViewStyleGray];
More informations on UIActivityIndicator-for-SDWebImage: https://github.com/JJSaccolo/UIActivityIndicator-for-SDWebImage
try this
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0ul);
dispatch_async(queue, ^{
NSData *storeImageData = [NSData dataWithContentsOfURL:[NSURL URLWithString:productImageArray[indexPath.row]]];
dispatch_sync(dispatch_get_main_queue(), ^{
[spinner stopAnimating];
self.productImage.image = [UIImage imageWithData:storeImageData];
});
});
or try like
self.productImage.image = nil; //// [UIImage imageNamed:#"default.png"];
NSURLSessionTask *task = [[NSURLSession sharedSession] dataTaskWithURL:[NSURL URLWithString:productImageArray[indexPath.row]] completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
if (data) {
UIImage *currentImage = [UIImage imageWithData:data];
if (currentImage) {
dispatch_async(dispatch_get_main_queue(), ^{
UITableviewCell *getCurrentCell = (id)[tableView cellForRowAtIndexPath:indexPath];
if (getCurrentCell)
self.productImage.image = currentImage;
});
}
}
}];
[task resume];
NSString *url_Img1 = #"Your url";
Uiimageview *view_Image.image = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:url_Img1]]];
(
(
"http://sportsromio.aiminfotechs.com/WEBSERVICES/available_sports/volleyball.png",
"http://sportsromio.aiminfotechs.com/WEBSERVICES/available_sports/football.png"
),
(
"http://sportsromio.aiminfotechs.com/WEBSERVICES/available_sports/football.png",
"http://sportsromio.aiminfotechs.com/WEBSERVICES/available_sports/cricket.png"
)
I used this array how can I used it.
Put this code in 'cellForRowIndexPath'
int x = 0;
for (NSURL * url in yourArrayName) {
UIImageView *yourImageView =[[UIImageView alloc] initWithFrame:CGRectMake(x,50,20,20)];
yourImageView.image = [UIImage imageWithData:[NSData dataWithContentsOfURL:url]];
[cell addSubview:yourImageView];
x = x + 60;
}
add in cell for Row
int x = 0;
for (NSString * stringurl in [imgs objectAtIndex:indexPath.row]) {
UIImageView *yourImageView =[[UIImageView alloc] initWithFrame:CGRectMake(x,10,40,40)];
NSURL *url=[NSURL URLWithString:stringurl];
__block UIActivityIndicatorView *activityIndicator;
__weak UIImageView *weakImageView = yourImageView;
[yourImageView sd_setImageWithURL:url
placeholderImage:[UIImage imageNamed:#"placeholder"]
options:SDWebImageProgressiveDownload
progress:^(NSInteger receivedSize, NSInteger expectedSize) {
if (!activityIndicator) {
[weakImageView addSubview:activityIndicator = [UIActivityIndicatorView.alloc initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray]];
activityIndicator.center = weakImageView.center;
[activityIndicator startAnimating];
}
}
completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, NSURL *imageURL) {
[activityIndicator removeFromSuperview];
activityIndicator = nil;
}];
[cell addSubview:yourImageView];
x = x + 40;
}
I have cobbled together some methods to resize images and put them into a UIScrollView for horizontal scrolling, however one of my problems is that I'm capturing strongly, and I have attempted a few options that I have read about, but all result in no images being displayed. I'm hoping one of you can help me resolve this issue so I can quit cooking so much memory when my app loads the images into the scroll view.
- (void)setImage:(NSURL *)imageURL errorImage:(UIImage *)errorImage{
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:imageURL];
[request addValue:#"image/*" forHTTPHeaderField:#"Accept"];
UIImageView *newView = [[UIImageView alloc] initWithFrame: CGRectMake(self.x, 0, self.screenWidth, self.screenHight)];
[self.scrollView addSubview: newView];
self.x = (self.x + newView.frame.size.width);
if(self.x > self.view.frame.size.width) {
self.scrollView.contentSize = CGSizeMake(self.x, self.scrollView.frame.size.height);
}
[[newView subviews] makeObjectsPerformSelector:#selector(removeFromSuperview)]; // Remove previous that not stop
__block UIActivityIndicatorView *activityIndicator = [[UIActivityIndicatorView alloc] init];
activityIndicator.frame = newView.bounds;
[activityIndicator setHidden:NO];
[activityIndicator startAnimating];
activityIndicator.color = [UIColor redColor];
[newView addSubview:activityIndicator];
void (^removeSpinner)(void) = ^{ // Desctuctor Block
if (activityIndicator) {
[activityIndicator setHidden:YES];
[activityIndicator stopAnimating];
[activityIndicator removeFromSuperview];
activityIndicator = nil;
}
};
[newView setImageWithURLRequest:request placeholderImage:nil success: ^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) {
removeSpinner();
// resize the resulting image for this device
newView.image = [self imageScaleCropToSize:image];
NSLog(#"successfully loaded image: %#", imageURL);
} failure: ^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) {
removeSpinner();
NSLog(#"failed loading [%#]: %#", imageURL, error);
}];
}
I have a custom cell with UIImageView, and it is not showing the image. I have tried setting image to default cell.imageView.image property, and it works just fine, but doesn't work with my custom ImageView.
I load my custom Cell from Xib, and I believe it has to do with lazy loading of UIImageView. How do I make it work?
Here is my code:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"MyCell";
DVGTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
cell.tag = indexPath.row;
if (self.loader.parsedData[indexPath.row] != nil)
{
cell.imageCustom.image = nil;
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0ul);
dispatch_async(queue, ^(void) {
NSString *url = [self.loader.parsedData[indexPath.row] objectForKey:#"imageLR"];
NSData *imageData = nil;
if ([self.cache objectForKey:url] != nil)
{
imageData = [self.cache objectForKey:url];
}
else
{
imageData = [NSData dataWithContentsOfURL:[NSURL URLWithString:url]];
[self.cache setObject:imageData forKey:[self.loader.parsedData[indexPath.row] objectForKey:#"imageLR"]];
}
dispatch_async(dispatch_get_main_queue(), ^{
if (cell.tag == indexPath.row) {
UIImage *image = [[UIImage alloc] initWithData:imageData];
cell.imageCustom.image = image;
[cell setNeedsLayout];
}
});
});
}
return cell;
}
I usually do Lazy loading for ImageViews with this piece of code, hope it helps:
- (void) loadImageForImageView:(UIImageView *)theImageView WithURL:(NSURL *)url {
NSOperationQueue *queue = [NSOperationQueue new];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url cachePolicy:NSURLRequestReturnCacheDataElseLoad timeoutInterval:3.0];
[NSURLConnection sendAsynchronousRequest:request queue:queue completionHandler:^(NSURLResponse *reponse, NSData *data, NSError *error) {
UIImage *image = [UIImage imageWithData:data];
dispatch_async(dispatch_get_main_queue(), ^{
theImageView.image = image;
for (UIActivityIndicatorView *spinner in theImageView.subviews) {
[spinner removeFromSuperview];
break;
}
});
}];
}
In your cellForRowAtIndexPath:
UIActivityIndicatorView *spinner = [[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray];
[spinner setColor:[UIColor darkGrayColor]];
spinner.frame = CGRectMake(130 , 53, 20, 20);
[spinner startAnimating];
[imageCell addSubview:spinner];
[self loadImageForImageView:imageCell WithURL:imageURL];
Where imageCell is your UIImageView.
I have a UIScrollView that I want to load a list of images from flickr. Then I want the photos to be displayed like that of the native stock iphone photo app where you scroll through the photos.
Here is my code
- (void)viewDidLoad
{
[super viewDidLoad];
for (int i = 0; i < self.urlArray.count; i++) {
CGRect frame;
frame.origin.x = self.scrollView.frame.size.width * i;
frame.origin.y = 0;
frame.size = self.scrollView.frame.size;
UIView *subview = [[UIView alloc] initWithFrame:frame];
[self returnImageFromFlickr:[self.urlArray objectAtIndex:i]];
UIImageView *imageView = self.largePhoto;
[subview addSubview:imageView];
[self.scrollView addSubview:subview];
}
self.scrollView.contentSize = CGSizeMake(self.scrollView.frame.size.width * self.urlArray.count, self.scrollView.frame.size.height);
}
-(void)returnImageFromFlickr:(NSURL *)url {
NSURLRequest *request = [[NSURLRequest alloc] initWithURL:url];
[self.largePhoto setImageWithURLRequest:request placeholderImage:[UIImage imageNamed:#"placeholder.png"] success:^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) {
[self.largePhoto setImageWithURL:url placeholderImage:[UIImage imageNamed:#"placeholder.png"]];
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) {
}];
}
What is happening only the last image is being shown.
I tried your solution as I understood it and got this. This is not brining up a photo. Just a white screen. Plus a warning in the returnImageFromFlicrk method at
[imageView setImageWithURL:url placeholderImage:[UIImage imageNamed:#"placeholder.png"]];
saying
Capturing 'imageView' strongly in this block is likely to lead to a retain cycle
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
/*for (int i = 0; i < self.urlArray.count; i++) {
CGRect frame;
frame.origin.x = self.scrollView.frame.size.width * i;
frame.origin.y = 0;
frame.size = self.scrollView.frame.size;
UIView *subview = [[UIView alloc] initWithFrame:frame];
[self returnImageFromFlickr:[self.urlArray objectAtIndex:i]];
UIImageView *imageView = self.largePhoto;
[subview addSubview:imageView];
//subview.backgroundColor = [colors objectAtIndex:i];
[self.scrollView addSubview:subview];
}*/
for (int i = 0; i < self.urlArray.count; i++) {
CGRect frame;
frame.origin.x = self.scrollView.frame.size.width * i;
frame.origin.y = 0;
frame.size = self.scrollView.frame.size;
UIImageView *imageView = [[UIImageView alloc] init];
[self returnImageFromFlickr:[self.urlArray objectAtIndex:i] imageview:imageView];
[self.scrollView addSubview:imageView];
}
self.scrollView.contentSize = CGSizeMake(self.scrollView.frame.size.width * self.urlArray.count, self.scrollView.frame.size.height);
}
-(void)returnImageFromFlickr:(NSURL *)url imageview:(UIImageView *)imageView {
NSURLRequest *request = [[NSURLRequest alloc] initWithURL:url];
[imageView setImageWithURLRequest:request placeholderImage:[UIImage imageNamed:#"placeholder.png"] success:^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) {
[imageView setImageWithURL:url placeholderImage:[UIImage imageNamed:#"placeholder.png"]];
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) {
}];
}
You are not setting right parameters to the Scroll content pan that is why all the images you want are not displaying in scrollView. Try updating ScrollView's content pan to fit the width of all images. Like
self.scrollView.contentSize = CGSizeMake(Width, Height);
in this case height will be the hight of single image and width will be (width of single image * total number of images)
You overwrite self.largePhoto, you need set your imageView in returnImageFromFlickr
try this
UIImageView *imageView = [[UIImageView alloc] init];
[self returnImageFromFlickr:[self.urlArray objectAtIndex:i] imageview:imageView];
and
-(void)returnImageFromFlickr:(NSURL *)url imageview:(UIImageView *)imageView {
NSURLRequest *request = [[NSURLRequest alloc] initWithURL:url];
[imageView setImageWithURLRequest:request placeholderImage:[UIImage imageNamed:#"placeholder.png"] success:^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) {
[imageView setImage:image];
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) {
}];
}
All I needed to do was move the code from viewDidLoad to viewDidApear