双击或使用按钮将相机从后向前切换(Xcode 8,Swift 3) [英] Double Tap or Use Button To Switch Camera From Back to Front (Xcode 8, Swift 3)

查看:89
本文介绍了双击或使用按钮将相机从后向前切换(Xcode 8,Swift 3)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以,最近我一直试图在Swift 3中实现从后到前摄像头切换摄像机视图的功能。但是,没有运气。

So, lately I have been trying to implement the function of switching the camera view from back to front camera in Swift 3. However, with no luck.

目前,我的默认视图来自后置摄像头 - 我可以用它拍照然后重拍。但是,任何人都可以帮助我,并展示如何双击屏幕切换摄像头或只是使用指定的按钮切换它们?谢谢!

Currently, my default view is from the back camera - I can take pictures with it and then retake. But can anyone help me and show how do I either double tap the screen to switch cameras or simply use the assigned button to switch them? Thank you!

import UIKit
import AVFoundation
import FirebaseDatabase

class CameraView: UIViewController, UIImagePickerControllerDelegate, UINavigationControllerDelegate {

override var prefersStatusBarHidden: Bool {
    return true
}

var captureSession : AVCaptureSession!
var stillImageOutput : AVCaptureStillImageOutput!
var previewLayer : AVCaptureVideoPreviewLayer!

@IBOutlet var cameraView: UIView!
override func viewDidLoad() {
    super.viewDidLoad()

    // Do any additional setup after loading the view.
}

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
    // Dispose of any resources that can be recreated.
}

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    previewLayer?.frame = cameraView.bounds
}

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)

    captureSession = AVCaptureSession()
    captureSession?.sessionPreset = AVCaptureSessionPreset1920x1080

    var backCamera = AVCaptureDevice.defaultDevice(withMediaType: AVMediaTypeVideo)
    var error : NSError?

    do {
        var input = try! AVCaptureDeviceInput(device: backCamera)
        if (error == nil && captureSession?.canAddInput(input) != nil) {

            captureSession?.addInput(input)

            stillImageOutput = AVCaptureStillImageOutput()
            stillImageOutput.outputSettings = [AVVideoCodecKey: AVVideoCodecJPEG]

            if (captureSession?.canAddOutput(stillImageOutput) != nil) {

                captureSession?.addOutput(stillImageOutput)

                previewLayer = AVCaptureVideoPreviewLayer (session: captureSession)
                previewLayer.videoGravity = AVLayerVideoGravityResizeAspectFill
                previewLayer.connection.videoOrientation = AVCaptureVideoOrientation.portrait
                cameraView.layer.addSublayer(previewLayer)
                captureSession?.startRunning() }
        }

    } catch {

    }
}

@IBOutlet var tempImageView: UIImageView!
@IBAction func didPressTakePhoto(_ sender: UIButton) {

    if let videoConnection = stillImageOutput.connection(withMediaType: AVMediaTypeVideo) {

        videoConnection.videoOrientation = AVCaptureVideoOrientation.portrait
        stillImageOutput.captureStillImageAsynchronously(from: videoConnection, completionHandler: {

            (sampleBuffer, error) in
            if sampleBuffer != nil {

                var imageData = AVCaptureStillImageOutput.jpegStillImageNSDataRepresentation(sampleBuffer)
                var dataProvider = CGDataProvider.init(data: imageData as! CFData)
                var cgImageRef = CGImage.init(jpegDataProviderSource: dataProvider!, decode: nil, shouldInterpolate: true, intent: .defaultIntent)

                var image = UIImage (cgImage: cgImageRef!, scale: 1.0, orientation: UIImageOrientation.right)

                self.tempImageView.image = image
                self.tempImageView.isHidden = false

            }

        })

    }
}

var didTakePhoto = Bool()

@IBAction func didPressTakeAnother(_ sender: UIButton) {

    if didTakePhoto == true {

        tempImageView.isHidden = true
        didTakePhoto = false

    } else {

        captureSession?.startRunning()
        didTakePhoto = true

    }
}
}


推荐答案

不要看到这里有任何问题 - 这是工作解决方案:

don't see here any problems - here is working solution:

import Foundation
import UIKit
import AVFoundation

class MainViewController: UIViewController {

    var tempImage: UIImageView?

    var captureSession: AVCaptureSession?
    var stillImageOutput: AVCaptureStillImageOutput?
    var videoPreviewLayer: AVCaptureVideoPreviewLayer?
    var currentCaptureDevice: AVCaptureDevice?

    var usingFrontCamera = false


    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        loadCamera()
    }

    override func viewDidAppear(_ animated: Bool) {
        super.viewDidAppear(animated)
        videoPreviewLayer!.frame = self.cameraPreviewSurface.bounds
    }

    @IBAction func switchButtonAction(_ sender: Any) {
        usingFrontCamera = !usingFrontCamera
        loadCamera()
    }


    func getFrontCamera() -> AVCaptureDevice?{
        let videoDevices = AVCaptureDevice.devices(withMediaType: AVMediaTypeVideo)


        for device in videoDevices!{
            let device = device as! AVCaptureDevice
            if device.position == AVCaptureDevicePosition.front {
                return device
            }
        }
        return nil
    }

    func getBackCamera() -> AVCaptureDevice{
        return AVCaptureDevice.defaultDevice(withMediaType: AVMediaTypeVideo)
    }



    func loadCamera() {
        if(captureSession == nil){
            captureSession = AVCaptureSession()
            captureSession!.sessionPreset = AVCaptureSessionPresetPhoto
        }
        var error: NSError?
        var input: AVCaptureDeviceInput!

        currentCaptureDevice = (usingFrontCamera ? getFrontCamera() : getBackCamera())

        do {
            input = try AVCaptureDeviceInput(device: currentCaptureDevice)
        } catch let error1 as NSError {
            error = error1
            input = nil
            print(error!.localizedDescription)
        }

        for i : AVCaptureDeviceInput in (self.captureSession?.inputs as! [AVCaptureDeviceInput]){
            self.captureSession?.removeInput(i)
        }
        if error == nil && captureSession!.canAddInput(input) {
            captureSession!.addInput(input)
            stillImageOutput = AVCaptureStillImageOutput()
            stillImageOutput?.outputSettings = [AVVideoCodecKey: AVVideoCodecJPEG]
            if captureSession!.canAddOutput(stillImageOutput) {
                captureSession!.addOutput(stillImageOutput)
                videoPreviewLayer = AVCaptureVideoPreviewLayer(session: captureSession)
                videoPreviewLayer!.videoGravity = AVLayerVideoGravityResizeAspectFill
                videoPreviewLayer!.connection?.videoOrientation = AVCaptureVideoOrientation.portrait
                //self.cameraPreviewSurface.layer.sublayers?.forEach { $0.removeFromSuperlayer() }
                self.cameraPreviewSurface.layer.addSublayer(videoPreviewLayer!)
                DispatchQueue.main.async {
                    self.captureSession!.startRunning()
                }


            }
        }



    }
}

一些笔记:

cameraPreviewSurface - 这是你的UIView,相机会在哪里显示

cameraPreviewSurface - this is your UIView where camera will show

不要重新分配会话,不要只是添加输入,而是在添加新内容之前 - 删除现有内容,

don't reassign the session, don't just add input, but before add new - remove existing ones,

PS使用swift 3.0.1 / xcode 8.1完成的代码

p.s. code done with swift 3.0.1 / xcode 8.1

干杯)

这篇关于双击或使用按钮将相机从后向前切换(Xcode 8,Swift 3)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