博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
AVFoundation | 封装一个好用的视频播放器
阅读量:5875 次
发布时间:2019-06-19

本文共 6122 字,大约阅读时间需要 20 分钟。

一:简介

AVFoundation是苹果在iOS和OS X系统中用于处理基于时间的媒体数据的Objective-C框架. 供使用者来开发媒体类型的应用程序。

上图是iOS系统下媒体应用的结构层. AVKit框架用于简化媒体应用的创建过程,如果你只需要看电影,那么使用这个就可以了, UKit可以支持简单的录制功能 . 而更多功能需要低层级框架支持.下面简单介绍下AVFoundation内最主要的支撑框架和其提供的功能。

  • CoreAudio : 处理所有音频事件.是由多个框架整合在一起的总称,为音频和MIDI内容的录制,播放和处理提供相应接口.设置可以针对音频信号进行完全控制,并通过Audio Units来构建一些复杂的音频处理.有兴趣的可以单独了解一下这个框架。

  • CoreMedia: 是AVFoundation所用到低层级媒体管道的一部分.提供音频样本和视频帧处理所需的低层级数据类型和接口。

  • CoreAnimation: 动画相关框架, 封装了支持OpenGL和OpenGL ES功能的ObjC各种类. AVFoundation可以利用CoreAnimation让开发者能够在视频的编辑和播放过程中添加动画和图片效果。

下面我就和大家详细的分享一下,如何使用AVFoundation来实现一个好用的视频播放器。如果好用或者对你有所帮助,不要忘了关注点个赞呦!!!

二:实现思路分析

  1. 视频控制界面实现

  2. 用于视频显示的View创建

  3. 视频数据下载器FBYVideoDownload创建

  4. 播放、暂停、横竖屏操作方法实现

  5. 监听播放进度

  6. 控制存储缓冲范围

  7. 拖动滑块,控制快进快退

  8. 定义临时文件路径

  9. 定义缓存文件夹路径

  10. 发起视频路径网路请求方法

  11. 播放结束设置

  12. 前后视频播放控制

三:实现源码分析

根据实现思路分析,一步步进行编码实现:

1. 视频控制界面实现

- (FBYVideoPlayerView *)videoPlayControl{    if (!_videoPlayControl) {        _videoPlayControl = [[FBYVideoPlayerView alloc] initWithFrame:self.backgroundView.bounds];        [self.backgroundView addSubview:_videoPlayControl];            }    return _videoPlayControl;}复制代码

2. 用于视频显示的View创建

- (UIView *)videoShowView{    if (!_videoShowView) {        _videoShowView = [[UIView alloc] init];        _videoShowView.layer.masksToBounds = YES;        [self.backgroundView addSubview:_videoShowView];    }    return _videoShowView;}复制代码

3. 视频数据下载器FBYVideoDownload创建

@property(nonatomic, weak) id 
delegate;//定义初始化方法 传入videoUrl参数(NSString)- (instancetype)initWithURL:(NSString *)videoUrl withDelegate:(id)delegate;//开始下载- (void)start;//暂停- (void)suspend;//关闭- (void)cancel;复制代码

4. 播放、暂停、横竖屏操作方法实现

//全屏        [_videoPlayControl setFullScreenButtonClick_block:^{            if (weakSelf.delegate && [weakSelf.delegate respondsToSelector:@selector(videoPlayerDidFullScreenButtonClick)]) {                [weakSelf.delegate videoPlayerDidFullScreenButtonClick];            }        }];        //播放/暂停        [_videoPlayControl setPlayButtonClick_block:^(BOOL play) {            if (play) {                [weakSelf.player play];            }else{                [weakSelf.player pause];            }            weakSelf.playButtonState = !weakSelf.playButtonState;        }];复制代码

5. 监听播放进度

self.timeObserve = [self.player addPeriodicTimeObserverForInterval:CMTimeMake(1, 1) queue:dispatch_get_main_queue() usingBlock:^(CMTime time) {        CGFloat current = CMTimeGetSeconds(time);        CGFloat total = CMTimeGetSeconds(weakSelf.currentPlayerItem.duration);        CGFloat progress = current / total;                weakSelf.videoPlayControl.currentTime = current;        weakSelf.videoPlayControl.playValue = progress;                if (weakSelf.isCanToGetLocalTime) {            weakSelf.localTime = [weakSelf getLocalTime];        }        NSInteger timeNow = [weakSelf getLocalTime];        if (timeNow - weakSelf.localTime > 1.5) {            [weakSelf.videoPlayControl videoPlayerDidBeginPlay];            weakSelf.isCanToGetLocalTime = YES;        }    }];复制代码

6. 监听播放器的状态

[self.currentPlayerItem addObserver:self forKeyPath:@"status" options:NSKeyValueObservingOptionNew context:nil];复制代码

7. 监听当前的缓冲进度

[self.currentPlayerItem addObserver:self forKeyPath:@"loadedTimeRanges" options:NSKeyValueObservingOptionNew context:nil];复制代码

8. 监听到当前没有缓冲数据

