在這里需要兩對文件
1.在第一個.h文件內(nèi)寫兩個Block參數(shù)和一個代理協(xié)議
第一個參數(shù):正在下載
typedef void (^Downloading)(long long bytesWritten,float progress);
第二個參數(shù):下載完成
typedef void (^Complete)(NSString *filePath,NSString *url);
自寫代理協(xié)議及方法
@protocol DownloadDelegate<NSObject>
- (void)didFinishDownload:(NSString *)url
@end
@interface Download :NSObject
設置你聲明的代理屬性
@property (nonatomic,weak)id<DownloadDelegate>delegate;
?自定義init方法,在初始化的時候就去創(chuàng)建一個下載任務
- (instancetype)initWithUrl:(NSString *)url;
?開始下載
- (void)startDownload;
?暫停下載
- (void)stopDownload;
?下載的時候和下載完成會走其中的Block
- (void)downloading:(Downloading)downloading didFinished:(Complete)Complete;
@end
2.在第一個.m文件內(nèi)實現(xiàn)這些方法
在這里會使用NSURLSession下的一些方法
#import "Download.h"
遵守一個代理
@interface Download ()<NSURLSessionDownloadDelegate>
聲明屬性
@property (nonatomic,strong) NSURLSession *session;
下載任務
@property (nonatomic,strong) NSURLSessionDownloadTask *task;?
正在下載
@property (nonatomic, copy)Downloading downloading;
下載完成
@property (nonatomic,strong) Complete complete;
@end
@implementation Download
寫個懶加載
- (NSURLSession *)session{
? ? if (!_session){
_session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]delegate:self delegateQueue:nil];
? ? }
?return _session;
}
自定義init方法,在初始化的時候就去創(chuàng)建一個下載任務
- (instancetype)initWithUrl:(NSString *)url{
? ? if ([super init]) {
? ? ? // 創(chuàng)建一個下載任務
? ? ? self.task = [self.session downloadTaskWithURL:[NSURL URLWithString:url]];
? ? }
return self;
}
開始下載
- (void)startDownload{
? ? [self.task resume];
}
暫停下載
- (void)stopDownload{
[self.task suspend];
}
正在下載
這是NSURLSession自帶的一個方法慌随,里面的參數(shù)downloadTask:下載任務角雷,didWriteData:寫入數(shù)據(jù),totalBytesWritten:已經(jīng)寫入總的數(shù)據(jù),totalBytesExpectedToWrite:預計寫的總數(shù)據(jù)
- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didWriteData:(int64_t)bytesWritten totalBytesWritten:(int64_t)totalBytesWritten totalBytesExpectedToWrite:(int64_t)totalBytesExpectedToWrite {
?if (self.downloading){
self.downloading(bytesWritten,100*totalBytesWritten/(float)totalBytesExpectedToWrite);
? ?}
}
下載完成
- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didFinishDownloadingToURL:(NSURL *)location {
// 我們要存放下載文件的路徑
NSString *filePath = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES).lastObject;
// 拼接文件的名字,名字是從服務器上獲取下來的
NSString *fileName = downloadTask.response.suggestedFilename;
filePath = [filePath stringByAppendingPathComponent:fileName];
// 文件管理器慎菲,把臨時的文件移動到緩存文件夾下
[[NSFileManager defaultManager] moveItemAtPath:location.path toPath:filePath error:nil];
NSLog(@"%@",filePath);
if (self.complete) {
self.complete(filePath,@"網(wǎng)址");
? ?}
}
下載的時候和下載完成會走其中的Block
- (void)downloading:(Downloading)downloading didFinished:(Complete)Complete {
self.downloading = downloading;
self.complete = Complete;
}
第二個文件的.h內(nèi)
#import<Foundation/Foundation.h>
@interface DownloadCoreData : NSObject
+ (instancetype)sharedManager;
- (Download *)addDownloadWithUrl:(NSString *)url;
- (Download *)findDownloadWithUrl:(NSString *)url;
- (void)didFinishDownload:(NSString *)url;
@end
第二個文件的.m內(nèi)
#import "DownloadCoreData.h"
遵守上個文件寫的代理
@interface DownloadCoreData ()<DownloadDelegate>
聲明一個字典屬性
@property (nonatomic,strong)NSMutableDictionary *dic;
@end
@implementation DownloadCoreData
懶加載
- (NSMutableDictionary *)dic{
? if (!_dic) {
_dic = [NSMutableDictionary dictionary]; ?
? ? }
return _dic;
}
GCD單例
+ (instancetype)sharedManager {
static DownloadCoreData *handle = nil;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
handle = [[DownloadCoreData alloc]init];
? ?});
return handle;
}
- (Download *)addDownloadWithUrl:(NSString *)url {
Download *download = [[Download alloc]initWithUrl:url];
download.delegate = self;
[download startDownload];
[self.dic setObject:download forKey:url];
return download;
? }
- (Download *)findDownloadWithUrl:(NSString *)url {
return self.dic[url];
}
- (void)didFinishDownload:(NSString *)url {
[self.dic removeObjectForKey:url];
}
@end