【问题标题】:Swift - Capturing RAW Image with zoomFactor crashes the appSwift - 使用 zoomFactor 捕获 RAW 图像会使应用程序崩溃
【发布时间】:2021-07-15 07:18:02
【问题描述】:

我在拍摄 zoomFactor1.0 不同的 RAW 照片时遇到问题。 事实上,如果我以最小缩放级别拍照,一切正常。但是,如果我尝试放大更接近更改 zoomFactor 的主题,应用程序会崩溃并出现以下错误:

由于未捕获的异常'NSInvalidArgumentException'而终止应用程序,原因:'*** -[AVCapturePhotoOutput capturePhotoWithSettings:delegate:] 指定拜耳原始捕获时,视频设备的videoZoomFactor必须设置为1.0'

这仅在拍摄 RAW 时发生。如果我使用标准 HEVC 格式拍摄,一切正常。我正在使用 Swift 4.2 和 AVFoundation 框架

这是错误引用的代码:

extension CameraController: AVCapturePhotoCaptureDelegate, AVCaptureVideoDataOutputSampleBufferDelegate {

public func photoOutput(_ output: AVCapturePhotoOutput, didFinishProcessingPhoto photo: AVCapturePhoto, error: Error?) {
    guard error == nil else {
        print("Error capturing photo: \(error!)")
        return
    }
    
    // Access the file data representation of this photo.
    guard let photoData = photo.fileDataRepresentation() else {
        print("No photo data to write.")
        return
    }
    
    print("Generating IMAGE with metadata \n", photo.metadata)
    
    
    if photo.isRawPhoto {
        // Generate a unique URL to write the RAW file.
        rawFileURL = makeUniqueDNGFileURL()
        do {
            // Write the RAW (DNG) file data to a URL.
            try photoData.write(to: rawFileURL!)
            print("RAW-URL Generated")
            createRAWImageOnAlbum(withRAWURL: rawFileURL!)
        } catch {
            fatalError("Couldn't write DNG file to the URL.")
        }
    } else {
        createHEVCPhotoOnAlbum(photo: photo)
    }
}

private func makeUniqueDNGFileURL() -> URL {
    let tempDir = FileManager.default.temporaryDirectory
    let fileName = ProcessInfo.processInfo.globallyUniqueString
    return tempDir.appendingPathComponent(fileName).appendingPathExtension("dng")
}

}

你知道这是什么原因吗?

我在这里设置zoomFactor

    func updateZoom(toValue: CGFloat) throws {
    let session = AVCaptureDevice.DiscoverySession(deviceTypes: [.builtInWideAngleCamera], mediaType: AVMediaType.video, position: .unspecified)
    
    guard let cameras = (session.devices.compactMap { $0 }) as? [AVCaptureDevice], !cameras.isEmpty else { throw CameraControllerError.noCamerasAvailable }
    
    for camera in cameras {
        if camera.position == .back {
            self.rearCamera = camera
            try camera.lockForConfiguration()
            camera.ramp(toVideoZoomFactor: toValue, withRate: 4)
            camera.unlockForConfiguration()
        } else if camera.position == .front {
            self.frontCamera = camera
            try camera.lockForConfiguration()
            camera.ramp(toVideoZoomFactor: toValue, withRate: 4)
            camera.unlockForConfiguration()
        }
    }
}

【问题讨论】:

标签: ios swift avfoundation avcapturesession


【解决方案1】:

请检查设备支持的缩放系数,其中captureDevice 是您的AVCaptureDevice 实例:

func checkZoom(zoomFactor: CGFloat) {
    
    guard
        zoomFactor <= captureDevice.maxAvailableVideoZoomFactor,
        zoomFactor >= captureDevice.minAvailableVideoZoomFactor
    else {
        print("ZoomFactor not supported \(zoomFactor)")
        return
    }
}

【讨论】:

  • 我已经尝试过您的解决方案,它只确认我在正确的缩放比例范围内工作,因为从未打印过“不支持缩放因子”。对我来说奇怪的是,只有在拍摄 RAW 时才会抛出错误
  • 所以在调用 ramp() 方法时会崩溃。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-09-29
  • 1970-01-01
  • 2022-10-04
  • 2019-02-13
相关资源
最近更新 更多