[self.currentPlayerItem addObserver:self forKeyPath:@"playbackBufferEmpty" options:NSKeyValueObservingOptionNew context:nil];复制代码

9. 控制存储缓冲范围

- (void)playForActivity{    if (self.playButtonState) {        [self.player play];    }    self.isBufferEmpty = NO;    self.isPlaying = YES;    [self.videoPlayControl videoPlayerDidBeginPlay];}复制代码

10. 拖动滑块,控制快进快退

//拖动滑块[_videoPlayControl setSliderTouchEnd_block:^(CGFloat time) {            [weakSelf seekToTimePlay:time];        }];        //快进快退[_videoPlayControl setFastFastForwardAndRewind_block:^(CGFloat time) {            [weakSelf seekToTimePlay:time];        }];复制代码

11. 定义临时文件路径

self.videoTempPath = [NSString tempFilePathWithFileName:videoName];复制代码

12. 定义缓存文件夹路径

self.videoCachePath = [NSString cacheFilePathWithName:videoName];复制代码

13. 发起视频路径网路请求方法

- (void)sendHttpRequst{    [_fileHandle seekToEndOfFile];    NSURL *url = [NSURL URLWithString:_videoUrl];    NSMutableURLRequest *requeset = [NSMutableURLRequest requestWithURL:url];        //指定头信息  当前已下载的进度    [requeset setValue:[NSString stringWithFormat:@"bytes=%ld-", _curruentLength] forHTTPHeaderField:@"Range"];        //创建请求    NSURLSessionDataTask *dataTask = [self.session dataTaskWithRequest:requeset];    self.dataTask = dataTask;        //发起请求    [self.dataTask resume];}复制代码

14. 播放结束设置

- (void)playerItemDidPlayToEnd:(NSNotification *)notification{    //重新开始播放    __weak typeof(self) weak_self = self;    [self.player seekToTime:CMTimeMake(0, 1) completionHandler:^(BOOL finished) {        __strong typeof(weak_self) strong_self = weak_self;        if (!strong_self) return;        [strong_self.player play];    }];}复制代码

15. 前后视频播放控制

//进入后台- (void)appDidEnterBackground{    if (self.stopWhenAppDidEnterBackground) {        [self pauseVideo];    }}//进入前台- (void)appDidEnterForeground{    [self playVideo];}复制代码

五:项目实际使用

1. 下载demo

下载demo,将demo中FBYVideoData文件夹引入项目中。

2. 在项目中引入FBYVideoPlayer并继承FBYVideoPlayerDelegate代理

#import "FBYVideoPlayer.h"@interface ViewController ()
@property (nonatomic ,strong) FBYVideoPlayer *videoPlayer;@property (nonatomic ,strong) UIView *videoPlayBGView;@property (nonatomic ,copy) NSString*videoUrl;@end复制代码

3. 初始化创建基层view

self.videoPlayBGView = [[UIView alloc] initWithFrame:CGRectMake(0, 90, SCREEN_WIDTH, SCREEN_WIDTH * 0.6)];self.videoPlayBGView.backgroundColor = [UIColor blackColor];    [self.view addSubview:self.videoPlayBGView];复制代码

4. 初始化调用视频播放方法

self.videoPlayer = [[FBYVideoPlayer alloc] init];self.videoPlayer.delegate = self;[self.videoPlayer playWithUrl:self.videoUrl showView:self.videoPlayBGView];复制代码

5. 初始化调用视频播放方法

self.videoPlayer = [[FBYVideoPlayer alloc] init];self.videoPlayer.delegate = self;[self.videoPlayer playWithUrl:self.videoUrl showView:self.videoPlayBGView];复制代码

本篇文章demo源码:

希望可以帮助大家,如有问题可加QQ技术交流群: 668562416 如果哪里有什么不对或者不足的地方,还望读者多多提意见或建议

如需转载请联系我,经过授权方可转载,谢谢

本篇已同步到个人博客:


欢迎关注我的公众号:网罗开发

你可能感兴趣的文章
QTP学习笔记1
查看>>
【Linux网络编程】广播地址介绍
查看>>
iOS8新特性扩展(Extension)应用之二——分享插件
查看>>
数据迁移工具sqoop入门
查看>>
JDBC编程 之 增删改查
查看>>
《高效程序员的修炼》 读书笔记
查看>>
Android Animation动画详解(二): 组合动画特效
查看>>
《Netty权威指南》目录
查看>>
iGraph 2015双促复盘总结
查看>>
Android 开发第一弹:倒计时
查看>>
Linux Mac之间文件传输
查看>>
(六)unsigned的用法
查看>>
iOS开发- 以图搜图功能实现 (源码+解析)
查看>>
二维码篇【一】【JS】使用jquery.qrcode生成二维码
查看>>
LevelDB:Bloom源码精读——数据结构
查看>>
一个设置访问权限的实例
查看>>
【Android】 banner+tab吸顶+viewpager切换+刷新加载之实现
查看>>
找零问题与动态规划
查看>>
Leetcode279完全平方数
查看>>
jTopo学习笔记5——动画
查看>>