Как получить переднюю камеру в Swift?
Я пытаюсь получить переднюю камеру с живым видом. Я могу получить заднюю камеру, используя:
var backCamera = AVCaptureDevice.defaultDeviceWithMediaType(AVMediaTypeVideo)
Но я не могу найти, как получить переднюю камеру. Как изменить код выше, чтобы использовать переднюю камеру?
Ответы
Ответ 1
Вот рабочий пример из одного из моих проектов, чтобы получить переднюю камеру. Это находится в objective-c, но доказано, что оно работает и достаточно легко конвертируется в быстрый.
NSArray *videoDevices = [AVCaptureDevice devicesWithMediaType:AVMediaTypeVideo];
AVCaptureDevice *captureDevice = nil;
for (AVCaptureDevice *device in videoDevices){
if (device.position == AVCaptureDevicePositionFront){
captureDevice = device;
break;
}
}
И в Swift 3.2 +:
if let videoDevices = AVCaptureDevice.devices(withMediaType: AVMediaTypeVideo) {
var captureDevice: AVCaptureDevice
for device in videoDevices {
if let device = device as? AVCaptureDevice {
if device.position == AVCaptureDevicePosition.front {
captureDevice = device
break
}
}
}
}
Ответ 2
guard let device = AVCaptureDevice.devices().filter({ $0.position == .Front })
.first as? AVCaptureDevice else {
fatalError("No front facing camera found")
}
Если вы ищете более короткое решение, хотя .filter
, за которым следует .first
, не является наиболее эффективным
Ответ 3
В iOS 10.0 и более поздних версиях вам не нужно выполнять итерацию через AVCaptureDevice
. devices
(или devicesWithMediaType
), чтобы найти камеру по положению. (Фактически, оба этих API устарели в iOS 10 и не возвращают полный набор доступных устройств на iPhone 7 Plus, iPhone 8 Plus или iPhone X.)
Если вам просто нужно найти одно устройство на основе простых характеристик (например, переднюю камеру, которая может снимать видео), просто используйте AVCaptureDevice
. defaultDevice(withDeviceType:mediaType:position:)
. Например:
guard let device = AVCaptureDevice.defaultDevice(
withDeviceType: .builtInWideAngleCamera,
mediaType: AVMediaTypeVideo,
position: .front)
else { fatalError("no front camera. but don't all iOS 10 devices have them?")
// then use the device: captureSession.addInput(device) or whatever
Действительно, все это для большинства случаев использования.
Там также AVCaptureDeviceDiscoverySession
в качестве замены старого метода итерации через массив devices
. Тем не менее, большинство вещей, которые вы обычно повторяете в массиве devices
, можно найти, используя новый метод defaultDevice(withDeviceType:mediaType:position:)
, поэтому вы можете также использовать это и писать меньше кода.
Случаи, когда AVCaptureDeviceDiscoverySession
заслуживают внимания, являются менее распространенными, более сложными случаями: скажем, вы хотите найти все устройства, которые поддерживать определенную частоту кадров или использовать наблюдение за ключевым значением, чтобы увидеть, когда изменяется набор доступных устройств.
Кстати, у Apple также есть руководство к системе захвата фотографий iOS 10/Swift 3, а некоторые пример кода, который показывает лучшие рекомендации для этих API.
Ответ 4
Swift 4, iOS 10+ и Xcode 9 beta 5 заменяет
if let cameraID = AVCaptureDevice.defaultDevice(withDeviceType: AVCaptureDeviceType.builtInWideAngleCamera, mediaType: AVMediaTypeVideo, position: AVCaptureDevicePosition.front)?.localizedName {
//cameraID = "Front Camera"
}
с реализацией AVCaptureDevice.DiscoverySession
if #available(iOS 10,*){
if let cameraID = AVCaptureDevice.DiscoverySession(deviceTypes: [AVCaptureDeviceType.builtInWideAngleCamera], mediaType: AVMediaTypeVideo, position: AVCaptureDevicePosition.front).devices.first?.localizedName{
//cameraID = "Front Camera"
}
}
Ответ 5
Задержки:
guard let device = AVCaptureDevice.default(AVCaptureDevice.DeviceType.builtInWideAngleCamera, for: .video, position: .front) else {
return
}
Ответ 6
На основе решения, представленного mbuff24.
Методы массива включают. First (где:) кроме .filter()
guard let frontCamera = AVCaptureDevice.devices().first(where: { ($0 as AnyObject).position == .front }) as? AVCaptureDevice else {
fatalError("No front facing camera found")
}
Ответ 7
import AVFoundation
import Foundation
@IBOutlet weak var imageView: UIImageView!
let captureSession = AVCaptureSession()
let stillImageOutput = AVCaptureStillImageOutput()
var previewLayer : AVCaptureVideoPreviewLayer?
var captureDevice : AVCaptureDevice?
var Arrdata:[Studentdata] = []
override func viewDidLoad() {
super.viewDidLoad()
captureSession.sessionPreset = AVCaptureSessionPresetHigh
if let devices = AVCaptureDevice.devices() as? [AVCaptureDevice]
{
for device in devices
{
if (device.hasMediaType(AVMediaTypeVideo))
{
if(device.position == AVCaptureDevicePosition.front)
{
captureDevice = device
if captureDevice != nil
{
print("Capture device found")
beginSession()
}
}
}
}
}
}
func beginSession()
{
do
{
try captureSession.addInput(AVCaptureDeviceInput(device: captureDevice))
stillImageOutput.outputSettings = [AVVideoCodecKey:AVVideoCodecJPEG]
if captureSession.canAddOutput(stillImageOutput)
{
captureSession.addOutput(stillImageOutput)
}
}
catch
{
print("error: \(error.localizedDescription)")
}
guard let previewLayer = AVCaptureVideoPreviewLayer(session: captureSession) else
{
print("no preview layer")
return
}
self.view.layer.addSublayer(previewLayer)
previewLayer.frame = self.view.layer.frame
captureSession.startRunning()
self.view.addSubview(imageView)
}