如何在Swift中创建一个更改摄像机视图的按钮?

时间:2015-03-22 14:12:33

标签: ios iphone swift camera

我想知道在按下按钮时如何更改相机视图。目前,我正在使用布尔值var camera = false,当我按下按钮时,我想将值更改为true并获取另一个相机。但这不起作用。 我现在有这个:

 @IBAction func changeCamera(sender: AnyObject) {

    camera = true

}

override func viewWillAppear(animated: Bool) {

    captureSession = AVCaptureSession()
    captureSession!.sessionPreset = AVCaptureSessionPresetPhoto
    var captureDevice:AVCaptureDevice! = nil
    //var backCamera = AVCaptureDevice.defaultDeviceWithMediaType(AVMediaTypeVideo)
    if (camera == false){
    let videoDevices = AVCaptureDevice.devicesWithMediaType(AVMediaTypeVideo)


    for device in videoDevices{
        let device = device as AVCaptureDevice
        if device.position == AVCaptureDevicePosition.Front {
            captureDevice = device
            break
        }
    }
    } else {
        var captureDevice = AVCaptureDevice.defaultDeviceWithMediaType(AVMediaTypeVideo)

    }

    var error: NSError?
    var input = AVCaptureDeviceInput(device: captureDevice, error: &error)

    if error == nil && captureSession!.canAddInput(input) {
        captureSession!.addInput(input)

        stillImageOutput = AVCaptureStillImageOutput()
        stillImageOutput!.outputSettings = [AVVideoCodecKey: AVVideoCodecJPEG]
        if captureSession!.canAddOutput(stillImageOutput) {
            captureSession!.addOutput(stillImageOutput)

            previewLayer = AVCaptureVideoPreviewLayer(session: captureSession)
            previewLayer!.videoGravity = AVLayerVideoGravityResizeAspect
            previewLayer!.connection?.videoOrientation = AVCaptureVideoOrientation.Portrait
            previewView.layer.addSublayer(previewLayer)

            captureSession!.startRunning()
        }
    }

}

1 个答案:

答案 0 :(得分:15)

问题在于您设置相机来源。

您在viewDidAppear中进行设置,只有在视图出现在设备上时才会调用它。这是从另一个视图控制器导航到该视图控制器或关闭由此视图控制器呈现的视图控制器时。

我的建议是将摄像机选择代码移动到viewDidLoad和调用changeCamera操作时调用的自己的函数中。

@IBAction func changeCamera(sender: AnObject?) {
    camera = !camera

    reloadCamera()
}


func viewDidAppear(animated: Bool) {
    // normal code

    reloadCamera()
}

func reloadCamera() {
    // camera loading code
    captureSession = AVCaptureSession()
    captureSession!.sessionPreset = AVCaptureSessionPresetPhoto
    var captureDevice:AVCaptureDevice! = nil
    // var backCamera = AVCaptureDevice.defaultDeviceWithMediaType(AVMediaTypeVideo)
    if (camera == false) {
        let videoDevices = AVCaptureDevice.devicesWithMediaType(AVMediaTypeVideo)


        for device in videoDevices{
            let device = device as AVCaptureDevice
            if device.position == AVCaptureDevicePosition.Front {
                captureDevice = device
                break
            }
        }
    } else {
        var captureDevice = AVCaptureDevice.defaultDeviceWithMediaType(AVMediaTypeVideo)
    }

    var error: NSError?
    var input = AVCaptureDeviceInput(device: captureDevice, error: &error)

    if error == nil && captureSession!.canAddInput(input) {
    captureSession!.addInput(input)

    stillImageOutput = AVCaptureStillImageOutput()
    stillImageOutput!.outputSettings = [AVVideoCodecKey: AVVideoCodecJPEG]
    if captureSession!.canAddOutput(stillImageOutput) {
        captureSession!.addOutput(stillImageOutput)

        previewLayer = AVCaptureVideoPreviewLayer(session: captureSession)
        previewLayer!.videoGravity = AVLayerVideoGravityResizeAspect
        previewLayer!.connection?.videoOrientation = AVCaptureVideoOrientation.Portrait
        previewView.layer.addSublayer(previewLayer)

        captureSession!.startRunning()
    }
}

此外,另一项改进是使用自定义枚举来存储当前正在使用的相机而不是布尔值。这意味着你可以在以后添加它,如果有第三个相机。这看起来像是:

enum CameraType {
    case front
    case back
}

var camera = CameraType.back

我希望这有帮助,对于省略完整的代码示例表示歉意,目前在iPad上,但是当我到达计算机时我会更新。


更新

确保在更换相机之前从视图中删除上一个预览图层。

func reloadCamera() {
    captureSession?.stopRunning()
    previewLayer?.removeFromSuperlayer()

    // The rest of the camera loading code...

这可以解决您的相机冻结问题。