微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

播放视频带有音频;来自资产以及录制视频和音频来自前置摄像头?

如何解决播放视频带有音频;来自资产以及录制视频和音频来自前置摄像头?

我不知道这是否可能,但是实现该目标有一个问题。

我有一个UIView的{​​{1}}(VideoView),并播放资产中的一些视频并拥有自己的音频。

在此视图上,还有另一个(较小的)UIView(Cameraview),具有:

  • AVCaptureVideoPreviewLayer(显示前置摄像头)
  • AVCaptureSession
  • AVCaptureDevice
  • AVAudioSession

显示用户前置摄像头的预览并录制自己的音频和视频。

并同时运行。与FaceTime通话类似。

AVPlayerLayer中的

AVAudioSession设置如下:

Cameraview

但是,尽管如此,我在播放视频(VideoView)的录制视频(由Cameraview录制)中仍有某种回声。

我已经尝试过单独保存音频,但是问题是相同的。 这是我的第一个AV *应用程序,我对音频/视频没有太多经验。 有人可以指出我的错误在哪里或指向正确的方向...

Sample Screenshot

VideView.swift

let audioSession = AVAudioSession.sharedInstance()
do {
  if #available(iOS 11.0,*) {
     try audioSession.setCategory(.playAndRecord,mode: .spokenAudio,policy: AVAudioSession.RouteSharingPolicy.default,options: [.duckOthers])
  } else {
    try audioSession.setCategory(.playAndRecord,mode: .spokenAudio)
  }
  try audioSession.setActive(true)
} catch let error {
  print("Audio setup error",#file,#function,#line,error.localizedDescription)
}

Cameraview.swift

protocol VideoViewDelegate {
    func didEndVideo()
    func didEndVideo(of instance: VideoView)
    func isVideoReady()
}

class VideoView: UIView {
    
    var playerLayer: AVPlayerLayer?
    var player: AVPlayer?
    var isLoop: Bool = false
    
    var delegate: VideoViewDelegate!
    
    var observer: NSkeyvalueObservation?
    
    override init(frame: CGRect) {
        super.init(frame: frame)
        backgroundColor = .black
    }
    
    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
    }
    
    func ply(for url: URL) {
        player = AVPlayer(url: url)
        playerLayer = AVPlayerLayer(player: player)
        playerLayer?.frame = bounds
        playerLayer?.videoGravity = AVLayerVideoGravity.resizeAspectFill
        
        if let playerLayer = self.playerLayer {
            layer.addSublayer(playerLayer)
        }
        
        NotificationCenter.default.addobserver(self,selector: #selector(reachTheEndOfTheVideo),name: NSNotification.Name.AVPlayerItemDidplayToEndTime,object: self.player?.currentItem)
    }
    
    func prepare(url: URL) {
        player?.replaceCurrentItem(with: AVPlayerItem(url: url))
        NotificationCenter.default.addobserver(self,object: self.player?.currentItem)
    }
    
    func destroyMe() {
        stop()
        NotificationCenter.default.removeObserver(self)
        observer?.invalidate()
    }
    
    func play() {
        if player?.timeControlStatus != AVPlayer.TimeControlStatus.playing {
            player?.play()
        }
    }
    
    func pause() {
        player?.pause()
    }
    
    func stop() {
        player?.pause()
        player?.seek(to: CMTime.zero)
    }
    
    @objc
    func reachTheEndOfTheVideo(_ notification: Notification) {
        if isLoop {
            player?.pause()
            player?.seek(to: CMTime.zero)
            player?.play()
        } else {
            player?.pause()
            player?.seek(to: CMTime.zero)
            
            UIView.animate(withDuration: 0.4) { [weak self] in
                self!.transform = .identity
            }
            if delegate != nil { delegate.didEndVideo() }
            if delegate != nil { delegate.didEndVideo(of: self) }
        }
    }
}

谢谢

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。