From dda1bb47163a39e07ba559d16684b9891193cc85 Mon Sep 17 00:00:00 2001 From: Andrew den Exter Date: Tue, 10 Dec 2013 17:20:59 +1000 Subject: [PATCH] Fix incorrect/missing application of recording settings in camerabin. Don't set profiles if no settings are specified. Apply all settings before starting a pipeline as the mode can switch without being restarted and incompatible video recording settings can prevent the pipeline starting even in image capture mode. Set audio encoding settings and encoder profiles if they are supplied. Change-Id: I06febf977c2cae306383f9dbaae0f81f531b4757 Reviewed-by: Yoann Lopes --- .../camerabin/camerabinaudioencoder.cpp | 9 ++-- .../gstreamer/camerabin/camerabinrecorder.cpp | 6 ++- .../gstreamer/camerabin/camerabinsession.cpp | 41 +++++++++++++++---- .../gstreamer/camerabin/camerabinsession.h | 1 + .../camerabin/camerabinvideoencoder.cpp | 15 +++++-- 5 files changed, 55 insertions(+), 17 deletions(-) diff --git a/src/plugins/gstreamer/camerabin/camerabinaudioencoder.cpp b/src/plugins/gstreamer/camerabin/camerabinaudioencoder.cpp index 78750f03..0fa854cc 100644 --- a/src/plugins/gstreamer/camerabin/camerabinaudioencoder.cpp +++ b/src/plugins/gstreamer/camerabin/camerabinaudioencoder.cpp @@ -106,18 +106,19 @@ void CameraBinAudioEncoder::resetActualSettings() GstEncodingProfile *CameraBinAudioEncoder::createProfile() { QString codec = m_actualAudioSettings.codec(); + QString preset = m_actualAudioSettings.encodingOption(QStringLiteral("preset")).toString(); GstCaps *caps; if (codec.isEmpty()) - caps = gst_caps_new_any(); + return 0; else caps = gst_caps_from_string(codec.toLatin1()); return (GstEncodingProfile *)gst_encoding_audio_profile_new( caps, - NULL, //preset - NULL, //restriction - 0); //presence + !preset.isEmpty() ? preset.toLatin1().constData() : NULL, //preset + NULL, //restriction + 0); //presence } QT_END_NAMESPACE diff --git a/src/plugins/gstreamer/camerabin/camerabinrecorder.cpp b/src/plugins/gstreamer/camerabin/camerabinrecorder.cpp index c8967dfb..4ac0d942 100644 --- a/src/plugins/gstreamer/camerabin/camerabinrecorder.cpp +++ b/src/plugins/gstreamer/camerabin/camerabinrecorder.cpp @@ -191,8 +191,10 @@ GstEncodingContainerProfile *CameraBinRecorder::videoProfile() GstEncodingProfile *audioProfile = m_session->audioEncodeControl()->createProfile(); GstEncodingProfile *videoProfile = m_session->videoEncodeControl()->createProfile(); - gst_encoding_container_profile_add_profile(containerProfile, audioProfile); - gst_encoding_container_profile_add_profile(containerProfile, videoProfile); + if (audioProfile) + gst_encoding_container_profile_add_profile(containerProfile, audioProfile); + if (videoProfile) + gst_encoding_container_profile_add_profile(containerProfile, videoProfile); } return containerProfile; diff --git a/src/plugins/gstreamer/camerabin/camerabinsession.cpp b/src/plugins/gstreamer/camerabin/camerabinsession.cpp index f85811e2..70ed3e23 100644 --- a/src/plugins/gstreamer/camerabin/camerabinsession.cpp +++ b/src/plugins/gstreamer/camerabin/camerabinsession.cpp @@ -94,6 +94,7 @@ #define SUPPORTED_IMAGE_CAPTURE_CAPS_PROPERTY "image-capture-supported-caps" #define SUPPORTED_VIDEO_CAPTURE_CAPS_PROPERTY "video-capture-supported-caps" #define SUPPORTED_VIEWFINDER_CAPS_PROPERTY "viewfinder-supported-caps" +#define AUDIO_CAPTURE_CAPS_PROPERTY "audio-capture-caps" #define IMAGE_CAPTURE_CAPS_PROPERTY "image-capture-caps" #define VIDEO_CAPTURE_CAPS_PROPERTY "video-capture-caps" #define VIEWFINDER_CAPS_PROPERTY "viewfinder-caps" @@ -346,6 +347,32 @@ void CameraBinSession::setupCaptureResolution() } } +void CameraBinSession::setAudioCaptureCaps() +{ + QAudioEncoderSettings settings = m_audioEncodeControl->audioSettings(); + const int sampleRate = settings.sampleRate(); + const int channelCount = settings.channelCount(); + + if (sampleRate == -1 && channelCount == -1) + return; + + GstStructure *structure = gst_structure_new( + "audio/x-raw-int", + "endianness", G_TYPE_INT, 1234, + "signed", G_TYPE_BOOLEAN, TRUE, + "width", G_TYPE_INT, 16, + "depth", G_TYPE_INT, 16, + NULL); + if (sampleRate != -1) + gst_structure_set(structure, "rate", G_TYPE_INT, sampleRate, NULL); + if (channelCount != -1) + gst_structure_set(structure, "channels", G_TYPE_INT, channelCount, NULL); + + GstCaps *caps = gst_caps_new_full(structure, NULL); + g_object_set(G_OBJECT(m_camerabin), AUDIO_CAPTURE_CAPS_PROPERTY, caps, NULL); + gst_caps_unref(caps); +} + GstElement *CameraBinSession::buildCameraSource() { #if CAMERABIN_DEBUG @@ -651,14 +678,14 @@ void CameraBinSession::setState(QCamera::State newState) GstState pending = GST_STATE_NULL; gst_element_get_state(m_camerabin, &binState, &pending, 0); - if (captureMode() == QCamera::CaptureVideo) { - m_recorderControl->applySettings(); + m_recorderControl->applySettings(); - g_object_set (G_OBJECT(m_camerabin), - "video-profile", - m_recorderControl->videoProfile(), - NULL); - } + g_object_set (G_OBJECT(m_camerabin), + "video-profile", + m_recorderControl->videoProfile(), + NULL); + + setAudioCaptureCaps(); setupCaptureResolution(); diff --git a/src/plugins/gstreamer/camerabin/camerabinsession.h b/src/plugins/gstreamer/camerabin/camerabinsession.h index fe419c12..3332f4c7 100644 --- a/src/plugins/gstreamer/camerabin/camerabinsession.h +++ b/src/plugins/gstreamer/camerabin/camerabinsession.h @@ -193,6 +193,7 @@ private slots: private: bool setupCameraBin(); void setupCaptureResolution(); + void setAudioCaptureCaps(); static void updateBusyStatus(GObject *o, GParamSpec *p, gpointer d); QUrl m_sink; diff --git a/src/plugins/gstreamer/camerabin/camerabinvideoencoder.cpp b/src/plugins/gstreamer/camerabin/camerabinvideoencoder.cpp index 47a61c9a..cb479d8d 100644 --- a/src/plugins/gstreamer/camerabin/camerabinvideoencoder.cpp +++ b/src/plugins/gstreamer/camerabin/camerabinvideoencoder.cpp @@ -160,18 +160,25 @@ QPair CameraBinVideoEncoder::rateAsRational(qreal frameRate) const GstEncodingProfile *CameraBinVideoEncoder::createProfile() { QString codec = m_actualVideoSettings.codec(); + QString preset = m_actualVideoSettings.encodingOption(QStringLiteral("preset")).toString(); + GstCaps *caps; if (codec.isEmpty()) - caps = gst_caps_new_any(); + caps = 0; else caps = gst_caps_from_string(codec.toLatin1()); - return (GstEncodingProfile *)gst_encoding_video_profile_new( + GstEncodingVideoProfile *profile = gst_encoding_video_profile_new( caps, - NULL, //preset + !preset.isEmpty() ? preset.toLatin1().constData() : NULL, //preset NULL, //restriction - 0); //presence + 1); //presence + + gst_encoding_video_profile_set_pass(profile, 0); + gst_encoding_video_profile_set_variableframerate(profile, TRUE); + + return (GstEncodingProfile *)profile; } QT_END_NAMESPACE