浏览代码

拆分试听模块;缓冲图标加快

harry 3 年之前
父节点
当前提交
88d4de4194

+ 76 - 2
BFRecordScreenKit/Classes/RecordScreen/Controller/BFMusicManager.swift

@@ -14,8 +14,83 @@ import Alamofire
 
 class BFMusicManager {
     
+    var playStatusCallback : ((AVPlayerItem?, BFMuicInfoCellState) -> Void)?
+    
+    // 试听音乐
+    let player:AVPlayer = {
+        let p = AVPlayer(playerItem: nil)
+        return p
+    }()
+    
+    var loadedTimeRangesObserver : NSKeyValueObservation?
+    var retaRangesObserver : NSKeyValueObservation?
+
+    init() {
+        loadedTimeRangesObserver = player.observe(\AVPlayer.currentItem?.loadedTimeRanges, options: [.new, .initial]) { [weak self] (player, change) in
+            BFLog(1, message: "status: 0")
+
+            DispatchQueue.main.async {[weak self] in
+                guard let wself = self else { return }
+                
+                guard let ranges = change.newValue as? [CMTimeRange] else { return }
+                if let totalDur = player.currentItem?.duration, totalDur.isValid,  CMTimeCompare(ranges.first?.duration ?? .zero, totalDur) >= 0{
+                    BFLog(1, message: "status: 1")
+                    wself.playStatusCallback?(wself.player.currentItem, .playing)
+                }
+            }
+        }
+        
+    }
+    
+    func play() {
+        player.play()
+        
+        DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) { [weak self] in
+            guard let wself = self else { return }
+            
+            if wself.player.rate == 1.0 {
+                wself.playStatusCallback?(wself.player.currentItem, .playing)
+            }
+        }
+    }
+    
+    func pause() {
+        player.pause()
+        playStatusCallback?(player.currentItem, .pause)
+    }
+    
+    func stop() {
+        playStatusCallback?(player.currentItem, .normal)
+
+    }
+    
+    func replaceCurrentItem(newItemUrl: URL) {
+        if player.currentItem != nil {
+            NotificationCenter.default.removeObserver(self, name: .AVPlayerItemDidPlayToEndTime, object: player.currentItem)
+        }
+        player.replaceCurrentItem(with: AVPlayerItem(url: newItemUrl))
+        NotificationCenter.default.addObserver(forName: .AVPlayerItemDidPlayToEndTime, object: player.currentItem, queue: .main) {[weak self] notice in
+            guard let wself = self else { return }
+            wself.player.currentItem?.seek(to: .zero, completionHandler: nil)
+//                            wself.choseCell()?.status = .pause
+//                            wself.chosedCellStatu = .pause
+            wself.play()
+        }
+    }
+    
+    deinit {
+        NotificationCenter.default.removeObserver(self)
+        loadedTimeRangesObserver?.invalidate()
+        loadedTimeRangesObserver = nil
+    }
+
+}
+
+
+// class method
+extension BFMusicManager {
     public class func downloadMusic(model: PQVoiceModel, complete:(@escaping () -> Void)) {
-//        BFNetRequestAdaptor.postRequestData(url: "", parames: [:], commonParams: commonParams(), encoding: JSONEncoding.default, isJsonEncodingNormal: true, timein)
+
         if let path = model.musicPath, let url = URL(string: path) {
             
             let request = URLRequest(url: url)
@@ -50,5 +125,4 @@ class BFMusicManager {
         print("new location:\(documnets)")
 
     }
-
 }

+ 18 - 44
BFRecordScreenKit/Classes/RecordScreen/Controller/BFMusicSearchController.swift

@@ -38,11 +38,7 @@ class BFMusicSearchController: BFBaseViewController {
     var keywork : String?
 
     // 试听音乐
-    let player:AVPlayer = {
-        let p = AVPlayer(playerItem: nil)
-        
-        return p
-    }()
+    let playerManager = BFMusicManager()
     
     lazy var searchTF : UITextField = {
         let searchTF = UITextField()
@@ -142,24 +138,13 @@ class BFMusicSearchController: BFBaseViewController {
         
 //        musicVolume = 0.2
         
-        loadedTimeRangesObserver = player.observe(\AVPlayer.currentItem?.loadedTimeRanges, options: [.new, .initial]) { [weak self] (player, change) in
+        playerManager.playStatusCallback = {[weak self] playerItem, playStatus in
+            guard let wself = self else { return }
             
-            DispatchQueue.main.async {[weak self] in
-                guard let wself = self else { return }
-                
-                guard let ranges = change.newValue as? [CMTimeRange] else { return }
-                if let totalDur = player.currentItem?.duration, totalDur.isValid,  CMTimeCompare(ranges.first?.duration ?? .zero, totalDur) >= 0{
-                    if let indx = wself.chosedIndexPath, let cell = wself.musicTb.cellForRow(at: indx) as? BFMuicInfoCell {
-                        if (player.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" == cell.data?.musicPath ?? "a" {
-                            if cell.status == .loading{
-                                cell.status = .playing
-                            }
-                        }
-                    }
-                    wself.chosedCellStatu = .playing
-                }
-//                BFLog(1, message: "开始播放音乐:\(ranges.first?.start.seconds ?? 0), dur:\( ranges.first?.duration.seconds ?? 0), tot:\(player.currentItem?.duration.seconds ?? 0)")
+            if let indx = wself.chosedIndexPath, let cell = wself.musicTb.cellForRow(at: indx) as? BFMuicInfoCell, (playerItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" == cell.data?.musicPath ?? "a" {
+                cell.status = playStatus
             }
+            wself.chosedCellStatu = playStatus
         }
         
     }
@@ -187,7 +172,7 @@ class BFMusicSearchController: BFBaseViewController {
         frame.origin.x = slidV.x - 7 + ((slidV.width - 28) / 100.0) * CGFloat(musicVolume)
         progressL.frame = frame
         
-        player.volume = Float(musicVolume) / 100.0
+        playerManager.player.volume = Float(musicVolume) / 100.0
 
     }
 }
@@ -205,7 +190,7 @@ extension BFMusicSearchController : UITableViewDelegate, UITableViewDataSource {
 
             cell.useCallback = {[weak self, weak cell] in
                 guard let wself = self else { return }
-                wself.player.pause()
+                wself.playerManager.pause()
                 cell?.status = .pause
                 cell?.data?.volume = (Int)(wself.slidV.value * 100.0)
                 wself.choseAction?(cell?.data)
@@ -213,7 +198,7 @@ extension BFMusicSearchController : UITableViewDelegate, UITableViewDataSource {
             }
             cell.cutCallBack = {[weak self, weak cell] in
                 guard let wself = self else { return }
-                wself.player.pause()
+                wself.playerManager.pause()
                 cell?.status = .pause
                 cell?.data?.volume = (Int)(wself.slidV.value * 100.0)
 
@@ -248,10 +233,10 @@ extension BFMusicSearchController : UITableViewDelegate, UITableViewDataSource {
             if chosedIndexPath == indexPath {
                 if cell.status != .pause{
                     cell.status = .pause
-                    player.pause()
+                    playerManager.pause()
                 }else{
                     cell.status = .loading
-                    player.play()
+                    playerManager.play()
                 }
                 return
             }
@@ -262,29 +247,18 @@ extension BFMusicSearchController : UITableViewDelegate, UITableViewDataSource {
             if cell.status == .normal {
                 if let urlStr = cell.data?.musicPath, let url = URL(string: urlStr){
                     BFLog(1, message: "歌曲地址: \(url)")
-                    if url.absoluteString != (player.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" {
-                        if player.currentItem != nil {
-                            NotificationCenter.default.removeObserver(self, name: .AVPlayerItemDidPlayToEndTime, object: player.currentItem)
-                        }
-                        player.replaceCurrentItem(with: AVPlayerItem(url: url))
-                        NotificationCenter.default.addObserver(forName: .AVPlayerItemDidPlayToEndTime, object: player.currentItem, queue: .main) {[weak self] notice in
-                            guard let wself = self else { return }
-                            wself.player.currentItem?.seek(to: .zero, completionHandler: nil)
-//                            wself.choseCell()?.status = .pause
-//                            wself.chosedCellStatu = .pause
-                            wself.player.play()
-                        }
-                        
+                    if url.absoluteString != (playerManager.player.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" {
+                        playerManager.replaceCurrentItem(newItemUrl: url)
                         cell.status = .loading
                     }else {
                         cell.status = .playing
                     }
-                    player.play()
+                    playerManager.play()
                 }
             }else if cell.status == .pause{
-                player.play()
+                playerManager.play()
             } else{
-                player.pause()
+                playerManager.pause()
                 cell.status = .pause
             }
             chosedCellStatu = cell.status
@@ -299,7 +273,7 @@ extension BFMusicSearchController : UITableViewDelegate, UITableViewDataSource {
         cell?.changeSelected(false)
         
         chosedIndexPath = nil
-        player.pause()
+        playerManager.pause()
     }
     
     // MARK: - 搜素接口
@@ -363,7 +337,7 @@ extension BFMusicSearchController : UITableViewDelegate, UITableViewDataSource {
     }
     
     func resetRearch() {
-        player.pause()
+        playerManager.pause()
         chosedCellStatu = .normal
         chosedIndexPath = nil
         currPage = 1

+ 23 - 44
BFRecordScreenKit/Classes/RecordScreen/View/BFChooseMusicView.swift

@@ -37,6 +37,8 @@ class BFChooseMusicView: UIView {
     // 各类别音乐列表,以类别id为key
     var musicDic = [Int64 : [PQVoiceModel]]()
     
+    var playManager = BFMusicManager()
+    
     var searchModel : PQVoiceModel?{
         willSet{
             if searchModel != nil {
@@ -93,14 +95,6 @@ class BFChooseMusicView: UIView {
     
     var chosedCellStatu : BFMuicInfoCellState = .pause
     
-    var loadedTimeRangesObserver : NSKeyValueObservation?
-
-    // 试听音乐
-    let player:AVPlayer = {
-        let p = AVPlayer(playerItem: nil)
-        return p
-    }()
-    
     lazy var categoryView : UICollectionView = {
         let layout = BFCollectionViewFlowLayout()
         layout.dele = self
@@ -232,22 +226,13 @@ class BFChooseMusicView: UIView {
         
         self.musicVolume = 20
 
-        loadedTimeRangesObserver = player.observe(\AVPlayer.currentItem?.loadedTimeRanges, options: [.new, .initial]) { [weak self] (player, change) in
+        playManager.playStatusCallback = {[weak self] playerItem, status in
+            guard let wself = self else { return }
             
-            DispatchQueue.main.async {[weak self] in
-                guard let wself = self else { return }
-                
-                guard let ranges = change.newValue as? [CMTimeRange] else { return }
-                if let indx = wself.chosedIndexPath, let cell = wself.musicTb.cellForRow(at: indx) as? BFMuicInfoCell, let totalDur = player.currentItem?.duration, totalDur.isValid,  CMTimeCompare(ranges.first?.duration ?? .zero, totalDur) >= 0{
-                    if (player.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" == cell.data?.musicPath ?? "a" {
-                        if cell.status != .playing{
-                            cell.status = .playing
-                            wself.chosedCellStatu = .playing
-                        }
-                    }
-                }
-                BFLog(1, message: "开始播放音乐:\(ranges.first?.start.seconds ?? 0), dur:\( ranges.first?.duration.seconds ?? 0), tot:\(player.currentItem?.duration.seconds ?? 0)")
+            if let indx = wself.chosedIndexPath, let cell = wself.musicTb.cellForRow(at: indx) as? BFMuicInfoCell, (playerItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" == cell.data?.musicPath ?? "a" {
+                cell.status = status
             }
+            wself.chosedCellStatu = status
         }
         
         prepareCatoryList()
@@ -361,7 +346,7 @@ class BFChooseMusicView: UIView {
         frame.origin.x = slidV.x - 7 + ((slidV.width - 28) / 100.0) * CGFloat(musicVolume)
         progressL.frame = frame
         
-        player.volume = Float(musicVolume) / 100.0
+        playManager.player.volume = Float(musicVolume) / 100.0
         chosedMusic?.volume = musicVolume
 
     }
@@ -379,7 +364,7 @@ class BFChooseMusicView: UIView {
     
     @objc func btnAction(btn:UIButton) {
         
-        player.pause()
+        playManager.pause()
  
         choseCell()?.status = .pause
 
@@ -404,7 +389,7 @@ class BFChooseMusicView: UIView {
     // 取消选歌
     func cancelChooseMusic() {
 //        chosedMusic = nil
-        player.pause()
+        playManager.pause()
         choseCell()?.status = .normal
         choseCell()?.changeSelected(false)
         chosedIndexPath = nil
@@ -425,7 +410,7 @@ extension BFChooseMusicView:UITableViewDelegate, UITableViewDataSource {
         cell.selectionStyle = .none
         cell.cutCallBack = {[weak self, weak cell] in
             guard let wself = self else { return }
-            wself.player.pause()
+            wself.playManager.pause()
             if let data = cell?.data {
                 wself.cutActionCallback?(data)
             }
@@ -458,14 +443,16 @@ extension BFChooseMusicView:UITableViewDelegate, UITableViewDataSource {
     }
     
     func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
+
         if let cell = tableView.cellForRow(at: indexPath) as? BFMuicInfoCell {
             if chosedIndexPath == indexPath {
                 if cell.status != .pause{
                     cell.status = .pause
-                    player.pause()
+                    playManager.pause()
                 }else{
+                    BFLog(1, message: "status: 2")
                     cell.status = .loading
-                    player.play()
+                    playManager.play()
                 }
                 return
             }
@@ -480,28 +467,20 @@ extension BFChooseMusicView:UITableViewDelegate, UITableViewDataSource {
             if cell.status == .normal {
                 if let urlStr = cell.data?.musicPath, let url = URL(string: urlStr){
                     BFLog(1, message: "歌曲地址: \(url)")
-                    if url.absoluteString != (player.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" {
+                    if url.absoluteString != (playManager.player.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? "b" {
                         cell.status = .loading
-                        if player.currentItem != nil {
-                            NotificationCenter.default.removeObserver(self, name: .AVPlayerItemDidPlayToEndTime, object: player.currentItem)
-                        }
-                        player.replaceCurrentItem(with: AVPlayerItem(url: url))
-                        NotificationCenter.default.addObserver(forName: .AVPlayerItemDidPlayToEndTime, object: player.currentItem, queue: .main) {[weak self] notice in
-                            guard let wself = self else { return }
-                            wself.player.currentItem?.seek(to: .zero, completionHandler: nil)
-//                            wself.choseCell()?.status = .pause
-//                            wself.chosedCellStatu = .pause
-                            wself.player.play()
-                        }
+                        playManager.replaceCurrentItem(newItemUrl: url)
                     }else {
                         cell.status = .playing
                     }
-                    player.play()
+                    playManager.play()
                 }
             }else if cell.status == .pause{
-                player.play()
+                BFLog(1, message: "status: 2")
+
+                playManager.play()
             } else{
-                player.pause()
+                playManager.pause()
                 cell.status = .pause
             }
             chosedCellStatu = cell.status
@@ -516,7 +495,7 @@ extension BFChooseMusicView:UITableViewDelegate, UITableViewDataSource {
         cell?.changeSelected(false)
         
         chosedIndexPath = nil
-        player.pause()
+        playManager.pause()
     }
 }