---------------------------------AsyncImageView.h------------------------
#ifndef ah_retain#if __has_feature(objc_arc)
#define ah_retain self
#define ah_dealloc self
#define release self
#define autorelease self
#else
#define ah_retain retain
#define ah_dealloc dealloc
#define __bridge
#endif
#endif
// ARC Helper ends
#import <UIKit/UIKit.h>
extern NSString *const AsyncImageLoadDidFinish;
extern NSString *const AsyncImageLoadDidFail;
extern NSString *const AsyncImageImageKey;
extern NSString *const AsyncImageURLKey;
extern NSString *const AsyncImageCacheKey;
extern NSString *const AsyncImageErrorKey;
@interface AsyncImageLoader : NSObject
+ (AsyncImageLoader *)sharedLoader;
+ (NSCache *)defaultCache;
@property (nonatomic, strong) NSCache *cache;
@property (nonatomic, assign) NSUInteger concurrentLoads;
@property (nonatomic, assign) NSTimeInterval loadingTimeout;
- (void)loadImageWithURL:(NSURL *)URL target:(id)target success:(SEL)success failure:(SEL)failure;
- (void)loadImageWithURL:(NSURL *)URL target:(id)target action:(SEL)action;
- (void)loadImageWithURL:(NSURL *)URL;
- (void)cancelLoadingURL:(NSURL *)URL target:(id)target action:(SEL)action;
- (void)cancelLoadingURL:(NSURL *)URL target:(id)target;
- (void)cancelLoadingURL:(NSURL *)URL;
- (void)cancelLoadingImagesForTarget:(id)target action:(SEL)action;
- (void)cancelLoadingImagesForTarget:(id)target;
- (NSURL *)URLForTarget:(id)target action:(SEL)action;
- (NSURL *)URLForTarget:(id)target;
@end
@interface UIImageView(AsyncImageView)
@property (nonatomic, strong) NSURL *imageURL;
@end
@interface AsyncImageView : UIImageView
@property (nonatomic, assign) BOOL showActivityIndicator;
@property (nonatomic, assign) UIActivityIndicatorViewStyle activityIndicatorStyle;
@property (nonatomic, assign) BOOL crossfadeImages;
@property (nonatomic, assign) NSTimeInterval crossfadeDuration;
@end
---------------------------------AsyncImageView.m------------------------
#import "AsyncImageView.h"
#import <objc/message.h>
NSString *const AsyncImageLoadDidFinish = @"AsyncImageLoadDidFinish";
NSString *const AsyncImageLoadDidFail = @"AsyncImageLoadDidFail";
NSString *const AsyncImageTargetReleased = @"AsyncImageTargetReleased";
NSString *const AsyncImageImageKey = @"image";
NSString *const AsyncImageURLKey = @"URL";
NSString *const AsyncImageCacheKey = @"cache";
NSString *const AsyncImageErrorKey = @"error";
@interface AsyncImageConnection : NSObject
@property (nonatomic, strong) NSURLConnection *connection;
@property (nonatomic, strong) NSMutableData *data;
@property (nonatomic, strong) NSURL *URL;
@property (nonatomic, strong) NSCache *cache;
@property (nonatomic, strong) id target;
@property (nonatomic, assign) SEL success;
@property (nonatomic, assign) SEL failure;
@property (nonatomic, readonly, getter = isLoading) BOOL loading;
@property (nonatomic, readonly) BOOL cancelled;
- (AsyncImageConnection *)initWithURL:(NSURL *)URL cache:(NSCache *)cache
target:(id)target success:(SEL)success failure:(SEL)failure;
- (void)start;
- (void)cancel;
- (BOOL)isInCache;
@end
@implementation AsyncImageConnection
@synthesize connection = _connection;
@synthesize data = _data;
@synthesize URL = _URL;
@synthesize cache = _cache;
@synthesize target = _target;
@synthesize success = _success;
@synthesize failure = _failure;
@synthesize loading = _loading;
@synthesize cancelled = _cancelled;
- (AsyncImageConnection *)initWithURL:(NSURL *)URL cache:(NSCache *)cache target:(id)target success:(SEL)success failure:(SEL)failure {
if ((self = [self init])) {
self.URL = URL;
self.cache = cache;
self.target = target;
self.success = success;
self.failure = failure;
}
return self;
}
- (UIImage *)cachedImage {
if ([_URL isFileURL]) {
NSString *path = [[_URL absoluteURL] path];
NSString *resourcePath = [[NSBundle mainBundle] resourcePath];
if ([path hasPrefix:resourcePath]) {
return [UIImage imageNamed:[path substringFromIndex:[resourcePath length]]];
}
}
return [_cache objectForKey:_URL];
}
- (BOOL)isInCache {
return [self cachedImage] != nil;
}
- (void)loadFailedWithError:(NSError *)error {
_loading = NO;
_cancelled = NO;
[[NSNotificationCenter defaultCenter] postNotificationName:AsyncImageLoadDidFail
object:_target userInfo:[NSDictionary dictionaryWithObjectsAndKeys: _URL, AsyncImageURLKey, error, AsyncImageErrorKey, nil]];
}
- (void)cacheImage:(UIImage *)image {
if (!_cancelled) {
if (image && _URL) {
BOOL storeInCache = YES;
if ([_URL isFileURL]) {
if ([[[_URL absoluteURL] path] hasPrefix:[[NSBundle mainBundle] resourcePath]]) {
//do not store in cache
storeInCache = NO;
}
}
if (storeInCache) {
[_cache setObject:image forKey:_URL];
}
}
NSMutableDictionary *userInfo = [NSMutableDictionary dictionaryWithObjectsAndKeys:
image, AsyncImageImageKey,
_URL, AsyncImageURLKey,
nil];
if (_cache) {
[userInfo setObject:_cache forKey:AsyncImageCacheKey];
}
_loading = NO;
[[NSNotificationCenter defaultCenter] postNotificationName:AsyncImageLoadDidFinish object:_target userInfo:[[userInfo copy] autorelease]];
}
else {
_loading = NO;
_cancelled = NO;
}
}
- (void)processDataInBackground:(NSData *)data {
@synchronized ([self class]) {
if (!_cancelled) {
UIImage *image = [[UIImage alloc] initWithData:data];
if (image) {
//add to cache (may be cached already but it doesn't matter)
[self performSelectorOnMainThread:@selector(cacheImage:)
withObject:image
waitUntilDone:YES];
[image release];
}
else {
@autoreleasepool {
NSError *error = [NSError errorWithDomain:@"AsyncImageLoader" code:0 userInfo:[NSDictionary dictionaryWithObject:@"Invalid image data" forKey:NSLocalizedDescriptionKey]];
[self performSelectorOnMainThread:@selector(loadFailedWithError:) withObject:error waitUntilDone:YES];
}
}
}
else {
//clean up
[self performSelectorOnMainThread:@selector(cacheImage:)
withObject:nil
waitUntilDone:YES];
}
}
}
- (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {
self.data = [NSMutableData data];
}
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
//add data
[_data appendData:data];
}
- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
[self performSelectorInBackground:@selector(processDataInBackground:) withObject:_data];
self.connection = nil;
self.data = nil;
}
- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error {
self.connection = nil;
self.data = nil;
[self loadFailedWithError:error];
}
- (void)start {
if (_loading && !_cancelled) {
return;
}
//begin loading
_loading = YES;
_cancelled = NO;
//check for nil URL
if (_URL == nil) {
[self cacheImage:nil];
return;
}
//check for cached image
UIImage *image = [self cachedImage];
if (image) {
//add to cache (cached already but it doesn't matter)
[self performSelectorOnMainThread:@selector(cacheImage:)
withObject:image
waitUntilDone:NO];
return;
}
//begin load
NSURLRequest *request = [NSURLRequest requestWithURL:_URL
cachePolicy:NSURLCacheStorageNotAllowed
timeoutInterval:[AsyncImageLoader sharedLoader].loadingTimeout];
_connection = [[NSURLConnection alloc] initWithRequest:request delegate:self startImmediately:NO];
[_connection scheduleInRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
[_connection start];
}
- (void)cancel {
_cancelled = YES;
[_connection cancel];
self.connection = nil;
self.data = nil;
}
- (void)dealloc {
[_connection release];
[_data release];
[_URL release];
[_target release];
[super ah_dealloc];
}
@end
@interface AsyncImageLoader ()
@property (nonatomic, strong) NSMutableArray *connections;
@end
@implementation AsyncImageLoader
@synthesize cache = _cache;
@synthesize connections = _connections;
@synthesize concurrentLoads = _concurrentLoads;
@synthesize loadingTimeout = _loadingTimeout;
+ (AsyncImageLoader *)sharedLoader {
static AsyncImageLoader *sharedInstance = nil;
if (sharedInstance == nil) {
sharedInstance = [[self alloc] init];
}
return sharedInstance;
}
+ (NSCache *)defaultCache {
static NSCache *sharedInstance = nil;
if (sharedInstance == nil) {
sharedInstance = [[NSCache alloc] init];
}
return sharedInstance;
}
- (AsyncImageLoader *)init {
if ((self = [super init])) {
self.cache = [[self class] defaultCache];
_concurrentLoads = 2;
_loadingTimeout = 60.0;
_connections = [[NSMutableArray alloc] init];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(imageLoaded:)
name:AsyncImageLoadDidFinish
object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(imageFailed:)
name:AsyncImageLoadDidFail
object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(targetReleased:)
name:AsyncImageTargetReleased
object:nil];
}
return self;
}
- (void)updateQueue {
//start connections
NSUInteger count = 0;
for (AsyncImageConnection *connection in _connections) {
if (![connection isLoading]) {
if ([connection isInCache]) {
[connection start];
}
else if (count < _concurrentLoads) {
count ++;
[connection start];
}
}
}
}
- (void)imageLoaded:(NSNotification *)notification {
//complete connections for URL
NSURL *URL = [notification.userInfo objectForKey:AsyncImageURLKey];
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if (connection.URL == URL || [connection.URL isEqual:URL]) {
//cancel earlier connections for same target/action
for (int j = i - 1; j >= 0; j--) {
AsyncImageConnection *earlier = [_connections objectAtIndex:(NSUInteger)j];
if (earlier.target == connection.target &&
earlier.success == connection.success) {
[earlier cancel];
[_connections removeObjectAtIndex:(NSUInteger)j];
i--;
}
}
//cancel connection (in case it's a duplicate)
[connection cancel];
//perform action
UIImage *image = [notification.userInfo objectForKey:AsyncImageImageKey];
objc_msgSend(connection.target, connection.success, image, connection.URL);
//remove from queue
[_connections removeObjectAtIndex:(NSUInteger)i];
}
}
//update the queue
[self updateQueue];
}
- (void)imageFailed:(NSNotification *)notification {
//remove connections for URL
NSURL *URL = [notification.userInfo objectForKey:AsyncImageURLKey];
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if ([connection.URL isEqual:URL]) {
//cancel connection (in case it's a duplicate)
[connection cancel];
//perform failure action
if (connection.failure) {
NSError *error = [notification.userInfo objectForKey:AsyncImageErrorKey];
objc_msgSend(connection.target, connection.failure, error, URL);
}
//remove from queue
[_connections removeObjectAtIndex:(NSUInteger)i];
}
}
//update the queue
[self updateQueue];
}
- (void)targetReleased:(NSNotification *)notification {
//remove connections for URL
id target = [notification object];
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if (connection.target == target) {
//cancel connection
[connection cancel];
[_connections removeObjectAtIndex:(NSUInteger)i];
}
}
//update the queue
[self updateQueue];
}
- (void)loadImageWithURL:(NSURL *)URL target:(id)target success:(SEL)success failure:(SEL)failure {
//check cache
UIImage *image = [_cache objectForKey:URL];
if (image) {
[self cancelLoadingImagesForTarget:self action:success];
if (success) [target performSelectorOnMainThread:success withObject:image waitUntilDone:NO];
return;
}
//create new connection
AsyncImageConnection *connection =
[[AsyncImageConnection alloc] initWithURL:URL cache:_cache target:target success:success failure:failure];
BOOL added = NO;
for (NSUInteger i = 0; i < [_connections count]; i++) {
AsyncImageConnection *existingConnection = [_connections objectAtIndex:i];
if (!existingConnection.loading) {
[_connections insertObject:connection atIndex:i];
added = YES;
break;
}
}
if (!added) {
[_connections addObject:connection];
}
[connection release];
[self updateQueue];
}
- (void)loadImageWithURL:(NSURL *)URL target:(id)target action:(SEL)action {
[self loadImageWithURL:URL target:target success:action failure:NULL];
}
- (void)loadImageWithURL:(NSURL *)URL {
[self loadImageWithURL:URL target:nil success:NULL failure:NULL];
}
- (void)cancelLoadingURL:(NSURL *)URL target:(id)target action:(SEL)action {
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if ([connection.URL isEqual:URL] && connection.target == target && connection.success == action) {
[connection cancel];
[_connections removeObjectAtIndex:(NSUInteger)i];
}
}
}
- (void)cancelLoadingURL:(NSURL *)URL target:(id)target {
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if ([connection.URL isEqual:URL] && connection.target == target) {
[connection cancel];
[_connections removeObjectAtIndex:(NSUInteger)i];
}
}
}
- (void)cancelLoadingURL:(NSURL *)URL {
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if ([connection.URL isEqual:URL]) {
[connection cancel];
[_connections removeObjectAtIndex:(NSUInteger)i];
}
}
}
- (void)cancelLoadingImagesForTarget:(id)target action:(SEL)action {
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if (connection.target == target && connection.success == action) {
[connection cancel];
}
}
}
- (void)cancelLoadingImagesForTarget:(id)target {
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if (connection.target == target) {
[connection cancel];
}
}
}
- (NSURL *)URLForTarget:(id)target action:(SEL)action {
//return the most recent image URL assigned to the target for the given action
//this is not neccesarily the next image that will be assigned
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if (connection.target == target && connection.success == action) {
return [[connection.URL ah_retain] autorelease];
}
}
return nil;
}
- (NSURL *)URLForTarget:(id)target {
//return the most recent image URL assigned to the target
//this is not neccesarily the next image that will be assigned
for (int i = (int)[_connections count] - 1; i >= 0; i--) {
AsyncImageConnection *connection = [_connections objectAtIndex:(NSUInteger)i];
if (connection.target == target) {
return [[connection.URL ah_retain] autorelease];
}
}
return nil;
}
- (void)dealloc {
[[NSNotificationCenter defaultCenter] removeObserver:self];
[_cache release];
[_connections release];
[super ah_dealloc];
}
@end
@implementation UIImageView(AsyncImageView)
- (void)setImageURL:(NSURL *)imageURL {
[[AsyncImageLoader sharedLoader] loadImageWithURL:imageURL target:self action:@selector(setImage:)];
}
- (NSURL *)imageURL {
return [[AsyncImageLoader sharedLoader] URLForTarget:self action:@selector(setImage:)];
}
@end
@interface AsyncImageView ()
@property (nonatomic, strong) UIActivityIndicatorView *activityView;
@end
@implementation AsyncImageView
@synthesize showActivityIndicator = _showActivityIndicator;
@synthesize activityIndicatorStyle = _activityIndicatorStyle;
@synthesize crossfadeImages = _crossfadeImages;
@synthesize crossfadeDuration = _crossfadeDuration;
@synthesize activityView = _activityView;
- (void)setUp {
_showActivityIndicator = (self.image == nil);
_activityIndicatorStyle = UIActivityIndicatorViewStyleGray;
_crossfadeImages = YES;
_crossfadeDuration = 0.4;
}
- (id)initWithFrame:(CGRect)frame {
if ((self = [super initWithFrame:frame])) {
[self setUp];
}
return self;
}
- (id)initWithCoder:(NSCoder *)aDecoder {
if ((self = [super initWithCoder:aDecoder])) {
[self setUp];
}
return self;
}
- (void)setImageURL:(NSURL *)imageURL {
super.imageURL = imageURL;
if (_showActivityIndicator && !self.image && imageURL) {
if (_activityView == nil) {
_activityView = [[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:_activityIndicatorStyle];
_activityView.hidesWhenStopped = YES;
_activityView.center = CGPointMake(self.bounds.size.width / 2.0f, self.bounds.size.height / 2.0f);
_activityView.autoresizingMask = UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleRightMargin | UIViewAutoresizingFlexibleBottomMargin;
[self addSubview:_activityView];
}
[_activityView startAnimating];
}
}
- (void)setActivityIndicatorStyle:(UIActivityIndicatorViewStyle)style {
_activityIndicatorStyle = style;
[_activityView removeFromSuperview];
self.activityView = nil;
}
- (void)setImage:(UIImage *)image {
if (_crossfadeImages) {
//implement crossfade transition without needing to import QuartzCore
id animation = objc_msgSend(NSClassFromString(@"CATransition"), @selector(animation));
objc_msgSend(animation, @selector(setType:), @"kCATransitionFade");
objc_msgSend(animation, @selector(setDuration:), _crossfadeDuration);
objc_msgSend(self.layer, @selector(addAnimation:forKey:), animation, nil);
}
super.image = image;
[_activityView stopAnimating];
}
- (void)dealloc {
[[AsyncImageLoader sharedLoader] cancelLoadingURL:self.imageURL target:self];
[_activityView release];
[super ah_dealloc];
}
@end
USED FOLLOWING CODE IN CELL FOR ROW AT INDEX METHOD
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {static NSString *CellIdentifier = @"cutomeCell";
self.CustomeCellObject =(CustomeCell *) [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (self.MLSListCustomeCellObject == nil) {
if(UI_USER_INTERFACE_IDIOM() ==UIUserInterfaceIdiomPhone) {
(IS_WIDESCREEN)?
(nib = [[NSBundle mainBundle] loadNibNamed:@"CustomeCell" owner:self options:nil]):(nib = [[NSBundle mainBundle] loadNibNamed:@"CustomeCell" owner:self options:nil]);
}
else {
nib = [[NSBundle mainBundle] loadNibNamed:@"CustomeCell_iPad" owner:self options:nil];
}
self.CustomeCellObject = [nib objectAtIndex:0];
@try {
NSString *Year_BuiltString=[[NSString alloc] initWithFormat:@"%@",[[self.searchPropertyListArry objectAtIndex:indexPath.row*2]objectForKey:@"year"]];
if ([Year_BuiltString isEqualToString:@"<null>"] || [Year_BuiltString isEqualToString:@""] || [Year_BuiltString isEqualToString:@"(null)"] || Year_BuiltString == nil) {
self.CustomeCellObject.ybLbl.text=@"";
}
else {
self.CustomeCellObject.ybLbl.text=[NSString stringWithFormat:@"YB: %@",Year_BuiltString];
}
self.CustomeCellObject.requestShowingBtn.tag = indexPath.row*2;
[self.CustomeCellObject.requestShowingBtn addTarget:self action:@selector(goToRequestShowingView:) forControlEvents:UIControlEventTouchUpInside];
self.asyncImageViewimageViewObject = [[AsyncImageView alloc] initWithFrame:CGRectMake(0.0f, 0.0f, 131.0f, 88.0f)];
self.asyncImageViewimageViewObject.contentMode = UIViewContentModeScaleAspectFill;
self.asyncImageViewimageViewObject.clipsToBounds = YES;
self.asyncImageViewimageViewObject.tag = IMAGE_VIEW_TAG;
NSInteger lenght=indexPath.row*2+1;
NSURL *url = [[NSURL alloc] initWithString:[[self.searchPropertyListArry objectAtIndex:lenght]objectForKey:@"images"]];
NSLog(@"url---%@",url);
//cancel loading previous image for cell
[[AsyncImageLoader sharedLoader] cancelLoadingImagesForTarget:self.asyncImageViewimageViewObject];
//load the image
self.asyncImageViewimageViewObject.imageURL = url;
[self.CustomeCellObject.homeImageView addSubview:self.asyncImageViewimageViewObject];
}
@catch (NSException *excep) {
NSLog(@" Due to exception %@",[excep description]);
}
}
self.CustomeCellObject.selectionStyle=UITableViewCellSelectionStyleBlue;
return self.CustomeCellObject;
}
CHEK FACEBOOK LOGIN AND TWITTER LOGIN CODE
if([SLComposeViewController isAvailableForServiceType:SLServiceTypeFacebook])
{
NSLog(@"login");
Go to next view;
}
else
{
NSLog(@"logout");
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Hello" message:@"There are no Facebook accounts configured. You can add or create a Facebook account in Settings." delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil];
[alert show];
}
if([SLComposeViewController isAvailableForServiceType:SLServiceTypeTwitter])
{
NSLog(@"login");
Go to next view;
}
else
{
NSLog(@"logout");
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Hello" message:@"There are no Twitter accounts configured. You can add or create a Twitter account in Settings." delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil];
[alert show];
}
How to create the table view custom cell
http://www.edumobile.org/iphone/ipad-development/custom-table-view-cells-in-ipad-programming/