iOS開發(fā)-視頻播放AVPlayer(AVPlayer的封裝臼朗、tableviewcell上視頻播放以及滑動播放暫停)

寫在前面寇损、感謝作者

使用AVPlayer自定義支持全屏的播放器http://www.reibang.com/p/11e05d684c05

仿微博視頻邊下邊播之滑動TableView自動播放

說明:本文使用的是第一篇文章作者的框架狼纬,加入第二篇文章作者的思路呀邢,實現(xiàn)了 在tabbleViewCell上播放視頻缤苫、滑動自動播放暫停以及對播放器的定制等等。注意:此處并不包含播放完成cell自動滑動的功能坛怪,這一點也不難淤齐,相信你學(xué)會了滑動自動播放,這一功能也就水到渠成了袜匿。

項目效果圖

關(guān)于制作GIF圖的一種方法請?zhí)D(zhuǎn)

videoPlay.gif

非常遺憾更啄,不滿足蘋果審核要求,項目遲遲未能上線居灯、不能被大家所下載

2017年7月11日 下午11:37
發(fā)件人 Apple
Guideline 3.2.2 - Business - Other Business Model Issues - Unacceptable

The feature in your app displays or promotes third-party apps, which is not appropriate for the App Store.

Please see attached screenshots for details.

Next Steps

To resolve this issue, please remove the feature from your app.

隱藏好像都已經(jīng)無可救藥了

2017年7月13日 下午8:37
發(fā)件人 Apple

  1. 2.2 Business: Other Business Model Issues - Unacceptable
    Guideline 3.2.2 - Business - Other Business Model Issues - Unacceptable

Your app displays or promotes third-party apps, which is not appropriate for the App Store.

Next Steps

We encourage you to review your app concept and incorporate different content and features that are in compliance with the App Store Review Guidelines.

對比 作者與我修改后的界面(我只是單純的修改了一下界面)

作者的界面:


author1.png
author2.png

我修改后的界面:


modify1.png
modify2.png

修改地方:
將原來播放暫停的按鈕移動到屏幕正中央祭务,在左下角播放暫停按鈕處添加一個靜音按鈕,也就是要么靜音要么以某一音量播放(我添加的為0.3)

回到正題:AVPlayer的封裝怪嫌、tableviewcell上視頻播放以及滑動播放暫停

實現(xiàn)原理:關(guān)于tableviewcell上播放視頻的一些說明:首先义锥、我們并不是讓每一個cell都擁有一個播放器,而是讓tableview所在的控制器擁有一個播放器岩灭,然后根據(jù)計算來決定哪個cell此時應(yīng)該播放視頻拌倍,進而將控制器的播放器 添加 到cell的contentView上。在滑動過程中,我們會不斷的判斷正在播放的cell是否滑出屏幕或者正在播放的cell需要被另一個cell所替代柱恤,通過判斷來對播放器的銷毀以及重新初始化并添加到相應(yīng)的cell上数初。

讓控制器擁有一個播放器是我在項目實踐過程中想到的一個方案并付諸實踐,效果還可以梗顺,至少從內(nèi)存的角度可以看到變化泡孩。由原先的 130M左右降到現(xiàn)在的65M左右。

準備工作:下載作者或我的playerView代碼
作者GitHubhttps://github.com/JmoVxia/CLPlayer

個人修改后的代碼

說明:我會直接使用我項目中的截圖來給大家分享寺谤,沒有一個完整的demo仑鸥。但是我會教你怎么使用。

1.0關(guān)于cell中對于播放器view的布局 以及 cell需要添加一個videoFrame的屬性

playercell.png

播放器所在的視圖結(jié)構(gòu)大致就是這樣矗漾。將播放暫停按鈕的操作傳到tableview所在的控制器锈候,這里有一點需要注意:那就是 計算出 播放器所在的視圖也就是上面videoView的frame,傳遞給控制器以便初始化播放器的時候?qū)⑵涮砑拥絚ell上敞贡。所以泵琳,給每個需要播放視頻的cell 添加一個屬性,videoFrame誊役,來記錄videoView的frame

+ (instancetype)cellWithTableView:(UITableView *)tableView;

@property (nonatomic,strong)ConventionsModel *convention;

