Search code examples
iosobjective-cobjective-c-blockswrapper

How to Create Wrapper class for my block method so i can use it by single line


I created a small solution for downloading any kind of file and then save the that to Cache.db. Everything is working perfectly so far but now i want to create a Wrapper Class for this class so i can convert the Nsdata to any format i want

#import "DownLoadFiles.h"

@implementation DownLoadFiles
@synthesize task,session,dataType;


-(void)DownloadCacheFile:(NSURLRequest*)urlRequest callBackBlock:(void (^)(id))responeBlock{
    NSURLSession *sessions = [NSURLSession sharedSession];
    NSCachedURLResponse *cachedResponse = [[NSURLCache sharedURLCache] cachedResponseForRequest:urlRequest];

    if ([cachedResponse isKindOfClass:[NSNull class]]||cachedResponse==nil) {

        NSLog(@"cachedResponse -- %@",[cachedResponse response]);


        NSURLSessionDataTask *tasked=   [sessions dataTaskWithRequest:urlRequest
                                                    completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
                                                            responeBlock(data);
                                                    }];
        [tasked resume];


    }else{
        switch (urlRequest.cachePolicy) {
            case NSURLRequestUseProtocolCachePolicy:
            case NSURLRequestReturnCacheDataElseLoad:
            case NSURLRequestReturnCacheDataDontLoad: {

                    responeBlock([cachedResponse data]);
                break;
            }
            default:
                break;
        }
    }
}

@end

for instance that i know the url contain image so i want to convert the NSData to UIImage so same as for the rest of the format Types like json, avi, etc. like this.

@implementation AKImage
@synthesize image;

-(UIImage*)SetImageforUrl:(NSURLRequest*)imgRequest {
    UIImage *image;

       DownLoadFiles*dwnl=[[DownLoadFiles alloc] init];
        [dwnl DownloadCacheFile:req
                  callBackBlock:^(id response) {
           image=  [UIImage imageWithData:response];

       }];
    return image;
}

@end

so the problem starts here. i want to return the image but image will not wait for the lazy method to return the data, so it is returning nil and after some time block has data.

at my viewController i want to use AKImage wrapper Class like this

AKImage *akObj=[[AKImage alloc] init];
self.imgView.image=[akObjt SetImageforUrl:req];

but currently this block does not allow me to do that


Solution

  • You need to add a custom callback to your method so it will call when the download callback is called.

    -(void)imageforUrl:(NSURLRequest*)imgRequest completion:(void (^)(UIImage *image))handler {
    
        DownLoadFiles *dwnl = [[DownLoadFiles alloc] init];
    
        [dwnl DownloadCacheFile:req callBackBlock:^(id response) {
    
            // Update UI on the main queue
            dispatch_async(dispatch_get_main_queue(), ^{
                handler([UIImage imageWithData:response]);
            });
        }];
    }
    

    Then call it like this:

    AKImage *akObj = [[AKImage alloc] init];
    [akObjt imageforUrl: req completion:^(UIImage *image) {
        self.imgView.image = image
    }];
    

    Been awhile since I wrote some Objective-C, please double check the syntax yourself.

    Edit:

    To make a class method: What is the difference between class and instance methods?