因为项目需要,需求是高德地图的MAAnnotationView能加载网络图片作为图标,研究了SDWebImageView里的MKAnnotationView+WebCache,仿写了MAAnnotationView+WebCache
下面放出代码
MAAnnotationView+WebCache.h
#import
#import"SDWebImageManager.h"
//@interface MAAnnotationView_WebCache : MAAnnotationView
/**
* Integrates SDWebImage async downloading and caching of remote images with MAAnnotationView.
*/
@interfaceMAAnnotationView (WebCache)
/**
* Get the current image URL.
*
* Note that because of the limitations of categories this property can get out of sync
* if you use sd_setImage: directly.
*/
- (NSURL*)sd_imageURL;
/**
* Set the imageView `image` with an `url`.
*
* The download is asynchronous and cached.
*
* @param url The url for the image.
*/
- (void)sd_setImageWithURL:(NSURL*)url;
/**
* Set the imageView `image` with an `url` and a placeholder.
*
* The download is asynchronous and cached.
*
* @param urlThe url for the image.
* @param placeholder The image to be set initially, until the image request finishes.
* @see sd_setImageWithURL:placeholderImage:options:
*/
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder;
/**
* Set the imageView `image` with an `url`, placeholder and custom options.
*
* The download is asynchronous and cached.
*
* @param urlThe url for the image.
* @param placeholder The image to be set initially, until the image request finishes.
* @param optionsThe options to use when downloading the image. @see SDWebImageOptions for the possible values.
*/
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder options:(SDWebImageOptions)options;
/**
* Set the imageView `image` with an `url`.
*
* The download is asynchronous and cached.
*
* @param urlThe url for the image.
* @param completedBlock A block called when operation has been completed. This block has no return value
*and takes the requested UIImage as first parameter. In case of error the image parameter
*is nil and the second parameter may contain an NSError. The third parameter is a Boolean
*indicating if the image was retrived from the local cache or from the network.
*The fourth parameter is the original image url.
*/
- (void)sd_setImageWithURL:(NSURL*)url completed:(SDWebImageCompletionBlock)completedBlock;
/**
* Set the imageView `image` with an `url`, placeholder.
*
* The download is asynchronous and cached.
*
* @param urlThe url for the image.
* @param placeholderThe image to be set initially, until the image request finishes.
* @param completedBlock A block called when operation has been completed. This block has no return value
*and takes the requested UIImage as first parameter. In case of error the image parameter
*is nil and the second parameter may contain an NSError. The third parameter is a Boolean
*indicating if the image was retrived from the local cache or from the network.
*The fourth parameter is the original image url.
*/
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder completed:(SDWebImageCompletionBlock)completedBlock;
/**
* Set the imageView `image` with an `url`, placeholder and custom options.
*
* The download is asynchronous and cached.
*
* @param urlThe url for the image.
* @param placeholderThe image to be set initially, until the image request finishes.
* @param optionsThe options to use when downloading the image. @see SDWebImageOptions for the possible values.
* @param completedBlock A block called when operation has been completed. This block has no return value
*and takes the requested UIImage as first parameter. In case of error the image parameter
*is nil and the second parameter may contain an NSError. The third parameter is a Boolean
*indicating if the image was retrived from the local cache or from the network.
*The fourth parameter is the original image url.
*/
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder options:(SDWebImageOptions)options completed:(SDWebImageCompletionBlock)completedBlock;
/**
* Cancel the current download
*/
- (void)sd_cancelCurrentImageLoad;
@end
MAAnnotationView+WebCache.m
#import"MAAnnotationView+WebCache.h"
#import"objc/runtime.h"
#import"UIView+WebCacheOperation.h"
staticcharimageURLKey;
@implementationMAAnnotationView (WebCache)
- (NSURL*)sd_imageURL {
returnobjc_getAssociatedObject(self, &imageURLKey);
}
- (void)sd_setImageWithURL:(NSURL*)url {
[selfsd_setImageWithURL:urlplaceholderImage:niloptions:0completed:nil];
}
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder {
[selfsd_setImageWithURL:urlplaceholderImage:placeholderoptions:0completed:nil];
}
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder options:(SDWebImageOptions)options {
[selfsd_setImageWithURL:urlplaceholderImage:placeholderoptions:optionscompleted:nil];
}
- (void)sd_setImageWithURL:(NSURL*)url completed:(SDWebImageCompletionBlock)completedBlock {
[selfsd_setImageWithURL:urlplaceholderImage:niloptions:0completed:completedBlock];
}
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder completed:(SDWebImageCompletionBlock)completedBlock {
[selfsd_setImageWithURL:urlplaceholderImage:placeholderoptions:0completed:completedBlock];
}
- (void)sd_setImageWithURL:(NSURL*)url placeholderImage:(UIImage*)placeholder options:(SDWebImageOptions)options completed:(SDWebImageCompletionBlock)completedBlock {
[selfsd_cancelCurrentImageLoad];
objc_setAssociatedObject(self, &imageURLKey, url,OBJC_ASSOCIATION_RETAIN_NONATOMIC);
self.image= placeholder;
if(url) {
__weakMAAnnotationView*wself =self;
id operation = [SDWebImageManager.sharedManagerdownloadImageWithURL:urloptions:optionsprogress:nilcompleted:^(UIImage*image,NSError*error,SDImageCacheTypecacheType,BOOLfinished,NSURL*imageURL) {
if(!wself)return;
dispatch_main_sync_safe(^{
__strongMAAnnotationView *sself = wself;
if(!sself)return;
if(image) {
sself.image = image;
}
if(completedBlock && finished) {
completedBlock(image, error, cacheType, url);
}
});
}];
[selfsd_setImageLoadOperation:operationforKey:@"MAAnnotationViewImage"];
}else{
dispatch_main_async_safe(^{
NSError *error = [NSError errorWithDomain:@"SDWebImageErrorDomain"code:-1userInfo:@{NSLocalizedDescriptionKey :@"Trying to load a nil url"}];
if(completedBlock) {
completedBlock(nil, error, SDImageCacheTypeNone, url);
}
});
}
}
- (void)sd_cancelCurrentImageLoad {
[selfsd_cancelImageLoadOperationWithKey:@"MAAnnotationViewImage"];
}
@end
写这个类别的前提的导入SDWebImgage
写好这个之后,导入头文件就可以使用了
PS:我遇到了一个问题:加载相同的图标,本地的和网络的,网络的会变大,查阅资料后,网络图片后缀名加上@2X或@3X,就可以了。