//用來記錄播放器在cell的frame
@property (nonatomic,assign)CGRect videoFrame;

@property (nonatomic,assign)id<DiscoverVideoCellDelegate> delegate;

@end

在給cell設(shè)置數(shù)據(jù)后并強制布局后再計算videoFrame

- (void)setConvention:(ConventionsModel *)convention
{
    _convention = convention;

// 這里給cell上的控件賦值


//如果cell的高度需要自適應(yīng)获列,這里一定要強制布局,然后再計算videoFrame,否則蛔垢、播放器播放時可能不會在你想要的地方
[self layoutIfNeeded];

// convention.cellHeight = CGRectGetMaxY(self.gameIcon.frame) + CGRectGetMinY(self.titleLabel.frame);
//    }
    
    self.videoFrame = self.videoView.frame;
}

2.0在控制器中點擊播放暫停按鈕進行播放 或者 進入控制器后自動播放

理論說明:如果不需要自動播放击孩,那么通過代理將cell上的播放暫停按鈕點擊事件傳遞給控制器后,我們只需要 初始化 控制器擁有的那個播放器屬性鹏漆,并將其添加到點擊的cell上即可巩梢。

在需要自動播放時,我們就需要進行分類判斷艺玲,當進入該控制器括蝠,請求到數(shù)據(jù)后,播放當前tableview上的第一個(最上面的)視頻饭聚,當滑動tableview時忌警,播放cell中心(更準確的說:應(yīng)該是cell上videoView的中心)距離屏幕中心最近的cell上的視頻。

下面我直接分享自動播放的情況秒梳,在控制器中添加兩個屬性法绵、一個是播放器(view)一個是正在播放的cell。倘若你的tableview中只有一種cell酪碘,你可以直接使用該類型的cell朋譬,因為我的項目中并不是每個cell上都有視頻播放,所有我直接用UITableViewCell兴垦,模態(tài)屬性此熬,父類指向子類。

@property (nonatomic,strong)CLPlayerView *clPlayerView;

@property (nonatomic,strong)UITableViewCell *playingCell;

3.0請求到數(shù)據(jù)后播放第一個視頻

我們可以在請求到數(shù)據(jù)的回調(diào)里面刷新列表后播放第一個視頻

[self.tableView reloadData];
            
//進入界面播放
[self playVideoInVisiableCells];

3.1進入這個界面就自動播放

//進入這個界面就自動播放
-(void)playVideoInVisiableCells{
    
//下面是我實際項目中代碼。在這里你需要做的就是獲得第一個有視頻的cell犀忱,并進行播放和記錄。播放視頻可以抽到一個方法中扶关,需要的就是播放視頻所在的cell以及視頻播放所需要的地址URL等阴汇。可以仿照我的進行寫代碼节槐,當然搀庶,如果你的每個cell類型相同且都有視頻,你可以直接獲取可見的cell  NSArray *visiableCells = [self.tableView visibleCells]; 判斷 visiableCells.count是否大于0铜异,正在播放的cell就是第一個了哥倔。接下來我們說一說播放視頻- (void)initPlayerView:(DiscoverVideoCell *)cell playClick:(ConventionsModel *)convention


    // 找到下一個要播放的cell(最在屏幕中心的)
    DiscoverVideoCell *firstCell = nil;
    NSArray *visiableCells = [self.tableView visibleCells];
    
    //存放大框播放視頻
    for (int i = 0; i < visiableCells.count; i++) {
        UITableViewCell *cell = visiableCells[i];
        
        if ([cell isKindOfClass:[DiscoverVideoCell class]]) {
            firstCell = (DiscoverVideoCell *)cell;
            break;
        }
    }
    
    //播放第一個視頻
    [self initPlayerView:firstCell playClick:firstCell.convention];

}

4.0播放視頻

初始化視頻播放器,并將其添加到正在播放的cell上

