AVCaptureDevice 的 exposurePointOfInterest 不起作用

AVCaptureDevice's exposurePointOfInterest does not work

我正在尝试根据图像的特定点更改我的相机应用程序中的曝光。

我使用的是用户点击屏幕时触发的以下代码。现在我只是尝试暴露在中心。

@IBAction func didTap()
{
    if captureDevice.isExposurePointOfInterestSupported
    {
        try! captureDevice.lockForConfiguration()

        captureDevice.exposurePointOfInterest = CGPoint(x: 0.5, y: 0.5)
        captureDevice.exposureMode = .continuousAutoExposure

        captureDevice.unlockForConfiguration()
    }
}

但是没有任何反应。

captureDevice.isExposurePointOfInterestSupported 是真的。 captureDevice 目前是 .builtInDualCamera

此代码位于基于示例代码的简单相机测试应用程序中。它在屏幕上显示实时摄像机图像。

有人 exposurePointOfInterest 在 iOS 14.4 上工作吗? 我可能缺少什么?

我实际上 运行 昨天进入了这个问题。事实证明,完全使用 (0.5, 0.5) 存在问题。当我使用 (0.51, 0.51) 时,它每次都有效

extension AVCaptureDevice {
    func change(_ block: (AVCaptureDevice) -> ()) {
        try! self.lockForConfiguration()
        block(self)
        self.unlockForConfiguration()
    }
}

@objc func handleTap() {
    device.change {
        [=10=].exposurePointOfInterest = CGPoint(x: 0.51, y: 0.51)
        [=10=].exposureMode = .autoExpose
    }
}

更新

可能还值得注意的是,虽然它是一个点指定曝光,但该点周围的区域仍然必须足够大才能触发曝光调整。我们称其为触发区域。

据我测试了解,(0.5, 0.5)点对触发区域的大小有特殊影响。每当这个点作为exposurePointOfInterest时,触发区域都比较大,不管exposureMode.continuousAutoExpose还是.autoExpose.

您可以使用以下代码了解该区域的大小,将您的 phone 指向一个明亮的区域(例如 lamp),然后查看您必须离该区域多近直到点击调整曝光。您会发现曝光 调整,但您必须非常接近。

@objc func handleTap() {
    device.change {
        [=11=].exposurePointOfInterest = CGPoint(x: 0.5, y: 0.5)
        [=11=].exposureMode = .autoExpose
    }
}

或者,您无法使用水龙头,只需将属性 exposureModeexposurePointOfInterest 保留为默认值 .continuousAutoExpose(0.5, 0.5)。或者您可以使用本机相机应用程序并查看它何时自动调整曝光。结果是一样的。

现在,如果您将 exposurePointOfInterest 设置为接近但不等于中点的值,比如 (0.51, 0.51),您会发现触发区域变得非常非常小.

您也可以使用 .continuousAutoExpose 并只调用一次,您会发现自动曝光调整更加敏感,因为触发区域要小得多:

func viewDidLoad() {
    super.viewDidLoad()
    device.change {
        [=12=].exposurePointOfInterest = CGPoint(x: 0.51, y: 0.51)
        [=12=].exposureMode = .continuousAutoExpose
    }
}

要了解这个较小区域的大小,请打开本机相机应用程序,然后点击某处 focus/expose。您会看到一个小边界框。这几乎是触发区域的大小。

假设您有这样的水龙头:

@objc func handleTap() {
    device.change {
        [=13=].exposurePointOfInterest = CGPoint(x: 0.51, y: 0.51)
        [=13=].exposureMode = .autoExpose
    }
}

如果没有任何反应,则该区域不够大,当您尝试在该点点击曝光时,您应该能够在本机相机应用程序中重现相同的无效果。

旁注

您的 didTap() 方法正在设置默认值,因此它基本上没有用。

如果要在点按时调整曝光,如果点始终相同,请使用 .autoExpose。不要使用 .continuousAutoExpose 因为它会一直 调整曝光 ,而不仅仅是轻按一下。只有点击会改变点时才有意义。