zoukankan      html  css  js  c++  java
  • AVPlayer中的问题

    AVPlayer的播放功能封装

    在.h中写方法的声明

    - (void)playWithString:(NSString *)musicUrlStr durationBlock:(void(^)(CMTime duration))durationBlock currentBlock:(void(^)(CMTime cuttentTime))currentBlock;

    注:

    durationBlock:回调播放器播放总时长

    currentBlock:回调播放器当前播放时长

    在.m中写方法的实现

    @property(nonatomic, strong)AVPlayer *player;

    //Block属性, 能在.m中全局使用

    @property(nonatomic, copy)void(^durationBlock)(CMTime duration);

    - (void)playWithString:(NSString *)musicUrlStr durationBlock:(void(^)(CMTime duration))durationBlock currentBlock:(void(^)(CMTime cuttentTime))currentBlock{

        //如果不存在player, 第一次时会创建

        if (!_player) {

            //AVPlayer 既可以播放远程的, 也可以播放本地的

            //既可以播放视频, 也可以播放音频

            //如果播放视频, 需要创建显示层 AVPlayerLayer

            self.player = [[AVPlayer alloc] initWithURL:[NSURL URLWithString:musicUrlStr]];

            //播放

            [_player play];

            //总时长, CMTime 是结构体类型

            //属性接收局部变量, 能在全局使用

            self.durationBlock = durationBlock;

            //KVO 检测播放器播放总时长

            [self.player addObserver:self forKeyPath:@"currentItem.duration" options:NSKeyValueObservingOptionNew context:nil];

            //当前时长 self.player.currentTime 不能用KVO检测  

           //Not key-value observable; use -addPeriodicTimeObserverForInterval:queue:usingBlock: instead.

            CMTime time = CMTimeMake(1, 1);//每1秒, 显示一次

            [self.player addPeriodicTimeObserverForInterval:time queue:dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0) usingBlock:^(CMTime time) {

                //回调当前时长

                //在主线程内完成回调

                dispatch_async(dispatch_get_main_queue(), ^{

                    currentBlock(time);

                });

            }];

            //监听播放结束

            [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(playToEnd:) name:AVPlayerItemDidPlayToEndTimeNotification object:nil];

        }else{

            //已经存在player, 替换播放 Item

            AVPlayerItem *item = [AVPlayerItem playerItemWithURL:[NSURL URLWithString:musicUrlStr]];

            [self.player replaceCurrentItemWithPlayerItem:item];

            [self.player play];

            self.durationBlock = durationBlock;

        }

    }

    //KVO 触发方法

    - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSString *,id> *)change context:(void *)context{

    //self.player.currentItem.duration 返回的是nan, 表示无穷大, 是因为timescale为0

    //如果是nan, 不回调

        if (self.player.currentItem.duration.timescale != 0) {

            self.durationBlock(self.player.currentItem.duration);

        }

    }

    注:CMTimeGetSeconds(self.player.currentItem.duration) 能直接得到总时间的秒数, 等价于

    self.player.currentItem.duration.value / self.player.currentItem.duration.timescale

    让播放器在某个时间点开始播放的方法:

    声明:

    - (void)seekToTime:(float)percent;//在指定的时间点播放, 用于slide滑动

    实现:

    - (void)seekToTime:(float)percent{

        CMTime time = CMTimeMake(percent * CMTimeGetSeconds(self.player.currentItem.duration), 1);

        [self pause];

        [self.player seekToTime:time completionHandler:^(BOOL finished) {

            [self.player play];

        }];

    }

  • 相关阅读:
    Forms身份验证
    常见的js图片或内轮换效果
    模仿select选择框
    基于jquery的js幻灯片类
    js弹出幕布遮罩层
    css那些事
    选择珠宝js业务逻辑源码
    aspnet帐号密码改了会出问题
    用rails做了个书评排行网站,欢迎光临!
    转发:为什么函数式编程至关重要
  • 原文地址:https://www.cnblogs.com/YhhMzl/p/5140622.html
Copyright © 2011-2022 走看看