You need to enable JavaScript to run this app.
导航
下载视频
最近更新时间:2025.11.20 16:07:28首次发布时间:2023.06.09 16:39:31
复制全文
我的收藏
有用
有用
无用
无用

播放器 SDK 支持下载功能。用户可在有网络的条件下将视频下载至本地,随后在无网络的环境下观看。播放器 SDK 支持下载 DirectUrl 视频源和 Vid 视频源,并提供开始、暂停、恢复、删除等控制下载任务的方法。本文介绍如何接入播放器 SDK 的下载功能,包含功能介绍、前提条件、集成步骤等内容。

注意

如需下载 HLS 视频,请集成 iOS 播放器 SDK 1.37.1.7 或以上版本。

初始化下载功能

使用下载功能前,您需要先在播放器 SDK 初始化过程中对下载功能进行一些必要的配置,例如是否开启下载 HLS 视频的能力、设置下载路径。此外您还可以设置最大并发数和空闲磁盘空间大小的限制等。

注意

需要特别注意的是,初始化代码的时序对下载功能是否能正常工作有直接影响:

  • 如果您需要下载 HLS 视频,需要在初始化播放器 SDK 之前开启 HLSProxyModule,从而开启 HLS 下载功能。此方法必须在 [TTSDKManager startWithConfiguration:] 方法之前调用。
  • 设置下载文件存储路径,需要在 [TTSDKManager startWithConfiguration:] 方法之前调用。
  • 其他下载配置则需要在 [TTSDKManager startWithConfiguration:] 方法之后调用。

示例代码如下:

#import <TTSDKFramework/TTVideoEngine+Preload.h>
#import <TTSDKFramework/TTVideoEngine+Options.h>
#import <TTSDKFramework/TTVideoEngineDownloader.h>

- (void)initTTSDK {
    // 开启 HLS 下载功能。可选,如业务中无需下载 HLS 视频,可跳过。
    [[TTVideoEngine ls_localServerConfigure] setOptionForKey:@(VEKKeyHLSProxyProtocolEnable_BOOL) value:@YES];

    // 必填,设置下载文件存储路径
    // 注意:必须是沙盒可写存储路径,并且是绝对路径
    // 以下为存储路径示例,您也可以根据实际情况填写其他 app 可写路径
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
    NSString *cacheDir = [paths firstObject];
    [TTVideoEngine ls_localServerConfigure].downloadDirectory = [cacheDir stringByAppendingPathComponent:@"VideoDownload"];
   
    // 初始化播放器 SDK
    [TTSDKManager startWithConfiguration:configuration];
    
    // 选填,设置最大并发下载数,默认值为 1
    [TTVideoEngineDownloader shareLoader].maxDownloadOperationCount = 3;
    
    // 选填,设置空闲磁盘空间大小的限制,默认值 1 GB
    // 当前设为 1G,如果剩余磁盘大小不足 1G,则返回 TTVideoEngineErrorNotEnoughDiskSpace 错误
    [TTVideoEngineDownloader shareLoader].limitFreeDiskSize = 1024 * 1024 * 1024;
    
    // iOS 播放器 SDK 默认支持缓存最多 50 个视频,如业务超出此限制,需进行以下设置
    [TTVideoEngine setGlobalForKey:VEGSKeyPlayerVideoModelMaxCache_NSInteger value:@(500)];
}

创建下载任务

播放器 SDK 支持播放 DirectUrl 视频源和 Vid 视频源。与之对应,播放器 SDK 也提供了不同数据源的下载能力。创建新的下载任务之前,建议您调用 getAllTasksWithCompletionHandler 方法获取已有下载任务。播放器 SDK 会自动保存未完成的下载任务,在对应业务启动时调用可以获取先前被中断的下载任务。您可以在 getAllTasksWithCompletionHandler 的 block 中创建下载任务,以保证调用顺序。

说明

创建 DirectUrl 视频源下载任务

[[TTVideoEngineDownloader shareLoader] getAllTasksWithCompletionHandler:^(NSArray<__kindof TTVideoEngineDownloadTask *> * _Nonnull tasks) {
    TTVideoEngineDownloadURLTask *urlTask = [[TTVideoEngineDownloader shareLoader] urlTask:@[urlString] key:key videoId:nil];
    [urlTask resume];
  }];