- (void)initPlayerView:(DiscoverVideoCell *)cell playClick:(ConventionsModel *)convention
{
  self.playingCell = cell;
//    self.playingIndexPath = [self.tableView indexPathForCell:cell];
    
    [_clPlayerView destroyPlayer];
    _clPlayerView = nil;
    
    CLPlayerView *playerView = [[CLPlayerView alloc] initWithFrame:cell.videoFrame];
    _clPlayerView = playerView;
    
    [cell.contentView addSubview:_clPlayerView];
    
    //視頻地址
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        _clPlayerView.url = convention.url;
        //播放
        [_clPlayerView playVideo];
        
    });
    
    //返回按鈕點擊事件回調(diào)
    [_clPlayerView backButton:^(UIButton *button) {
        NSLog(@"返回按鈕被點擊");
    }];
    
    //播放完成回調(diào)
    [_clPlayerView endPlay:^{
        
        //銷毀播放器
        [_clPlayerView destroyPlayer];
        _clPlayerView = nil;
        NSLog(@"播放完成");
    }];
}

5.0滾動播放暫停

//滾動播放暫停說明:對于正在播放的視頻揍庄、我們需要時刻監(jiān)聽cell是否移除界面咆蒿;而對于正在播放的cell被替代時,我們可以在滾動停止時進行播放器的初始化并播放蚂子。
所以沃测、只需要在以下三個代理方法中實現(xiàn)即可。

- (void)scrollViewDidScroll:(UIScrollView *)scrollView
{
   
//我發(fā)現(xiàn)作者對于內(nèi)存的釋放有一點問題食茎,播放器銷毀后內(nèi)存并沒有下降
//    [_clPlayerView calculateScrollOffset:self.tableView cell:self.playingCell];

//我嘗試去修改作者的蒂破,似乎也沒有起作用,所有自己在改方法中進行銷毀
    NSArray *cells = [self.tableView visibleCells];
    if (![cells containsObject:self.playingCell]) {
        
        if (_clPlayerView) {
            //銷毀播放器
            [_clPlayerView destroyPlayer];
            _clPlayerView = nil;
        }
        
    }
}

- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
    //滑動播放
    [self handleScrollPlaying:scrollView];
}

- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate{
    
    if (!decelerate){
        //滑動播放
        [self handleScrollPlaying:scrollView];
    }
    
}

//這里參考第二篇文章的計算方式别渔,更準確的計算方式應(yīng)該是:cell中videoView的中心距屏幕的中心最近的cell為正在播放的cell附迷。
//滑動播放
- (void)handleScrollPlaying:(UIScrollView *)scrollView
{
    // 找到下一個要播放的cell(最在屏幕中心的)
    DiscoverVideoCell *finnalCell = nil;
    NSArray *visiableCells = [self.tableView visibleCells];
    
    //存放大框播放視頻
    NSMutableArray *tempVideoCells = [NSMutableArray array];
    for (int i = 0; i < visiableCells.count; i++) {
        UITableViewCell *cell = visiableCells[i];
        
        if ([cell isKindOfClass:[DiscoverVideoCell class]]) {
            [tempVideoCells addObject:cell];
        }
    }
    
    
    NSMutableArray *indexPaths = [NSMutableArray array];
    CGFloat gap = MAXFLOAT;
    for (DiscoverVideoCell *cell in tempVideoCells) {
        
        [indexPaths addObject:[self.tableView indexPathForCell:cell]];
        
//計算距離屏幕中心最近的cell
        CGPoint coorCentre = [cell.superview convertPoint:cell.center toView:nil];
        CGFloat delta = fabs(coorCentre.y-[UIScreen mainScreen].bounds.size.height*0.5);
        if (delta < gap) {
            gap = delta;
            finnalCell = cell;
        }
        
    }
    
    // 注意, 如果正在播放的cell和finnalCell是同一個cell, 不應(yīng)該在播放
    if (finnalCell != nil && self.playingCell != finnalCell)  {  
        if (_clPlayerView) {
            [_clPlayerView destroyPlayer];
            _clPlayerView = nil;
        }
        
        [self initPlayerView:finnalCell playClick:finnalCell.convention];
        
        self.playingCell = finnalCell;
        return;
    }
}


在tableviewcell上播放視頻,在這里基本上就結(jié)束了哎媚。目前在項目中使用良好喇伯。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市抄伍,隨后出現(xiàn)的幾起案子艘刚,更是在濱河造成了極大的恐慌,老刑警劉巖截珍,帶你破解...
    沈念sama閱讀 211,639評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件攀甚,死亡現(xiàn)場離奇詭異,居然都是意外死亡岗喉,警方通過查閱死者的電腦和手機秋度,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,277評論 3 385
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來钱床,“玉大人荚斯,你說我怎么就攤上這事。” “怎么了事期?”我有些...
    開封第一講書人閱讀 157,221評論 0 348
  • 文/不壞的土叔 我叫張陵滥壕,是天一觀的道長。 經(jīng)常有香客問我兽泣,道長绎橘,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,474評論 1 283
  • 正文 為了忘掉前任唠倦,我火速辦了婚禮称鳞,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘稠鼻。我一直安慰自己冈止,他們只是感情好,可當我...
    茶點故事閱讀 65,570評論 6 386
  • 文/花漫 我一把揭開白布候齿。 她就那樣靜靜地躺著熙暴,像睡著了一般。 火紅的嫁衣襯著肌膚如雪毛肋。 梳的紋絲不亂的頭發(fā)上怨咪,一...
    開封第一講書人閱讀 49,816評論 1 290
  • 那天,我揣著相機與錄音润匙,去河邊找鬼诗眨。 笑死,一個胖子當著我的面吹牛孕讳,可吹牛的內(nèi)容都是我干的匠楚。 我是一名探鬼主播,決...
    沈念sama閱讀 38,957評論 3 408
  • 文/蒼蘭香墨 我猛地睜開眼厂财,長吁一口氣:“原來是場噩夢啊……” “哼芋簿!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起璃饱,我...
    開封第一講書人閱讀 37,718評論 0 266
  • 序言:老撾萬榮一對情侶失蹤与斤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后荚恶,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體撩穿,經(jīng)...
    沈念sama閱讀 44,176評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,511評論 2 327
  • 正文 我和宋清朗相戀三年谒撼,在試婚紗的時候發(fā)現(xiàn)自己被綠了食寡。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,646評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡廓潜,死狀恐怖抵皱,靈堂內(nèi)的尸體忽然破棺而出善榛,到底是詐尸還是另有隱情,我是刑警寧澤呻畸,帶...
    沈念sama閱讀 34,322評論 4 330
  • 正文 年R本政府宣布移盆,位于F島的核電站,受9級特大地震影響伤为,放射性物質(zhì)發(fā)生泄漏味滞。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 39,934評論 3 313
  • 文/蒙蒙 一钮呀、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧昨凡,春花似錦爽醋、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,755評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至哪痰,卻和暖如春遂赠,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背晌杰。 一陣腳步聲響...
    開封第一講書人閱讀 31,987評論 1 266
  • 我被黑心中介騙來泰國打工跷睦, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人肋演。 一個月前我還...
    沈念sama閱讀 46,358評論 2 360
  • 正文 我出身青樓抑诸,卻偏偏與公主長得像,于是被迫代替她去往敵國和親爹殊。 傳聞我的和親對象是個殘疾皇子蜕乡,可洞房花燭夜當晚...
    茶點故事閱讀 43,514評論 2 348

推薦閱讀更多精彩內(nèi)容

  • 發(fā)現(xiàn) 關(guān)注 消息 iOS 第三方庫、插件梗夸、知名博客總結(jié) 作者大灰狼的小綿羊哥哥關(guān)注 2017.06.26 09:4...
    肇東周閱讀 12,065評論 4 62
  • Summary: This distinction between knowledge and skills li...
    不是貓閱讀 231評論 0 0
  • 我們都是宇宙間小小的塵埃 有著平凡的夢想和愛 每天穿梭在城市的縫隙里 錯過了日出和日落 扛起行囊 背井離鄉(xiāng) 這個世...
    微笑的百合花閱讀 296評論 7 7
  • 尊敬的各位長輩层玲、親朋好友、小朋友們: 大家中午好反症! 今天是笑笑12歲生日慶典辛块!作為媽媽的我格外激動!在這...
    王敏11閱讀 704評論 0 1
  • 6月2日 星期五 晴 今晚在外邊吃完飯后惰帽,他們還在喝著憨降,聊著,我和如夢便在夜市逛了一圈该酗。 走出門后授药,很遠...
    XHF_6de4閱讀 181評論 0 0