zoukankan      html  css  js  c++  java
  • IOS 自定义Operation(下载功能)

     一个下载操作就交给一个HMDownloadOperation对象

    HMDownloadOperation.h / .m

    @class HMDownloadOperation;
    
    @protocol HMDownloadOperationDelegate <NSObject>
    @optional
    - (void)downloadOperation:(HMDownloadOperation *)operation didFinishDownload:(UIImage *)image;
    @end
    
    @interface HMDownloadOperation : NSOperation
    @property (nonatomic, copy) NSString *url;
    @property (nonatomic, strong) NSIndexPath *indexPath;
    @property (nonatomic, weak) id<HMDownloadOperationDelegate> delegate;
    @end
    View Code
    #import "HMDownloadOperation.h"
    
    @implementation HMDownloadOperation
    
    /**
     *  在main方法中实现具体操作
     */
    - (void)main
    {
        @autoreleasepool {
            
            NSURL *downloadUrl = [NSURL URLWithString:self.url];
            NSData *data = [NSData dataWithContentsOfURL:downloadUrl]; // 这行会比较耗时
            UIImage *image = [UIImage imageWithData:data];
    
            if ([self.delegate respondsToSelector:@selector(downloadOperation:didFinishDownload:)]) {
                dispatch_async(dispatch_get_main_queue(), ^{ // 回到主线程, 传递图片数据给代理对象
                    [self.delegate downloadOperation:self didFinishDownload:image];
                });
            }
        }
    }
    View Code

    控制器View 调用

    @interface HMViewController () <HMDownloadOperationDelegate>
    @property (nonatomic, strong) NSArray *apps;
    @property (nonatomic, strong) NSOperationQueue *queue;
    /** key:url value:operation对象 */
    @property (nonatomic, strong) NSMutableDictionary *operations;
    
    /** key:url value:image对象*/
    @property (nonatomic, strong) NSMutableDictionary *images;
    @end
    
    @implementation HMViewController
    
    - (NSArray *)apps
    {
        if (!_apps) {
            NSArray *dictArray = [NSArray arrayWithContentsOfFile:[[NSBundle mainBundle] pathForResource:@"apps.plist" ofType:nil]];
            
            NSMutableArray *appArray = [NSMutableArray array];
            for (NSDictionary *dict in dictArray) {
                HMApp *app = [HMApp appWithDict:dict];
                [appArray addObject:app];
            }
            _apps = appArray;
        }
        return _apps;
    }
    
    - (NSOperationQueue *)queue
    {
        if (!_queue) {
            _queue = [[NSOperationQueue alloc] init];
            _queue.maxConcurrentOperationCount = 3; // 最大并发数 == 3
        }
        return _queue;
    }
    
    - (NSMutableDictionary *)operations
    {
        if (!_operations) {
            _operations = [NSMutableDictionary dictionary];
        }
        return _operations;
    }
    
    - (NSMutableDictionary *)images
    {
        if (!_images) {
            _images = [NSMutableDictionary dictionary];
        }
        return _images;
    }
    
    - (void)viewDidLoad
    {
        [super viewDidLoad];
        
    }
    
    #pragma mark - 数据源方法
    - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
    {
        return self.apps.count;
    }
    
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
        static NSString *ID = @"app";
        UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
        if (!cell) {
            cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:ID];
        }
        
        HMApp *app = self.apps[indexPath.row];
        cell.textLabel.text = app.name;
        cell.detailTextLabel.text = app.download;
        
        // 显示图片
        // 保证一个url对应一个HMDownloadOperation
        // 保证一个url对应UIImage对象
        
        UIImage *image = self.images[app.icon];
        if (image) { // 缓存中有图片
            cell.imageView.image = image;
        } else { // 缓存中没有图片, 得下载
            cell.imageView.image = [UIImage imageNamed:@"57437179_42489b0"];
            
            HMDownloadOperation *operation = self.operations[app.icon];
            if (operation) { // 正在下载
                // ... 暂时不需要做其他事
                
            } else { // 没有正在下载
                // 创建操作
                operation = [[HMDownloadOperation alloc] init];
                operation.url = app.icon;
                operation.delegate = self;
                operation.indexPath = indexPath;
                [self.queue addOperation:operation]; // 异步下载
                
                self.operations[app.icon] = operation;
            }
        }
        
        // SDWebImage : 专门用来下载图片
        return cell;
    }
    
    #pragma mark - HMDownloadOperationDelegate
    - (void)downloadOperation:(HMDownloadOperation *)operation didFinishDownload:(UIImage *)image
    {
        // 1.移除执行完毕的操作
        [self.operations removeObjectForKey:operation.url];
        
        if (image) {
            // 2.将图片放到缓存中(images)
            self.images[operation.url] = image;
            
            // 3.刷新表格
            [self.tableView reloadRowsAtIndexPaths:@[operation.indexPath] withRowAnimation:UITableViewRowAnimationNone];
            
            // 3.将图片写入沙盒
    //        NSData *data = UIImagePNGRepresentation(image);
    //        [data writeToFile:@"" atomically:<#(BOOL)#>];
        }
        
    }
    
    - (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView
    {
        // 开始拖拽
        // 暂停队列
        [self.queue setSuspended:YES];
    }
    
    - (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset
    {
        [self.queue setSuspended:NO];
    }
    
    @end
  • 相关阅读:
    22 组合电路中的竞争--冒险
    21 典型的组合电路模块(2)
    vhdl和verilog的区别
    17 TTL电路系列(2)
    树莓派Pico
    ESP8266/ESP32自动下载电路原理分析
    CH340芯片
    26. 删除排序数组中的重复项
    25. K 个一组翻转链表
    23. 合并K个排序链表
  • 原文地址:https://www.cnblogs.com/liuwj/p/6605514.html
Copyright © 2011-2022 走看看