创建 Vid 视频源下载任务

[[TTVideoEngineDownloader shareLoader] getAllTasksWithCompletionHandler:^(NSArray<__kindof TTVideoEngineDownloadTask *> * _Nonnull tasks) {
    TTVideoEngineDownloadVidTask *vidTask = [[TTVideoEngineDownloader shareLoader] vidTask:videoID playAuthToken:token resolution:TTVideoEngineResolutionTypeSD];
    [vidTask resume];
  }];

控制下载任务

通过以下方法控制单个下载任务:

// 开始/恢复单个下载任务。
// 支持断点续传。
[task resume];

// 暂停单个下载任务,支持断点续传。
// 此方法需要在主线程调用。
[task suspend];

// 删除单个下载任务。
// 下载任务被删除后,任务会停止,同时 TTVideoEngineDownloader 将不再管理这个任务。
// 此接口为异步操作,您需要在 `getAllTasksWithCompletionHandler` 的回调中检查是否被删除。
[task invalidateAndCancel];

通过以下方法控制所有下载任务:

// 暂停所有下载任务。
// 此方法必须在 `getAllTasksWithCompletionHandler` 之后调用。
- (void)suspendAllTasks;

// 开始/恢复所有下载任务。
// 此方法必须在 `getAllTasksWithCompletionHandler` 之后调用。
- (void)resumeAllTasks;

// 删除所有下载任务。
// 此方法必须在 `getAllTasksWithCompletionHandler` 之后调用。
- (void)removeAllTasks;

注意

下载任务删除后,该任务对应的视频文件也会被删除。

设置监听

下载任务的完成情况、进度和状态等信息都需要通过实现 TTVideoEngineDownloaderDelegate 中的方法来获取,示例代码如下:

// 设置回调接收
 [TTVideoEngineDownloader shareLoader].delegate = self;
/**
 * 下载任务完成回调。
 * @param downloadTask 当前下载任务。
 * @param error 错误。error 为 null 则为下载任务成功,否则为下载任务失败。详细信息,请见[错误码文档](https://www.volcengine.com/docs/4/66441)。
 * - TTVideoEngineErrorNetworkNotAvailable = -9960,//网络不可用
 * - TTVideoEngineErrorSaveTaskItem = -9949,
 * - TTVideoEngineErrorWriteFile = -9948,
 * - TTVideoEngineErrorNotEnoughDiskSpace = -9947,
 * - TTVideoEngineErrorURLUnavailable = -9945,
 * - TTVideoEngineErrorServiceInaccessible = -9944,
 * - TTVideoEngineErrorExistedTask = -9943,
 */
- (void)VideoEngineDownloader:(TTVideoEngineDownloader *)downloader
         downloadTask:(TTVideoEngineDownloadTask *)downloadTask
     didCompleteWithError:(nullable NSError *)error;

/**
 * 下载任务进度更新回调。
 * @param downloadTask 当前下载任务。
 *                 - downloadTask.countOfBytesReceived 当前下载任务已下载的数据总量(HLS 不适用,见下方注意点)
 *                 - downloadTask.countOfBytesExpectedToReceive 当前下载任务需要下载的总数据量(HLS 不适用,见下方注意点)
 *                 - downloadTask.progress 当前下载任务进度 0.0~1.0
 * @param  bytesWritten 本次回调新增下载的数据量,单位为 Byte。
* @param  timeMS 当前时间。
 */
- (void)VideoEngineDownloader:(TTVideoEngineDownloader *)downloader
         downloadTask:(TTVideoEngineDownloadTask *)downloadTask
          writeData:(int64_t)bytesWritten
         timeInterval:(double)timeMS;

/**
 * 下载任务开始/恢复回调。
 * @param downloadTask 当前下载任务。
 * @param  fileOffset 已下载的数据量。
 * @param  expectedTotalBytes 该任务要下载的总数据量。
 */
- (void)VideoEngineDownloader:(TTVideoEngineDownloader *)downloader
         downloadTask:(TTVideoEngineDownloadTask *)downloadTask
      didResumeAtOffset:(int64_t)fileOffset
      expectedTotalBytes:(int64_t)expectedTotalBytes;

