美文网首页
iOS-音视屏采集

iOS-音视屏采集

作者: 三月望龙 | 来源:发表于2018-07-27 16:47 被阅读0次

    概述

    • 音视屏采集分音频采集和视频采集
    • 在iOS中,可以同步采集音频和视频
    • 采集的API在AVFoundation框架中

    采集流程

    1、初始化输入输出源

    • 设置采集视屏的输入和输出源
        private func setupVideo() {
            // 获取视屏input所需的设备,本例取的是前置摄像头
            let devices = AVCaptureDevice.devices(for: AVMediaType.video)
            guard let device = devices.filter({ $0.position == .front}).first else {return}
            
            // input
            guard let input = try? AVCaptureDeviceInput(device: device) else { return }
            self.videoInput = input
            
            // output
            let output = AVCaptureVideoDataOutput()
            output.setSampleBufferDelegate(self, queue: DispatchQueue.global())
            self.videoOutput = output
            
            // add session
            session.beginConfiguration()
            if session.canAddInput(input) {
                session.addInput(input)
            }
            if session.canAddOutput(output) {
                session.addOutput(output)
            }
            session.commitConfiguration()
        }
    
    • 设置采集的音频的输入和输出源
       private func setupAudio() {
            // input
            guard let device = AVCaptureDevice.default(for: AVMediaType.audio) else { return }
            guard let input = try? AVCaptureDeviceInput(device: device) else { return }
        
            // output
            let output = AVCaptureAudioDataOutput()
            output.setSampleBufferDelegate(self, queue: DispatchQueue.global())
            
            // add session
            session.beginConfiguration()
            if session.canAddInput(input) {
                session.addInput(input)
            }
            if session.canAddOutput(output) {
                session.addOutput(output)
            }
            session.commitConfiguration()
        }
    
    • 设置预览图层

    实时显示采集的画面,可以添加此预览图层
    不添加该图层也可以正常采集

        private func setupPreviewLayer() {
            let preview = AVCaptureVideoPreviewLayer(session: session)
            preview.frame = view.bounds
            view.layer.insertSublayer(preview, at: 0)
            self.previewLayer = preview
        }
    
    • 采集音视屏回调

    音频回调遵循AVCaptureAudioDataOutputSampleBufferDelegate
    视屏回调遵循AVCaptureVideoDataOutputSampleBufferDelegate
    注意: 音频回调方法和视屏回调方法是同一个方法

    extension ViewController:  AVCaptureVideoDataOutputSampleBufferDelegate, AVCaptureAudioDataOutputSampleBufferDelegate {
        func captureOutput(_ output: AVCaptureOutput, didDrop sampleBuffer: CMSampleBuffer, from connection: AVCaptureConnection) {
           // 丢弃采集 
        }
        func captureOutput(_ output: AVCaptureOutput, didOutput sampleBuffer: CMSampleBuffer, from connection: AVCaptureConnection) {
            // sampleBuffer 采集到的每一帧结果
            // 通过connection判断采集到的数据是视屏或音频信息
            if self.videoOutput?.connection(with: AVMediaType.video) == connection {
                print("采集到视屏")
            }else {
                print("采集到音频")
            }
        }
    }
    

    2、设置采集结果的保存

    如果需要保存采集到的音视屏,可以添加此实例

    • 初始化AVCaptureMovieFileOutput
        private func setupOutputFile () {
            if movieOutputFile != nil {
                session.removeOutput(movieOutputFile!)
            }
            
            let fileOutput = AVCaptureMovieFileOutput()
            let connection = fileOutput.connection(with: AVMediaType.video)
            connection?.automaticallyAdjustsVideoMirroring = true
            if session.canAddOutput(fileOutput) {
                session.addOutput(fileOutput)
            }
            self.movieOutputFile = fileOutput 
        }
    
    • 设置保存路径

    使用计算属性

        private var urlPath: URL? {
            let path = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true).first! + "/video.mp4"
            
            return URL(fileURLWithPath: path)
        }
    
    • 遵守文件写入代理AVCaptureFileOutputRecordingDelegate
    extension ViewController: AVCaptureFileOutputRecordingDelegate {
        func fileOutput(_ output: AVCaptureFileOutput, didStartRecordingTo fileURL: URL, from connections: [AVCaptureConnection]) {
            print("开始写入")
        }
        func fileOutput(_ output: AVCaptureFileOutput, didFinishRecordingTo outputFileURL: URL, from connections: [AVCaptureConnection], error: Error?) {
            print("结束写入")
        }
    }
    

    3、开始采集以及结束采集

    • 开始采集
        @IBAction func startCapture(_ sender: Any) {
             // 每次开始采集前, 设置预览图层
            setupPreviewLayer()
            
            // 开始录制,保存采集结果
            if let url = urlPath {
                self.movieOutputFile?.startRecording(to: url, recordingDelegate: self)
            }
            
            // 开始采集
            session.startRunning()
        }
    
    • 结束采集
        @IBAction func stopCapture(_ sender: Any) {
             // 结束录制
            self.movieOutputFile?.stopRecording()
            
            // 结束采集
            session.stopRunning()
            
            // 移出预览图层
            previewLayer?.removeFromSuperlayer()
        }
    

    4、旋转采集摄像头

        @IBAction func rotateCamera(_ sender: Any) {
            guard let videoInput = videoInput else { return }
            // 前置 -> 后置, 后置 -> 前置
            let position: AVCaptureDevice.Position = videoInput.device.position == .front ? .back : .front
            
            // 输入源重新添加设备
            let devices = AVCaptureDevice.devices(for: AVMediaType.video)
            guard let device = devices.filter({$0.position == position }).first else { return }
            guard let input = try? AVCaptureDeviceInput(device: device) else { return }
            
            // session重新添加输入源
            session.beginConfiguration()
            session.removeInput(videoInput)
            if session.canAddInput(input) {
                session.addInput(input)
            }
            session.commitConfiguration()
            
            // 保存最新输入源
            self.videoInput = input
        }
    

    相关文章

      网友评论

          本文标题:iOS-音视屏采集

          本文链接:https://www.haomeiwen.com/subject/xpegmftx.html