该文章阅读的SDWebImage的版本为4.3.3。
这个分类提供了为UIButton
设置网络图像的快捷方法。
1.公共方法
1.1.设置image的方法
/** 获取当前图像链接地址 */- (nullable NSURL *)sd_currentImageURL;复制代码
/** 获取指定状态图像链接地址 */- (nullable NSURL *)sd_imageURLForState:(UIControlState)state;复制代码
/** 设置指定状态的图像链接地址 */- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的图像链接地址和占位图 */- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的图像链接地址和占位图以及可选项 */- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的图像链接地址和完成回调 */- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state completed:(nullable SDExternalCompletionBlock)completedBlock;复制代码
/** 设置指定状态的图像链接地址和占位图以及完成回调 */- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder completed:(nullable SDExternalCompletionBlock)completedBlock NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的图像链接地址、占位图、可选项以及完成回调 */- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options completed:(nullable SDExternalCompletionBlock)completedBlock;复制代码
1.2.设置background image的方法
/** 获取当前背景图像链接地址 */- (nullable NSURL *)sd_currentBackgroundImageURL;/** 获取指定状态背景图像链接地址 */- (nullable NSURL *)sd_backgroundImageURLForState:(UIControlState)state;/** 设置指定状态的背景图像链接地址 */- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的背景图像链接地址和占位图 */- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的背景图像链接地址和占位图以及可选项 */- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的背景图像链接地址和占位图以及完成回调 */- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state completed:(nullable SDExternalCompletionBlock)completedBlock;复制代码
/** 设置指定状态的背景图像链接地址和占位图以及完成回调 */- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder completed:(nullable SDExternalCompletionBlock)completedBlock NS_REFINED_FOR_SWIFT;复制代码
/** 设置指定状态的背景图像链接地址、占位图、可选项以及完成回调 */- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options completed:(nullable SDExternalCompletionBlock)completedBlock;复制代码
1.3.取消网络图像加载的方法
/** 取消指定状态当前图像的网络加载 */- (void)sd_cancelImageLoadForState:(UIControlState)state;复制代码
/** 取消指定状态当前背景图像的网络加载 */- (void)sd_cancelBackgroundImageLoadForState:(UIControlState)state;复制代码
2.私有静态函数
/** 获取指定状态的图像链接键 */static inline NSString * imageURLKeyForState(UIControlState state) { return [NSString stringWithFormat:@"image_%lu", (unsigned long)state];}复制代码
/** 获取指定状态的背景图像链接键 */static inline NSString * backgroundImageURLKeyForState(UIControlState state) { return [NSString stringWithFormat:@"backgroundImage_%lu", (unsigned long)state];}复制代码
/** 获取指定状态的图像选项键 */static inline NSString * imageOperationKeyForState(UIControlState state) { return [NSString stringWithFormat:@"UIButtonImageOperation%lu", (unsigned long)state];}复制代码
/** 获取指定状态的背景图像选项键 */static inline NSString * backgroundImageOperationKeyForState(UIControlState state) { return [NSString stringWithFormat:@"UIButtonBackgroundImageOperation%lu", (unsigned long)state];}复制代码
3.私有方法
/** 获取保存图像链接的字典对象 */- (SDStateImageURLDictionary *)sd_imageURLStorage { SDStateImageURLDictionary *storage = objc_getAssociatedObject(self, &imageURLStorageKey); if (!storage) { storage = [NSMutableDictionary dictionary]; objc_setAssociatedObject(self, &imageURLStorageKey, storage, OBJC_ASSOCIATION_RETAIN_NONATOMIC); } return storage;}复制代码
4.实现
4.1.设置image的方法实现
- (nullable NSURL *)sd_currentImageURL { // 获取当前状态的图像地址 NSURL *url = self.sd_imageURLStorage[imageURLKeyForState(self.state)]; // 如果没有就获取普通状态的图像地址 if (!url) { url = self.sd_imageURLStorage[imageURLKeyForState(UIControlStateNormal)]; } return url;}- (nullable NSURL *)sd_imageURLForState:(UIControlState)state { // 获取指定状态的图像地址 return self.sd_imageURLStorage[imageURLKeyForState(state)];}- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state { // 调用全能方法 [self sd_setImageWithURL:url forState:state placeholderImage:nil options:0 completed:nil];}- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder { // 调用全能方法 [self sd_setImageWithURL:url forState:state placeholderImage:placeholder options:0 completed:nil];}- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options { [self sd_setImageWithURL:url forState:state placeholderImage:placeholder options:options completed:nil];}- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state completed:(nullable SDExternalCompletionBlock)completedBlock { // 调用全能方法 [self sd_setImageWithURL:url forState:state placeholderImage:nil options:0 completed:completedBlock];}- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder completed:(nullable SDExternalCompletionBlock)completedBlock { // 调用全能方法 [self sd_setImageWithURL:url forState:state placeholderImage:placeholder options:0 completed:completedBlock];}- (void)sd_setImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options completed:(nullable SDExternalCompletionBlock)completedBlock { if (!url) { // 不传链接就移除掉指定状态对应的值 [self.sd_imageURLStorage removeObjectForKey:imageURLKeyForState(state)]; } else { // 根据指定状态保存链接 self.sd_imageURLStorage[imageURLKeyForState(state)] = url; } // 调用UIView+WebCache分类方法加载图像 __weak typeof(self)weakSelf = self; [self sd_internalSetImageWithURL:url placeholderImage:placeholder options:options operationKey:imageOperationKeyForState(state) setImageBlock:^(UIImage *image, NSData *imageData) { [weakSelf setImage:image forState:state]; } progress:nil completed:completedBlock];}复制代码
4.2.设置background image的方法实现
- (nullable NSURL *)sd_currentBackgroundImageURL { // 获取当前状态的背景图像地址 NSURL *url = self.sd_imageURLStorage[backgroundImageURLKeyForState(self.state)]; // 如果没有就获取普通状态的背景图像地址 if (!url) { url = self.sd_imageURLStorage[backgroundImageURLKeyForState(UIControlStateNormal)]; } return url;}- (nullable NSURL *)sd_backgroundImageURLForState:(UIControlState)state { // 获取指定状态的背景图像地址 return self.sd_imageURLStorage[backgroundImageURLKeyForState(state)];}- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state { // 调用全能方法 [self sd_setBackgroundImageWithURL:url forState:state placeholderImage:nil options:0 completed:nil];}- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder { // 调用全能方法 [self sd_setBackgroundImageWithURL:url forState:state placeholderImage:placeholder options:0 completed:nil];}- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options { // 调用全能方法 [self sd_setBackgroundImageWithURL:url forState:state placeholderImage:placeholder options:options completed:nil];}- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state completed:(nullable SDExternalCompletionBlock)completedBlock { // 调用全能方法 [self sd_setBackgroundImageWithURL:url forState:state placeholderImage:nil options:0 completed:completedBlock];}- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder completed:(nullable SDExternalCompletionBlock)completedBlock { // 调用全能方法 [self sd_setBackgroundImageWithURL:url forState:state placeholderImage:placeholder options:0 completed:completedBlock];}- (void)sd_setBackgroundImageWithURL:(nullable NSURL *)url forState:(UIControlState)state placeholderImage:(nullable UIImage *)placeholder options:(SDWebImageOptions)options completed:(nullable SDExternalCompletionBlock)completedBlock { if (!url) { // 不传链接就移除掉指定状态对应的值 [self.sd_imageURLStorage removeObjectForKey:backgroundImageURLKeyForState(state)]; } else { // 根据指定状态保存链接 self.sd_imageURLStorage[backgroundImageURLKeyForState(state)] = url; } // 调用UIView+WebCache分类方法加载背景图像 __weak typeof(self)weakSelf = self; [self sd_internalSetImageWithURL:url placeholderImage:placeholder options:options operationKey:backgroundImageOperationKeyForState(state) setImageBlock:^(UIImage *image, NSData *imageData) { [weakSelf setBackgroundImage:image forState:state]; } progress:nil completed:completedBlock];}复制代码
4.3.取消网络图像加载的方法实现
- (void)sd_cancelImageLoadForState:(UIControlState)state { // 取消指定key的图像加载操作 [self sd_cancelImageLoadOperationWithKey:imageOperationKeyForState(state)];}- (void)sd_cancelBackgroundImageLoadForState:(UIControlState)state { // 取消指定key的背景图像加载操作 [self sd_cancelImageLoadOperationWithKey:backgroundImageOperationKeyForState(state)];}复制代码
源码阅读系列:SDWebImage