From 4fa23e08a116b4d9bb67e25771c511838104999f Mon Sep 17 00:00:00 2001 From: Yoann Lopes Date: Wed, 10 Feb 2016 14:52:44 +0100 Subject: AVFoundation: implement QVideoEncoderSettingsControl. Task-number: QTBUG-40338 Change-Id: Ic23dabaad94d7b293019460710ae1a097002e227 Reviewed-by: Christian Stromme --- .../camera/avfmediarecordercontrol_ios.mm | 38 +++++++++++++++++++++- 1 file changed, 37 insertions(+), 1 deletion(-) (limited to 'src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm') diff --git a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm index 73e19e683..3cb33ab58 100644 --- a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm +++ b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm @@ -38,6 +38,8 @@ #include "avfcameracontrol.h" #include "avfcameraservice.h" #include "avfcameradebug.h" +#include "avfvideoencodersettingscontrol.h" +#include "avfcamerautility.h" #include @@ -77,6 +79,7 @@ AVFMediaRecorderControlIOS::AVFMediaRecorderControlIOS(AVFCameraService *service , m_service(service) , m_state(QMediaRecorder::StoppedState) , m_lastStatus(QMediaRecorder::UnloadedStatus) + , m_videoSettings(nil) { Q_ASSERT(service); @@ -107,6 +110,9 @@ AVFMediaRecorderControlIOS::AVFMediaRecorderControlIOS(AVFCameraService *service AVFMediaRecorderControlIOS::~AVFMediaRecorderControlIOS() { [m_writer abort]; + + if (m_videoSettings) + [m_videoSettings release]; } QUrl AVFMediaRecorderControlIOS::outputLocation() const @@ -147,6 +153,32 @@ qreal AVFMediaRecorderControlIOS::volume() const void AVFMediaRecorderControlIOS::applySettings() { + AVFCameraSession *session = m_service->session(); + if (!session) + return; + + if (m_state != QMediaRecorder::StoppedState + || (session->state() != QCamera::ActiveState && session->state() != QCamera::LoadedState) + || !m_service->cameraControl()->captureMode().testFlag(QCamera::CaptureVideo)) { + return; + } + + AVCaptureConnection *conn = [m_service->videoOutput()->videoDataOutput() connectionWithMediaType:AVMediaTypeVideo]; + + m_videoSettings = m_service->videoEncoderSettingsControl()->applySettings(conn); + if (m_videoSettings) + [m_videoSettings retain]; +} + +void AVFMediaRecorderControlIOS::unapplySettings() +{ + AVCaptureConnection *conn = [m_service->videoOutput()->videoDataOutput() connectionWithMediaType:AVMediaTypeVideo]; + m_service->videoEncoderSettingsControl()->unapplySettings(conn); + + if (m_videoSettings) { + [m_videoSettings release]; + m_videoSettings = nil; + } } void AVFMediaRecorderControlIOS::setState(QMediaRecorder::State state) @@ -211,7 +243,9 @@ void AVFMediaRecorderControlIOS::setState(QMediaRecorder::State state) // generated, will restart in assetWriterStarted. [session stopRunning]; - if ([m_writer setupWithFileURL:nsFileURL cameraService:m_service]) { + applySettings(); + + if ([m_writer setupWithFileURL:nsFileURL cameraService:m_service videoSettings:m_videoSettings]) { m_state = QMediaRecorder::RecordingState; m_lastStatus = QMediaRecorder::StartingStatus; @@ -270,6 +304,8 @@ void AVFMediaRecorderControlIOS::assetWriterFinished() else m_lastStatus = QMediaRecorder::UnloadedStatus; + unapplySettings(); + m_service->videoOutput()->resetCaptureDelegate(); [m_service->session()->captureSession() startRunning]; -- cgit v1.2.3 From 2303d2fef8987f32b1615710ef8930f8d2854373 Mon Sep 17 00:00:00 2001 From: Yoann Lopes Date: Thu, 11 Feb 2016 01:47:12 +0100 Subject: AVFoundation: implement QMediaContainerControl. Change-Id: I5097a0450f5836e48a697249619a1822775f3ad8 Reviewed-by: Timur Pocheptsov --- src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm') diff --git a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm index 3cb33ab58..2052afb50 100644 --- a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm +++ b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm @@ -39,6 +39,7 @@ #include "avfcameraservice.h" #include "avfcameradebug.h" #include "avfvideoencodersettingscontrol.h" +#include "avfmediacontainercontrol.h" #include "avfcamerautility.h" #include @@ -215,7 +216,8 @@ void AVFMediaRecorderControlIOS::setState(QMediaRecorder::State state) const QString path(m_outputLocation.scheme() == QLatin1String("file") ? m_outputLocation.path() : m_outputLocation.toString()); const QUrl fileURL(QUrl::fromLocalFile(m_storageLocation.generateFileName(path, QCamera::CaptureVideo, - QLatin1String("clip_"), QLatin1String("mp4")))); + QLatin1String("clip_"), + m_service->mediaContainerControl()->containerFormat()))); NSURL *nsFileURL = fileURL.toNSURL(); if (!nsFileURL) { -- cgit v1.2.3 From f5de14107094080f15fad3beffb64ad95ff6c5e4 Mon Sep 17 00:00:00 2001 From: Yoann Lopes Date: Thu, 11 Feb 2016 04:34:57 +0100 Subject: AVFoundation: implement QAudioEncoderSettings. Change-Id: I24d3da1417142bc80bc6b6c1c8124c246afe03db Reviewed-by: Timur Pocheptsov Reviewed-by: Christian Stromme --- .../camera/avfmediarecordercontrol_ios.mm | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) (limited to 'src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm') diff --git a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm index 2052afb50..f2c16f675 100644 --- a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm +++ b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm @@ -38,6 +38,7 @@ #include "avfcameracontrol.h" #include "avfcameraservice.h" #include "avfcameradebug.h" +#include "avfaudioencodersettingscontrol.h" #include "avfvideoencodersettingscontrol.h" #include "avfmediacontainercontrol.h" #include "avfcamerautility.h" @@ -80,6 +81,7 @@ AVFMediaRecorderControlIOS::AVFMediaRecorderControlIOS(AVFCameraService *service , m_service(service) , m_state(QMediaRecorder::StoppedState) , m_lastStatus(QMediaRecorder::UnloadedStatus) + , m_audioSettings(nil) , m_videoSettings(nil) { Q_ASSERT(service); @@ -112,6 +114,8 @@ AVFMediaRecorderControlIOS::~AVFMediaRecorderControlIOS() { [m_writer abort]; + if (m_audioSettings) + [m_audioSettings release]; if (m_videoSettings) [m_videoSettings release]; } @@ -164,8 +168,13 @@ void AVFMediaRecorderControlIOS::applySettings() return; } - AVCaptureConnection *conn = [m_service->videoOutput()->videoDataOutput() connectionWithMediaType:AVMediaTypeVideo]; + // audio settings + m_audioSettings = m_service->audioEncoderSettingsControl()->applySettings(); + if (m_audioSettings) + [m_audioSettings retain]; + // video settings + AVCaptureConnection *conn = [m_service->videoOutput()->videoDataOutput() connectionWithMediaType:AVMediaTypeVideo]; m_videoSettings = m_service->videoEncoderSettingsControl()->applySettings(conn); if (m_videoSettings) [m_videoSettings retain]; @@ -173,9 +182,15 @@ void AVFMediaRecorderControlIOS::applySettings() void AVFMediaRecorderControlIOS::unapplySettings() { + m_service->audioEncoderSettingsControl()->unapplySettings(); + AVCaptureConnection *conn = [m_service->videoOutput()->videoDataOutput() connectionWithMediaType:AVMediaTypeVideo]; m_service->videoEncoderSettingsControl()->unapplySettings(conn); + if (m_audioSettings) { + [m_audioSettings release]; + m_audioSettings = nil; + } if (m_videoSettings) { [m_videoSettings release]; m_videoSettings = nil; @@ -247,7 +262,9 @@ void AVFMediaRecorderControlIOS::setState(QMediaRecorder::State state) applySettings(); - if ([m_writer setupWithFileURL:nsFileURL cameraService:m_service videoSettings:m_videoSettings]) { + if ([m_writer setupWithFileURL:nsFileURL cameraService:m_service + audioSettings:m_audioSettings + videoSettings:m_videoSettings]) { m_state = QMediaRecorder::RecordingState; m_lastStatus = QMediaRecorder::StartingStatus; -- cgit v1.2.3 From c6a8c2c846e8f4305aca05be662172e55d5fb674 Mon Sep 17 00:00:00 2001 From: Yoann Lopes Date: Tue, 9 Feb 2016 23:44:33 +0100 Subject: AVFoundation: fix orientation of recorded videos. Make sure the video is recorded in the same orientation as the device. That means the top of the video matches the physical side of the device which is on top when starting recording. This patch makes sure the behavior is the same as on Android. In a future version, we should have an API to pick the desired orientation of the recorded video. Change-Id: Ia8bbfe621a0e54de3cb6bfe0a520f37e8a932539 Reviewed-by: Christian Stromme --- .../camera/avfmediarecordercontrol_ios.mm | 23 +++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) (limited to 'src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm') diff --git a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm index f2c16f675..e65c98257 100644 --- a/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm +++ b/src/plugins/avfoundation/camera/avfmediarecordercontrol_ios.mm @@ -262,9 +262,26 @@ void AVFMediaRecorderControlIOS::setState(QMediaRecorder::State state) applySettings(); - if ([m_writer setupWithFileURL:nsFileURL cameraService:m_service - audioSettings:m_audioSettings - videoSettings:m_videoSettings]) { + // Make sure the video is recorded in device orientation. + // The top of the video will match the side of the device which is on top + // when recording starts (regardless of the UI orientation). + AVFCameraInfo cameraInfo = m_service->session()->activeCameraInfo(); + int screenOrientation = 360 - m_orientationHandler.currentOrientation(); + float rotation = 0; + if (cameraInfo.position == QCamera::FrontFace) + rotation = (screenOrientation + cameraInfo.orientation) % 360; + else + rotation = (screenOrientation + (360 - cameraInfo.orientation)) % 360; + + // convert to radians + rotation *= M_PI / 180.f; + + if ([m_writer setupWithFileURL:nsFileURL + cameraService:m_service + audioSettings:m_audioSettings + videoSettings:m_videoSettings + transform:CGAffineTransformMakeRotation(rotation)]) { + m_state = QMediaRecorder::RecordingState; m_lastStatus = QMediaRecorder::StartingStatus; -- cgit v1.2.3