FrontPage

概要

コード

import AVFoundation
import UIKit
import Photos

class ViewController: UIViewController {
   @IBOutlet weak var previewView: UIView!
   
   private var captureSession = AVCaptureMultiCamSession()
   
   private var audioInput: AVCaptureDeviceInput!
   private var audioPort: AVCaptureDeviceInput.Port!
   
   // 広角カメラの設定
   private var wideAngleInput: AVCaptureDeviceInput!
   private var wideAnglePort: AVCaptureDeviceInput.Port!
   private var wideAngleOutput: AVCaptureMovieFileOutput!
   private var wideAngleVideoConnection: AVCaptureConnection!
   
   // 望遠カメラの設定
   private var telephotoInput: AVCaptureDeviceInput!
   private var telephotoPort: AVCaptureDeviceInput.Port!
   private var telephotoOutput: AVCaptureMovieFileOutput!
   private var telephotoVideoConnection: AVCaptureConnection!
   
   // プレビュー
   private var videoPreviewLayer: AVCaptureVideoPreviewLayer!
   
   override func viewDidLoad() {
       super.viewDidLoad()
       
       // マルチキャプチャをサポートしているかどうか
       guard AVCaptureMultiCamSession.isMultiCamSupported else {
           fatalError()
       }
       
       setupSession()
   }

   // MARK: - セッションの設定
   private func setupSession() {
       captureSession.beginConfiguration()
       
       // マイクの準備
       do {
           let microphone = AVCaptureDevice.default(for: .audio)!
           let input = try AVCaptureDeviceInput(device: microphone)
           guard captureSession.canAddInput(input) else {
               fatalError()
           }
           
           audioInput = input
           captureSession.addInputWithNoConnections(input)
           
           guard let audioPort = input.ports(for: .audio,
                                             sourceDeviceType: microphone.deviceType,
                                             sourceDevicePosition: .back).first else {
               fatalError()
           }
           
           self.audioPort = audioPort
       }
       catch {
           fatalError(error.localizedDescription)
       }
       
       // カメラの利用準備
       do {
           try setupWideCamera()
           try setupTeleCamera()
           
           previewView.layer.addSublayer(videoPreviewLayer)
           videoPreviewLayer.frame = previewView.layer.frame
                       
           captureSession.commitConfiguration()
           captureSession.startRunning()
           
           if captureSession.canSetSessionPreset(.hd4K3840x2160) {
               print("4k利用可能")
           }
           else {
               print("4k利用不可能")
           }
       }
       catch {
           print("error")
       }
   }
   
   // MARK: - 広角カメラの設定
   
   private func setupWideCamera() throws {
       guard let camera = AVCaptureDevice.default(.builtInWideAngleCamera,
                                                  for: .video,
                                                  position: .back) else {
           print("camera not founc")
           throw NSError()
       }
       
       // sessinに追加
       wideAngleInput = try AVCaptureDeviceInput(device: camera)
       guard captureSession.canAddInput(wideAngleInput) else {
           print("can not add camera input")
           throw NSError()
       }
       
       captureSession.addInputWithNoConnections(wideAngleInput)
       
       guard let wideAnglePort = wideAngleInput.ports(
           for: .video, sourceDeviceType: camera.deviceType,
           sourceDevicePosition: camera.position).first else {
           print("can not find wide angle port")
           throw NSError()
       }
       
       self.wideAnglePort = wideAnglePort
       
       // outputをsessionに追加する
       wideAngleOutput = AVCaptureMovieFileOutput()
       guard captureSession.canAddOutput(wideAngleOutput) else {
           print("can not add wide angle output")
           throw NSError()
       }
       
       captureSession.addOutputWithNoConnections(wideAngleOutput)
       
       // inputとoutputを接続する
       wideAngleVideoConnection = AVCaptureConnection(
           inputPorts: [wideAnglePort], output: wideAngleOutput)
       
       wideAngleVideoConnection.videoOrientation = .portrait
       if (wideAngleVideoConnection.isVideoStabilizationSupported) {
           wideAngleVideoConnection.preferredVideoStabilizationMode = .cinematicExtended
       }
       
       guard captureSession.canAddConnection(wideAngleVideoConnection) else {
           print("can not add wide angle video connetion")
           throw NSError()
       }
       
       captureSession.addConnection(wideAngleVideoConnection)
       
       // マイクとoutputを接続する
       let audioConnection = AVCaptureConnection(
           inputPorts: [audioPort], output: wideAngleOutput)
       
       guard captureSession.canAddConnection(audioConnection) else {
           print("can not add audio connection")
           throw NSError()
       }
   }
   
   
   // MARK: - 望遠カメラの設定
   private func setupTeleCamera() throws {
       guard let camera = AVCaptureDevice.default(
           .builtInTelephotoCamera, for: .video, position: .back) else {
           print("not found builtin telephoto camera")
           throw NSError()
       }
       
       telephotoInput = try AVCaptureDeviceInput(device: camera)
       guard captureSession.canAddInput(telephotoInput) else {
           print("can not add telephoto camera")
           throw NSError()
       }
       
       captureSession.addInputWithNoConnections(telephotoInput)
       
       guard let telephotoPort = telephotoInput.ports(
           for: .video,
           sourceDeviceType: camera.deviceType,
           sourceDevicePosition: camera.position).first else {
           print("can not fine telephoto input port")
           throw NSError()
       }
       
       self.telephotoPort = telephotoPort
       
       // outputの設定
       telephotoOutput = AVCaptureMovieFileOutput()
       guard captureSession.canAddOutput(telephotoOutput) else {
           print("can not add telephoto output")
           throw NSError()
       }
       
       captureSession.addOutputWithNoConnections(telephotoOutput)
       
       // inputとoutputを接続する
       telephotoVideoConnection = AVCaptureConnection(
           inputPorts: [telephotoPort], output: telephotoOutput)
       
       telephotoVideoConnection.videoOrientation = .portrait
       if telephotoVideoConnection.isVideoStabilizationSupported {
           telephotoVideoConnection.preferredVideoStabilizationMode = .cinematicExtended
       }
       
       guard captureSession.canAddConnection(telephotoVideoConnection) else {
           print("can not add telephoto video connection")
           throw NSError()
       }
       
       captureSession.addConnection(telephotoVideoConnection)
       
       // マイクとinputとoutputを接続する
       let audioConnection = AVCaptureConnection(
           inputPorts: [audioPort], output: telephotoOutput)
       
       guard captureSession.canAddConnection(audioConnection) else {
           print("can not add audio connection. telephoto")
           throw NSError()
       }
       
       captureSession.addConnection(audioConnection)
       
       // プレビューの設定
       videoPreviewLayer = AVCaptureVideoPreviewLayer()
       videoPreviewLayer.setSessionWithNoConnection(captureSession)
       videoPreviewLayer.videoGravity = .resizeAspect
       videoPreviewLayer.bounds = previewView.bounds
       
       let layerConnection = AVCaptureConnection(
           inputPort: telephotoPort, videoPreviewLayer: videoPreviewLayer)
       layerConnection.videoOrientation = .portrait
       
       guard captureSession.canAddConnection(layerConnection) else {
           print("can not add layer connection")
           throw NSError()
       }
       
       captureSession.addConnection(layerConnection)
   }
}

トップ   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS