Как остановить задержку камеры в ячейке collectionView? - PullRequest
0 голосов
/ 25 августа 2018

У меня есть collectionView, у которого есть ячейки, действующие как экраны.Когда я открываю приложение пальцем в ячейку камеры, на секунду возникает задержка, а затем после плавного перемещения назад и вперед, ниже - видео этой задержки.Есть ли способ предотвратить это, может быть, начать сеанс захвата в фоновом режиме до достижения ячейки?Спасибо за вашу помощь.

enter image description here

Код для ячейки камеры

import UIKit
import AVFoundation


class MainCameraCollectionViewCell: UICollectionViewCell {

    var captureSession = AVCaptureSession()
    private var sessionQueue: DispatchQueue!
    var captureConnection = AVCaptureConnection()

    var backCamera: AVCaptureDevice?
    var frontCamera: AVCaptureDevice?
    var currentCamera: AVCaptureDevice?

    var photoOutPut: AVCapturePhotoOutput?

    var cameraPreviewLayer: AVCaptureVideoPreviewLayer?

    var image: UIImage?

    var usingFrontCamera = false

    override func awakeFromNib() {
        super.awakeFromNib()
        setupCaptureSession()
        setupDevice()
        setupInput()
        self.setupPreviewLayer()
        startRunningCaptureSession
    }

    func setupCaptureSession(){
        captureSession.sessionPreset = AVCaptureSession.Preset.photo
        sessionQueue = DispatchQueue(label: "session queue")
    }

    func setupDevice(usingFrontCamera:Bool = false){
        DispatchQueue.main.async {
            //sessionQueue.async {
            let deviceDiscoverySession = AVCaptureDevice.DiscoverySession(deviceTypes: [AVCaptureDevice.DeviceType.builtInWideAngleCamera], mediaType: AVMediaType.video, position: AVCaptureDevice.Position.unspecified)
            let devices = deviceDiscoverySession.devices

            for device in devices{
                if usingFrontCamera && device.position == AVCaptureDevice.Position.front {
                    //backCamera = device
                    self.currentCamera = device
                } else if device.position == AVCaptureDevice.Position.back {
                    //frontCamera = device
                    self.currentCamera = device
                }
            }
        }
    }
    func setupInput() {
        DispatchQueue.main.async {
            do {
                let captureDeviceInput = try AVCaptureDeviceInput(device: self.currentCamera!)
                if self.captureSession.canAddInput(captureDeviceInput) {
                    self.captureSession.addInput(captureDeviceInput)
                }
                self.photoOutPut = AVCapturePhotoOutput()
                self.photoOutPut?.setPreparedPhotoSettingsArray([AVCapturePhotoSettings(format:[AVVideoCodecKey: AVVideoCodecType.jpeg])], completionHandler: nil)
                if self.captureSession.canAddOutput(self.photoOutPut!) {
                    self.captureSession.addOutput(self.photoOutPut!)
                }
            } catch {
                print(error)
            }
        }
    }
    func setupPreviewLayer(){
        cameraPreviewLayer = AVCaptureVideoPreviewLayer(session: captureSession)
        cameraPreviewLayer?.videoGravity = AVLayerVideoGravity.resizeAspectFill
        cameraPreviewLayer?.connection?.videoOrientation = AVCaptureVideoOrientation.portrait
        cameraPreviewLayer?.frame = CGRect(x: 0, y: 0, width: UIScreen.main.bounds.width, height: UIScreen.main.bounds.height)
        self.layer.insertSublayer(cameraPreviewLayer!, at: 0)
    }

    func startRunningCaptureSession(){
        captureSession.startRunning()
    }

    @IBAction func cameraButton_Touched(_ sender: Any) {
        let settings = AVCapturePhotoSettings(format: [AVVideoCodecKey: AVVideoCodecType.jpeg])
        //
        settings.isAutoStillImageStabilizationEnabled = true
        if let photoOutputConnection = self.photoOutPut?.connection(with: .video){
            photoOutputConnection.videoOrientation = (cameraPreviewLayer?.connection?.videoOrientation)!
        }
    }



    @IBAction func Flip_camera(_ sender: UIButton?) {
        print("Flip Touched")

        self.captureSession.beginConfiguration()
         if let inputs = self.captureSession.inputs as? [AVCaptureDeviceInput] {
            for input in inputs {
                self.captureSession.removeInput(input)
                print("input removed")
            }
            //This seemed to have fixed it
            for output in self.captureSession.outputs{
                captureSession.removeOutput(output)
                print("out put removed")
            }
        }


        self.usingFrontCamera = !self.usingFrontCamera
        self.setupCaptureSession()
        self.setupDevice(usingFrontCamera: self.usingFrontCamera)
        self.setupInput()
        self.captureSession.commitConfiguration()
        self.startRunningCaptureSession()
    }

}

1 Ответ

0 голосов
/ 25 августа 2018

Инициализация камеры требует времени. Как только ваше приложение запрашивает использование камеры, вспомогательное программное обеспечение должно быть инициализировано в фоновом режиме, что на самом деле не позволяет ускорить.

Я бы порекомендовал поместить все, что связано с AVFoundation, в фоновый поток и инициализировать его после загрузки вашего приложения. Таким образом, камера будет готова для пользователя, как только он / она будет готов провести к ячейке камеры. Если вы не хотите выполнять предварительную загрузку, вы можете, по крайней мере, по-прежнему размещать AVFoundation в фоновом режиме и использовать какой-то индикатор активности, чтобы показать пользователю, что что-то загружается, вместо того, чтобы просто блокировать основной поток во время загрузки камеры. до.

...