WeScan Swift相机自动对焦与摄像头选择问题求助
解决WeScan在iPhone 15上的自动对焦及摄像头选择问题
针对你用WeScan开发配料扫描应用时遇到的iPhone 15无法自动对焦、无法指定近距离摄像头的问题,直接修改WeScan源码或扩展API就能解决,具体方案如下:
一、指定近距离摄像头(适配小字扫描)
WeScan默认没暴露摄像头选择接口,需要修改CameraScannerViewController的摄像头初始化逻辑:
- 找到
CameraScannerViewController里的setupCaptureSession方法 - 替换设备选择代码,优先选支持微距的超广角摄像头:
// 替换原有的设备查找逻辑 guard let device = AVCaptureDevice.DiscoverySession( deviceTypes: [.builtInUltraWideCamera, .builtInWideAngleCamera], mediaType: .video, position: .back ).devices.first else { fatalError("无可用后置摄像头") }
这样会优先调用超广角(iPhone 15的超广角支持微距模式),适配近距离小字扫描需求。
二、添加自动对焦功能
WeScan默认没开启点击对焦和持续自动对焦,给CameraScannerViewController补全逻辑:
1. 开启持续自动对焦
在setupCaptureSession配置设备时,添加持续自动对焦设置:
// 配置摄像头设备时加入 do { try device.lockForConfiguration() // 开启持续自动对焦 if device.isFocusModeSupported(.continuousAutoFocus) { device.focusMode = .continuousAutoFocus } device.unlockForConfiguration() } catch { print("对焦配置失败:\(error)") }
2. 添加点击对焦手势
在CameraScannerViewController的viewDidLoad里添加点击手势:
let tapGesture = UITapGestureRecognizer(target: self, action: #selector(handleTapToFocus(_:))) previewView.addGestureRecognizer(tapGesture)
然后实现对焦处理方法:
@objc private func handleTapToFocus(_ gesture: UITapGestureRecognizer) { let touchPoint = gesture.location(in: previewView) guard let captureDevice = captureSession.inputs.first?.device as? AVCaptureDevice else { return } do { try captureDevice.lockForConfiguration() // 设置点击位置为对焦点 if captureDevice.isFocusPointOfInterestSupported && captureDevice.isFocusModeSupported(.autoFocus) { captureDevice.focusPointOfInterest = touchPoint captureDevice.focusMode = .autoFocus } // 同步调整曝光 if captureDevice.isExposurePointOfInterestSupported && captureDevice.isExposureModeSupported(.autoExpose) { captureDevice.exposurePointOfInterest = touchPoint captureDevice.exposureMode = .autoExpose } captureDevice.unlockForConfiguration() } catch { print("点击对焦失败:\(error)") } }
三、封装可配置API(避免重复改源码)
如果不想每次修改WeScan源码,可以给ImageScannerController加扩展,暴露配置接口:
extension ImageScannerController { /// 指定优先使用的摄像头类型 func setPreferredCamera(_ type: AVCaptureDevice.DeviceType) { guard let cameraVC = children.first as? CameraScannerViewController else { return } // 这里需要给CameraScannerViewController添加对应的setupCaptureSession重载方法 cameraVC.setupCaptureSession(withPreferredDevice: type) } /// 开启点击对焦功能 func enableTapToFocus() { guard let cameraVC = children.first as? CameraScannerViewController else { return } let tapGesture = UITapGestureRecognizer(target: cameraVC, action: #selector(cameraVC.handleTapToFocus(_:))) cameraVC.previewView.addGestureRecognizer(tapGesture) } }
然后在你的调用代码里直接使用:
func scanFromCamera() { let scannerViewController = ImageScannerController() scannerViewController.imageScannerDelegate = self // 指定超广角摄像头 scannerViewController.setPreferredCamera(.builtInUltraWideCamera) // 开启点击对焦 scannerViewController.enableTapToFocus() // 原有配置... scannerViewController.modalPresentationStyle = .popover scannerViewController.navigationBar.backgroundColor = .black scannerViewController.navigationBar.tintColor = .white scannerViewController.toolbar.backgroundColor = .black present(scannerViewController, animated: true) }
内容的提问来源于stack exchange,提问作者Adam First
相关产品推荐
相关产品推荐

