Запись видео останавливается.fileOutput (_ output: AVCaptureFileOutput, didFinishRecordingTo outputFileURL: error :: "Нет такого файла." - PullRequest
0 голосов
/ 08 марта 2019

У меня проблема с записью видео.

Поток, как: -

  1. Я открою экран моей камеры.
  2. запишет видео, затем перейдет к созданию экрана поста.
  3. Этот поток отлично работает в первый раз. Но когда я вернулся на камеру с экрана создания поста и снова попытался записать, он внезапно останавливает запись, как только я запускаю, и выдает ошибку «такого файла нет».

Любая помощь будет оценена. Спасибо.

var captureSession: AVCaptureSession?
var capturePhotoOutput: AVCapturePhotoOutput?
var videoPreviewLayer: AVCaptureVideoPreviewLayer?
var userSelectedFlashMode: AVCaptureDevice.FlashMode = .off
var movieFileOutput = AVCaptureMovieFileOutput()

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    captureSession = AVCaptureSession()
    captureSession?.beginConfiguration()
    let microphone = AVCaptureDevice.default(for: AVMediaType.audio)
    do {
        let micInput = try AVCaptureDeviceInput(device: microphone!)
        if (captureSession?.canAddInput(micInput))! {
            captureSession?.addInput(micInput)
        }
    } catch {
        print("SRL Error setting device audio input.")
    }
    guard let captureDevice = AVCaptureDevice.default(.builtInWideAngleCamera, for: AVMediaType.video, position: .back) else {
        fatalError("No video device found")
    }
    do {
        let input = try AVCaptureDeviceInput(device: captureDevice)
        captureSession?.addInput(input)
        capturePhotoOutput = AVCapturePhotoOutput()
        capturePhotoOutput?.isHighResolutionCaptureEnabled = true
        captureSession?.addOutput(capturePhotoOutput!)
        captureSession?.sessionPreset = .high
        movieFileOutput.maxRecordedDuration = CMTimeMake(value: Int64(59), timescale: 1)
        if (captureSession?.canAddOutput(movieFileOutput))! {
            captureSession?.addOutput(movieFileOutput)
        }
        self.captureSession?.commitConfiguration()
        let captureMetadataOutput = AVCaptureMetadataOutput()
        captureSession?.addOutput(captureMetadataOutput)
        captureMetadataOutput.setMetadataObjectsDelegate(self as? AVCaptureMetadataOutputObjectsDelegate, queue: DispatchQueue.main)
        captureMetadataOutput.metadataObjectTypes = [AVMetadataObject.ObjectType.qr]
        videoPreviewLayer = AVCaptureVideoPreviewLayer(session: captureSession!)
        videoPreviewLayer?.videoGravity = AVLayerVideoGravity.resizeAspectFill
        videoPreviewLayer?.frame = previewLayer.layer.bounds
        previewLayer.layer.addSublayer(videoPreviewLayer!)
        captureSession?.startRunning()
        self.btnCapture.isUserInteractionEnabled = true
    } catch let error {
        print(error.localizedDescription)
    }
}


override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    if let captureSession = self.captureSession {
        if captureSession.isRunning {
            captureSession.stopRunning()
            self.captureSession = nil
            self.btnCapture.isUserInteractionEnabled = false
        }
    }
}

Расширение для AVCaptureFileOutputRecordingDelegate

extension MediaCaptureViewCotroller: AVCaptureFileOutputRecordingDelegate {
@objc func longPress(_ sender: UILongPressGestureRecognizer) {
    var device : AVCaptureDevice!
    let videoDeviceDiscoverySession = AVCaptureDevice.DiscoverySession(deviceTypes: [.builtInWideAngleCamera], mediaType: AVMediaType.video, position: .unspecified)
    let devices = videoDeviceDiscoverySession.devices
    device = devices[0]
    if sender.state == .began {
        print("Started...")
        self.hideControls()
        let videoPreviewLayerOrientation = videoPreviewLayer?.connection?.videoOrientation
        if !movieFileOutput.isRecording {
            print("Recording...")
            if UIDevice.current.isMultitaskingSupported {
                self.backgroundRecordingID = UIApplication.shared.beginBackgroundTask(expirationHandler: nil)
            }
            let movieFileOutputConnection = movieFileOutput.connection(with: .video)
            movieFileOutputConnection?.videoOrientation = videoPreviewLayerOrientation!

            let availableVideoCodecTypes = movieFileOutput.availableVideoCodecTypes

            if #available(iOS 11.0, *) {
                if availableVideoCodecTypes.contains(.hevc) {
                    movieFileOutput.setOutputSettings([AVVideoCodecKey: AVVideoCodecType.hevc], for: movieFileOutputConnection!)
                }
            } else {
                movieFileOutput.setOutputSettings([AVVideoCodecKey: AVVideoCodecH264], for: movieFileOutputConnection!)
            }
            if ((device as AnyObject).hasMediaType(AVMediaType.video)) {
                if (device.hasTorch) {
                    self.captureSession?.beginConfiguration()
                    do {
                        if (device.hasTorch) {
                            try device.lockForConfiguration()
                            if userSelectedFlashMode == .on || userSelectedFlashMode == .auto {
                                device.torchMode = .on
                            }
                            device.unlockForConfiguration()
                        }
                    }catch{
                        print("Device tourch Flash Error ");
                    }
                    self.captureSession?.commitConfiguration()
                }
            }
            let outputFileName = NSUUID().uuidString
            let outputFilePath = (NSTemporaryDirectory() as NSString).appendingPathComponent(("outputFileName" as NSString).appendingPathExtension("mp4")!)
            print("RecordingStart PAth", outputFilePath)
            self.cleanup(path: outputFilePath)
            movieFileOutput.startRecording(to: URL(fileURLWithPath: outputFilePath), recordingDelegate: self)
        }
    } else if sender.state == .ended {
        print("Ended...")
        if movieFileOutput.isRecording {
            print("Stopped")
            movieFileOutput.stopRecording()
            if ((device as AnyObject).hasMediaType(AVMediaType.video)) {
                if (device.hasTorch) {
                    self.captureSession?.beginConfiguration()
                    do {
                        if (device.hasTorch){
                            try device.lockForConfiguration()
                            device.torchMode = .off
                            device.unlockForConfiguration()
                        }
                    }catch{
                        print("Device tourch Flash Error ");
                    }
                    self.captureSession?.commitConfiguration()
                }
            }
            self.showControls()
        }
    } else { }
}   
func fileOutput(_ output: AVCaptureFileOutput, didFinishRecordingTo outputFileURL: URL, from connections: [AVCaptureConnection], error: Error?) {
    print(outputFileURL.absoluteString)
    do {
        let data = try Data(contentsOf: outputFileURL)
        print("Recorded File size", data.count)
        //FIXME:- Navigate to create post screen
    } catch {
        print("error in decoding file", error.localizedDescription)
    }
    self.showControls()
}
func cleanup(path: String) {
    if FileManager.default.fileExists(atPath: path) {
        do {
            try FileManager.default.removeItem(atPath: path)
        } catch {
            print("Could not remove file at url: \(path)")
        }
    }
    if let currentBackgroundRecordingID = backgroundRecordingID {
        backgroundRecordingID = UIBackgroundTaskIdentifier.invalid
        if currentBackgroundRecordingID != UIBackgroundTaskIdentifier.invalid {
            UIApplication.shared.endBackgroundTask(currentBackgroundRecordingID)
        }
    }
}

}

...