/**
 * 下载任务状态变更回调。
 * @param downloadTask 当前下载任务。
 * @param  downloadState 当前下载任务状态:
 *                     - TTVideoEngineDownloadStateInit(0): 初始化。
 *                     - TTVideoEngineDownloadStateWaiting(1): 等待中。
 *                     - TTVideoEngineDownloadStateRunning(2): 运行中。
 *                     - TTVideoEngineDownloadStateSuspended(3): 暂停。
 *                     - TTVideoEngineDownloadStateCanceling(4): 正在取消。
 *                     - TTVideoEngineDownloadStateCompleted(5): 完成。
 */
- (void)VideoEngineDownloader:(TTVideoEngineDownloader *)downloader
         downloadTask:(TTVideoEngineDownloadTask *)downloadTask
         stateChanged:(TTVideoEngineDownloadState)downloadState;

注意

如果下载的媒体类型为 HLS(M3U8),SDK 无法知道整个视频的文件大小,回调中的 countOfBytesReceived 和 countOfBytesExpectedToReceive 数值并不准确。因此,对于 HLS(M3U8)您仅可以通过 - [TTVideoEngineDownloadTask progress] 获取下载的进度。

播放视频

SDK 内部已经处理了下载缓存与播放的关联关系。SDK 会优先播放已经下载的视频,即使它们尚未完全下载完成,因此您播放时无需额外设置。

播放 DirectUrl 视频源

参考以下示例代码播放 DirectUrl 视频源:

// 播放已下载的 HLS 视频前必须设置以下 option
[self.videoEngine setOptionForKey:VEKKeyIsAllowAllExtensions value:@1];

// 注意 cacheKey 与下载时使用的 cacheKey 一致
TTVideoEngineUrlSource *urlSource = [[TTVideoEngineUrlSource alloc] initWithUrl:videoUrl cacheKey:cacheKey];
[self.videoEngine setVideoEngineVideoSource:urlSource];
[self.videoEngine play];

播放 Vid 视频源

参考以下示例代码播放 Vid 视频源:

// 离线播放已下载的视频前必须设置以下 option 
[self.videoEngine setOptionForKey:VEKKeyModelCacheVideoInfoEnable_BOOL value:@(YES)];
[self.videoEngine setOptionForKey:VEKKeyPlayerVideoModelPriority_ENUM value:@(TTVideoEngineVideoModelUseLocal)];

// 播放已下载的 HLS 视频前必须设置以下 option
[self.videoEngine setOptionForKey:VEKKeyIsAllowAllExtensions value:@1];

// 注意 resolution 与下载时使用的 resolution 一致
TTVideoEngineVidSource *vidSource = [[TTVideoEngineVidSource alloc] initWithVid:vid playAuthToken:playAuthToken resolution:resolution];
[self.videoEngine setVideoEngineVideoSource:vidSource];
[self.videoEngine play];

常见问题

视频下载中断后无法恢复,该如何处理

  • 问题表现:进行视频下载时,如果中途发生断网,待网络恢复后调用 resume() 方法尝试恢复下载,会出现报错,错误码为 -9943。该错误码的含义是“任务已存在”。
  • 问题解决方案:针对上述问题,建议的解决方案是重新创建一个新的下载任务,具体步骤如下:
    1. 保存任务信息:在开始下载前,预先保存当前下载任务的关键信息,以便后续重新创建任务时使用。
      • 对于 URL 任务,至少需要保存视频的 URL
      • 对于 Vid 任务,至少需要保存 vidplayAuthToken
    2. 取消当前任务:当下载失败后,调用 [task invalidateAndCancel] 方法删除当前任务。SDK 会触发 VideoEngineDownloader:downloadTask:didCompleteWithError 的回调。
    3. 重新创建下载任务:在 didCompleteWithError 回调中,通过判断 error.code == TTVideoEngineErrorUserCancel 来确认任务是由用户(或代码逻辑)主动取消的。确认后,即可使用第一步中保存的任务信息,重新创建一个新的下载任务并开始下载。