|
@@ -32,9 +32,6 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
var rendView = GPUImageView()
|
|
|
var cameraProgressV: BFCameraProgressView?
|
|
|
|
|
|
- var dispatchQueue: DispatchQueue?
|
|
|
- var dispatchWorkItem: DispatchWorkItem?
|
|
|
-
|
|
|
override var recordItem: BFRecordItemModel? {
|
|
|
didSet {
|
|
|
cameraProgressV?.recordItem = recordItem
|
|
@@ -95,6 +92,8 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
wself.currentAssetProgress = CMTime(seconds: (currTime + wself.currPlayTime).seconds, preferredTimescale: 1000)
|
|
|
|
|
|
BFLog(message: "当前播放器状态: \(wself.avplayer.timeControlStatus.rawValue) \( wself.currentAssetProgress.seconds)")
|
|
|
+
|
|
|
+ wself.playRecordVoice()
|
|
|
}
|
|
|
// BFLog(1, message: "拖动 currTime: \(currTime.seconds)")
|
|
|
DispatchQueue.main.async { [weak self] in
|
|
@@ -456,7 +455,16 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
}
|
|
|
|
|
|
func playRecordVoice(needPlay: Bool = true) {
|
|
|
- BFLog(message: "开始查找!!!!currentAssetProgress:\(currentAssetProgress)")
|
|
|
+ //三种状态值
|
|
|
+// case paused = 0
|
|
|
+// case waitingToPlayAtSpecifiedRate = 1
|
|
|
+// case playing = 2
|
|
|
+ if recordPlayer?.timeControlStatus == .playing || recordPlayer?.timeControlStatus == .waitingToPlayAtSpecifiedRate {
|
|
|
+ BFLog( 2,message:"recordPlayer is playering 本次查找无效,有播放任务")
|
|
|
+ return
|
|
|
+ }
|
|
|
+ BFLog(message: "开始查找!!!!当前进度:\(currentAssetProgress.seconds) \(recordPlayer?.timeControlStatus.rawValue ?? -1)")
|
|
|
+
|
|
|
// 播放音频
|
|
|
var useVoiceStickers = [PQVoiceModel]()
|
|
|
if (recordItem?.voiceChangeStickers.count ?? 0) > 0 {
|
|
@@ -465,16 +473,19 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
useVoiceStickers = recordItem?.voiceStickers ?? [PQVoiceModel]()
|
|
|
}
|
|
|
|
|
|
-
|
|
|
- BFLog(message: "时间范围: currentAssetProgress\(currentAssetProgress.seconds)")
|
|
|
let spitTime = (recordItem?.voiceChangeStickers.count ?? 0) > 0 ? 0.0 : 0.333
|
|
|
|
|
|
if let mod = useVoiceStickers.first(where: { m in
|
|
|
CMTimeCompare(m.startCMTime, currentAssetProgress + CMTime(seconds: spitTime, preferredTimescale: 1000)) <= 0 && CMTimeCompare(m.endCMTime, (currentAssetProgress + CMTime(seconds: spitTime, preferredTimescale: 1000))) > 0
|
|
|
}) {
|
|
|
|
|
|
- for model in useVoiceStickers {
|
|
|
- BFLog(message: "时间范围:\(model.startCMTime.seconds) 到 \(model.endCMTime.seconds) \(currentAssetProgress.seconds)")
|
|
|
+ BFLog(message: "找到音频开始时间:\(mod.startCMTime.seconds)结束 \(mod.endCMTime.seconds) currentAssetProgress is \(currentAssetProgress.seconds)")
|
|
|
+
|
|
|
+ //当前播放的文件
|
|
|
+ let cureentPalyURlString = (recordPlayer?.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? ""
|
|
|
+ if(cureentPalyURlString.replacingOccurrences(of: "file://", with: "") == mod.wavFilePath && recordPlayer?.timeControlStatus != .playing){
|
|
|
+ BFLog( 2,message:"命中的和播放的文件路径一样? wavFilePath:\(mod.wavFilePath ?? "") recordPlayer Status \(recordPlayer?.timeControlStatus.rawValue ?? -1)")
|
|
|
+ return
|
|
|
}
|
|
|
recordPlayer?.replaceCurrentItem(with: AVPlayerItem(url: URL(fileURLWithPath: mod.wavFilePath)))
|
|
|
let tt = currentAssetProgress - mod.startCMTime
|
|
@@ -491,6 +502,21 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
}
|
|
|
BFLog(message: "finishedre \(finishedre) 当前时间\(self.currentAssetProgress.seconds)")
|
|
|
}
|
|
|
+
|
|
|
+ NotificationCenter.default.addObserver(forName: .AVPlayerItemNewErrorLogEntry, object: recordPlayer?.currentItem, queue: .main) { notify in
|
|
|
+ BFLog(message: "AVPlayerItemNewErrorLogEntry = \(notify)")
|
|
|
+ }
|
|
|
+ NotificationCenter.default.addObserver(forName: .AVPlayerItemFailedToPlayToEndTime, object: recordPlayer?.currentItem, queue: .main) { notify in
|
|
|
+ BFLog(message: "AVPlayerItemFailedToPlayToEndTime = \(notify)")
|
|
|
+ }
|
|
|
+ NotificationCenter.default.addObserver(forName: .AVPlayerItemPlaybackStalled, object: recordPlayer?.currentItem, queue: .main) { notify in
|
|
|
+ BFLog(message: "AVPlayerItemPlaybackStalled = \(notify)")
|
|
|
+ }
|
|
|
+ recordPlayer?.addPeriodicTimeObserver(forInterval: CMTime(value: 1, timescale: CMTimeScale(playerTimescale)), queue: .main) { [weak self] cmTime in
|
|
|
+ let delta = CMTimeGetSeconds(cmTime)
|
|
|
+
|
|
|
+ BFLog(message: "progress = \(delta)")
|
|
|
+ }
|
|
|
|
|
|
NotificationCenter.default.addObserver(forName: .AVPlayerItemDidPlayToEndTime, object: recordPlayer?.currentItem, queue: .main) { [weak self] _ in
|
|
|
guard let wself = self else {
|
|
@@ -499,69 +525,15 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
|
|
|
//录制的视频如果不是播放过程当中 就不进行录音的播放了。
|
|
|
let palyEndURlString = (wself.recordPlayer?.currentItem?.asset as? AVURLAsset)?.url.absoluteString ?? ""
|
|
|
- BFLog(message: "recordPlayer 播放完了:\(palyEndURlString) wself.avplayer.timeControlStatus \(wself.avplayer.timeControlStatus.rawValue)")
|
|
|
-// if let mod = wself.recordItem?.getUsedVoices().first(where: { m in
|
|
|
-// palyEndURlString == m.wavFilePath
|
|
|
-// }) {
|
|
|
-// mod.
|
|
|
-// }
|
|
|
- if wself.avplayer.timeControlStatus == .playing {
|
|
|
- wself.playRecordVoice()
|
|
|
- }
|
|
|
+ BFLog(message: "recordPlayer 播放完了:\(palyEndURlString) wself.avplayer.timeControlStatus \(wself.avplayer.timeControlStatus.rawValue) currentAssetProgress: \(wself.currentAssetProgress.seconds)")
|
|
|
+
|
|
|
}
|
|
|
} else {
|
|
|
BFLog(message: "没有找到即将播放的录制音频文件?\(currentAssetProgress.seconds)")
|
|
|
- findAvailableChangeVoice()
|
|
|
- }
|
|
|
- }
|
|
|
|
|
|
- // add by ak 正常播放未命中可使用录音时查找最近一个可用的音频, 并在 S 秒后会自动播放。
|
|
|
- /// <#Description#>
|
|
|
- func findAvailableChangeVoice() {
|
|
|
- var playCMTime = CMTime.zero
|
|
|
-
|
|
|
- if let mod = recordItem?.getUsedVoices().first(where: { m in
|
|
|
- CMTimeCompare(m.startCMTime, currentAssetProgress) >= 0
|
|
|
- }){
|
|
|
- BFLog(message: "当前时间\(currentAssetProgress.seconds),命中的开始时间:\(mod.startCMTime.seconds) 结束时间\(mod.endCMTime.seconds)")
|
|
|
- playCMTime = CMTimeSubtract(mod.startCMTime, currentAssetProgress)
|
|
|
-
|
|
|
- dispatchQueue = DispatchQueue.global(qos: .background) // create queue
|
|
|
- dispatchWorkItem = DispatchWorkItem { [weak self] in
|
|
|
- guard let wself = self else {
|
|
|
- return
|
|
|
- }
|
|
|
- if !wself.dispatchWorkItemIsCancel {
|
|
|
- wself.playRecordVoice(needPlay: true)
|
|
|
- } else {
|
|
|
- BFLog(message: "dispatchWorkItem Is Cancel")
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- if dispatchWorkItem != nil {
|
|
|
- BFLog(message: "\(playCMTime.seconds) s 后自动播放变音音频\(mod.wavFilePath ?? "") 当前时间:\(currentAssetProgress.seconds)")
|
|
|
- dispatchQueue?.asyncAfter(
|
|
|
- deadline: .now() + playCMTime.seconds,
|
|
|
- execute: dispatchWorkItem!
|
|
|
- )
|
|
|
- }
|
|
|
- }else{
|
|
|
- BFLog(message: "没有找到可播放的录制音频文件?\(currentAssetProgress.seconds)")
|
|
|
}
|
|
|
-
|
|
|
-
|
|
|
}
|
|
|
-
|
|
|
- // add by ak取消自动播放任务,1,暂停时 2,录制的视频播放结束时 调用
|
|
|
- func cancelDispatchWorkItem() {
|
|
|
- BFLog(message: "取消录制音频的查找下一个播放任务")
|
|
|
- // 取消变声音音频任务
|
|
|
- if let dispatchWorkItem = self.dispatchWorkItem {
|
|
|
- dispatchWorkItem.cancel()
|
|
|
- dispatchWorkItemIsCancel = true
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
+
|
|
|
func findNextModel() {
|
|
|
if let mod = recordItem?.videoStickers.sorted(by: { m1, m2 in
|
|
|
m1.timelineCMIn.seconds < m2.timelineCMIn.seconds
|
|
@@ -635,12 +607,9 @@ class BFRecordScreenCameraManager: BFRecordScreenBaseManager {
|
|
|
|
|
|
BFLog(1, message: "endPlay:\(wself.currentAssetProgress.seconds), 总时长:\(wself.recordItem!.materialDuraion.seconds), currplayer:\(wself.avplayer.currentItem?.currentTime().seconds ?? 0)")
|
|
|
|
|
|
- // 判断录音是否还在播放
|
|
|
+ // 判断录音是否还在播放,如果在播放停止
|
|
|
if wself.recordPlayer?.timeControlStatus == .playing {
|
|
|
wself.recordPlayer?.pause()
|
|
|
- wself.cancelDispatchWorkItem()
|
|
|
- wself.dispatchWorkItem = DispatchWorkItem { // create work item
|
|
|
- }
|
|
|
}
|
|
|
// 如果离结束大于0.7s,代表还有下一段视频
|
|
|
if ((wself.recordItem?.materialDuraion ?? .zero) - wself.currentAssetProgress).seconds > 0.7 {
|