diff options
author | Lev Zelenskiy <lev.zelenskiy@nokia.com> | 2012-03-05 14:16:06 +1000 |
---|---|---|
committer | Qt by Nokia <qt-info@nokia.com> | 2012-03-21 05:43:37 +0100 |
commit | b1eba5e9b2fa017228826c5962f437a50ce59e21 (patch) | |
tree | eed7438cc09fbeadb77c46aebb21e8c07c199dbb /src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp | |
parent | 2c034beab5a8d72a148c47e85e020dc64c58068f (diff) |
QMediaPlayer: GStreamer backend changes for playlist support.
Register type find function to check if unrecognized media is a playlist.
Emit MediaIsPlaylist error and let frontend handle playlists.
Change-Id: Ib17da1c46014ac3c0f2f48b75ea9de2f0428b573
Reviewed-by: Dmytro Poplavskiy <dmytro.poplavskiy@nokia.com>
Diffstat (limited to 'src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp')
-rw-r--r-- | src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp | 79 |
1 files changed, 65 insertions, 14 deletions
diff --git a/src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp b/src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp index 44ca79776..785de969a 100644 --- a/src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp +++ b/src/plugins/gstreamer/mediaplayer/qgstreamerplayersession.cpp @@ -47,6 +47,7 @@ #include "qgstreamervideorendererinterface.h" #include "gstvideoconnector.h" #include <private/qgstutils_p.h> +#include <private/playlistfileparser_p.h> #include <gst/gstvalue.h> #include <gst/base/gstbasesrc.h> @@ -113,8 +114,12 @@ QGstreamerPlayerSession::QGstreamerPlayerSession(QObject *parent) m_displayPrerolledFrame(true), m_sourceType(UnknownSrc), m_everPlayed(false), - m_isLiveSource(false) + m_isLiveSource(false), + m_isPlaylist(false) { + gboolean result = gst_type_find_register(0, "playlist", GST_RANK_MARGINAL, playlistTypeFindFunction, 0, 0, this, 0); + Q_ASSERT(result == TRUE); + #ifdef USE_PLAYBIN2 m_playbin = gst_element_factory_make("playbin2", NULL); #endif @@ -236,6 +241,7 @@ void QGstreamerPlayerSession::loadFromStream(const QNetworkRequest &request, QIO m_duration = -1; m_lastPosition = 0; m_haveQueueElement = false; + m_isPlaylist = false; if (m_appSrc) m_appSrc->deleteLater(); @@ -268,6 +274,7 @@ void QGstreamerPlayerSession::loadFromUri(const QNetworkRequest &request) m_duration = -1; m_lastPosition = 0; m_haveQueueElement = false; + m_isPlaylist = false; if (m_playbin) { m_tags.clear(); @@ -794,10 +801,13 @@ bool QGstreamerPlayerSession::play() if (m_playbin) { m_pendingState = QMediaPlayer::PlayingState; if (gst_element_set_state(m_playbin, GST_STATE_PLAYING) == GST_STATE_CHANGE_FAILURE) { - qWarning() << "GStreamer; Unable to play -" << m_request.url().toString(); - m_pendingState = m_state = QMediaPlayer::StoppedState; - - emit stateChanged(m_state); + if (!m_isPlaylist) { + qWarning() << "GStreamer; Unable to play -" << m_request.url().toString(); + m_pendingState = m_state = QMediaPlayer::StoppedState; + emit stateChanged(m_state); + } else { + return true; + } } else { resumeVideoProbes(); return true; @@ -818,10 +828,13 @@ bool QGstreamerPlayerSession::pause() return true; if (gst_element_set_state(m_playbin, GST_STATE_PAUSED) == GST_STATE_CHANGE_FAILURE) { - qWarning() << "GStreamer; Unable to pause -" << m_request.url().toString(); - m_pendingState = m_state = QMediaPlayer::StoppedState; - - emit stateChanged(m_state); + if (!m_isPlaylist) { + qWarning() << "GStreamer; Unable to pause -" << m_request.url().toString(); + m_pendingState = m_state = QMediaPlayer::StoppedState; + emit stateChanged(m_state); + } else { + return true; + } } else { resumeVideoProbes(); return true; @@ -1199,13 +1212,20 @@ bool QGstreamerPlayerSession::processBusMessage(const QGstreamerMessage &message gst_message_parse_warning(gm, &err, &debug); if (err->domain == GST_STREAM_ERROR && err->code == GST_STREAM_ERROR_CODEC_NOT_FOUND) emit error(int(QMediaPlayer::FormatError), tr("Cannot play stream of type: <unknown>")); - qWarning() << "Warning:" << QString::fromUtf8(err->message); + // GStreamer shows warning for HTTP playlists + if (!m_isPlaylist) + qWarning() << "Warning:" << QString::fromUtf8(err->message); g_error_free(err); g_free(debug); } else if (GST_MESSAGE_TYPE(gm) == GST_MESSAGE_ERROR) { GError *err; gchar *debug; gst_message_parse_error(gm, &err, &debug); + + // remember playlist value, + // it could be set to false after call to processInvalidMedia + bool isPlaylist = m_isPlaylist; + // Nearly all errors map to ResourceError QMediaPlayer::Error qerror = QMediaPlayer::ResourceError; if (err->domain == GST_STREAM_ERROR @@ -1214,7 +1234,9 @@ bool QGstreamerPlayerSession::processBusMessage(const QGstreamerMessage &message qerror = QMediaPlayer::AccessDeniedError; } processInvalidMedia(qerror, QString::fromUtf8(err->message)); - qWarning() << "Error:" << QString::fromUtf8(err->message); + if (!isPlaylist) + qWarning() << "Error:" << QString::fromUtf8(err->message); + g_error_free(err); g_free(debug); } @@ -1640,9 +1662,14 @@ void QGstreamerPlayerSession::processInvalidMedia(QMediaPlayer::Error errorCode, #ifdef DEBUG_PLAYBIN qDebug() << Q_FUNC_INFO; #endif - emit invalidMedia(); - stop(); - emit error(int(errorCode), errorString); + if (m_isPlaylist) { + stop(); + emit error(int(QMediaPlayer::MediaIsPlaylist), tr("Media is loaded as a playlist")); + } else { + emit invalidMedia(); + stop(); + emit error(int(errorCode), errorString); + } } void QGstreamerPlayerSession::showPrerollFrames(bool enabled) @@ -1795,4 +1822,28 @@ void QGstreamerPlayerSession::resumeVideoProbes() probe->stopFlushing(); } +void QGstreamerPlayerSession::playlistTypeFindFunction(GstTypeFind *find, gpointer userData) +{ + QGstreamerPlayerSession* session = (QGstreamerPlayerSession*)userData; + + const gchar *uri = 0; + g_object_get(G_OBJECT(session->m_playbin), "uri", &uri, NULL); + + guint64 length = gst_type_find_get_length(find); + if (!length) + length = 1024; + else + length = qMin(length, guint64(1024)); + + while (length > 0) { + guint8 *data = gst_type_find_peek(find, 0, length); + if (data) { + session->m_isPlaylist = (QPlaylistFileParser::findPlaylistType(QString::fromUtf8(uri), 0, data, length) != QPlaylistFileParser::UNKNOWN); + return; + } + length >>= 1; // for HTTP files length is not available, + // so we have to try different buffer sizes + } +} + QT_END_NAMESPACE |