| | |
| | | |
| | | class CameraCapture: NSObject, AVCaptureVideoDataOutputSampleBufferDelegate { |
| | | private let session = AVCaptureSession() |
| | | private var videoOutput: AVCaptureVideoDataOutput? |
| | | private var input: AVCaptureDeviceInput? |
| | | var onFrame: ((CVPixelBuffer) -> Void)? |
| | | |
| | | func start() { |
| | |
| | | return |
| | | } |
| | | |
| | | self.input = input |
| | | |
| | | session.beginConfiguration() |
| | | session.sessionPreset = .high |
| | | session.sessionPreset = .hd1920x1080 |
| | | |
| | | if session.canAddInput(input) { |
| | | session.addInput(input) |
| | | } |
| | | |
| | | |
| | | let output = AVCaptureVideoDataOutput() |
| | | output.videoSettings = [ |
| | | kCVPixelBufferPixelFormatTypeKey as String: kCVPixelFormatType_32BGRA |
| | | ] |
| | | output.setSampleBufferDelegate(self, queue: DispatchQueue(label: "camera.queue")) |
| | | |
| | | if session.canAddOutput(output) { |
| | | session.addOutput(output) |
| | | } |
| | | |
| | | self.videoOutput = output |
| | | // 在相机配置代码中 |
| | | if let videoConnection = output.connection(with: .video) { |
| | | // 自动旋转(推荐) |
| | | videoConnection.automaticallyAdjustsVideoMirroring = false |
| | | videoConnection.videoOrientation = .portrait // 或根据UI方向设置 |
| | | |
| | | // 对于前置摄像头启用镜像 |
| | | /*if videoConnection.isVideoMirroringSupported { |
| | | videoConnection.isVideoMirrored = (cameraPosition == .front) |
| | | }*/ |
| | | } |
| | | session.commitConfiguration() |
| | | session.startRunning() |
| | | print("📷 相机已开启") |
| | | } |
| | | |
| | | func captureOutput(_ output: AVCaptureOutput, |
| | | didOutput sampleBuffer: CMSampleBuffer, |
| | | from connection: AVCaptureConnection) { |
| | | guard let buffer = CMSampleBufferGetImageBuffer(sampleBuffer) else { return } |
| | | let width = CVPixelBufferGetWidth(buffer) |
| | | let height = CVPixelBufferGetHeight(buffer) |
| | | //print("📷 当前帧尺寸: \(width)x\(height)") |
| | | onFrame?(buffer) |
| | | } |
| | | |
| | | func stop(){ |
| | | session.stopRunning() |
| | | session.beginConfiguration() |
| | | |
| | | if let input = input { |
| | | session.removeInput(input) |
| | | } |
| | | |
| | | if let output = videoOutput { |
| | | session.removeOutput(output) |
| | | } |
| | | |
| | | session.commitConfiguration() |
| | | |
| | | input = nil |
| | | videoOutput = nil |
| | | print("📷 相机已关闭") |
| | | } |
| | | } |