Merge remote-tracking branch 'origin/5.3' into dev
Change-Id: I38ebcb3da0e4d2acc9e7108c9579ea98323864e0
This commit is contained in:
61
dist/changes-5.3.1
vendored
Normal file
61
dist/changes-5.3.1
vendored
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
Qt 5.3.1 is a bug-fix release. It maintains both forward and backward
|
||||||
|
compatibility (source and binary) with Qt 5.3.0.
|
||||||
|
|
||||||
|
For more details, refer to the online documentation included in this
|
||||||
|
distribution. The documentation is also available online:
|
||||||
|
|
||||||
|
http://qt-project.org/doc/qt-5.3
|
||||||
|
|
||||||
|
The Qt version 5.3 series is binary compatible with the 5.2.x series.
|
||||||
|
Applications compiled for 5.2 will continue to run with 5.3.
|
||||||
|
|
||||||
|
Some of the changes listed in this file include issue tracking numbers
|
||||||
|
corresponding to tasks in the Qt Bug Tracker:
|
||||||
|
|
||||||
|
http://bugreports.qt-project.org/
|
||||||
|
|
||||||
|
Each of these identifiers can be entered in the bug tracker to obtain more
|
||||||
|
information about a particular change.
|
||||||
|
|
||||||
|
****************************************************************************
|
||||||
|
* Library *
|
||||||
|
****************************************************************************
|
||||||
|
|
||||||
|
QtMultimedia
|
||||||
|
------------
|
||||||
|
|
||||||
|
- Importing QtMultimedia in QML with the 5.3 version number is now
|
||||||
|
correctly recognized.
|
||||||
|
- [QTBUG-38218][QTBUG-30447] VideoOutput (QML): Fix garbled rendering of
|
||||||
|
video frames when the stride is not equal to the width.
|
||||||
|
- [QTBUG-38755] Fixed parsing PLS playlist files when the system's locale
|
||||||
|
is not English.
|
||||||
|
|
||||||
|
****************************************************************************
|
||||||
|
* Platform Specific Changes *
|
||||||
|
****************************************************************************
|
||||||
|
|
||||||
|
Android
|
||||||
|
-------
|
||||||
|
|
||||||
|
- A media player's volume is now preserved when loading a new media.
|
||||||
|
- QMediaPlayer can now play Qt resource files on Android 4.1 and lower.
|
||||||
|
- [QTBUG-39015] Fixed sound being in rare occasions garbled when playing
|
||||||
|
audio with QAudioOutput and QSoundEffect.
|
||||||
|
- [QTBUG-39346] QMediaPlayer and the corresponding QML types can now play
|
||||||
|
files located in the application private storage, such as temporary
|
||||||
|
files.
|
||||||
|
|
||||||
|
Linux
|
||||||
|
-----
|
||||||
|
|
||||||
|
- [QTBUG-39202] Fixed crash on application startup when using a static
|
||||||
|
version of Qt.
|
||||||
|
- [QTBUG-38465] Fixed media player dropping a lot of frames when playing a
|
||||||
|
live stream.
|
||||||
|
|
||||||
|
Windows
|
||||||
|
-------
|
||||||
|
|
||||||
|
- [QTBUG-39202] Fixed crash on application startup when using a static
|
||||||
|
version of Qt.
|
||||||
@@ -66,6 +66,7 @@ Generator::Generator(const QAudioFormat &format,
|
|||||||
: QIODevice(parent)
|
: QIODevice(parent)
|
||||||
, m_pos(0)
|
, m_pos(0)
|
||||||
{
|
{
|
||||||
|
if (format.isValid())
|
||||||
generateData(format, durationUs, sampleRate);
|
generateData(format, durationUs, sampleRate);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -133,12 +134,14 @@ void Generator::generateData(const QAudioFormat &format, qint64 durationUs, int
|
|||||||
qint64 Generator::readData(char *data, qint64 len)
|
qint64 Generator::readData(char *data, qint64 len)
|
||||||
{
|
{
|
||||||
qint64 total = 0;
|
qint64 total = 0;
|
||||||
|
if (!m_buffer.isEmpty()) {
|
||||||
while (len - total > 0) {
|
while (len - total > 0) {
|
||||||
const qint64 chunk = qMin((m_buffer.size() - m_pos), len - total);
|
const qint64 chunk = qMin((m_buffer.size() - m_pos), len - total);
|
||||||
memcpy(data + total, m_buffer.constData() + m_pos, chunk);
|
memcpy(data + total, m_buffer.constData() + m_pos, chunk);
|
||||||
m_pos = (m_pos + chunk) % m_buffer.size();
|
m_pos = (m_pos + chunk) % m_buffer.size();
|
||||||
total += chunk;
|
total += chunk;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
return total;
|
return total;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -181,8 +181,7 @@ that the divider should be displayed.
|
|||||||
|
|
||||||
The main.qml file shows a
|
The main.qml file shows a
|
||||||
\l{video/qmlvideofx/qml/qmlvideofx/FileOpen.qml}{FileOpen}, which allows
|
\l{video/qmlvideofx/qml/qmlvideofx/FileOpen.qml}{FileOpen}, which allows
|
||||||
the user to select the input source and an
|
the user to select the input source and an EffectSelectionPanel
|
||||||
\l{video/qmlvideofx/qml/qmlvideofx/EffectSelectionPanel.qml}{EffectSelectionPanel}
|
|
||||||
item, which lists each of the available shader effects. As described above, a
|
item, which lists each of the available shader effects. As described above, a
|
||||||
\l{video/qmlvideofx/qml/qmlvideofx/Content.qml}{Content} item is used to load the
|
\l{video/qmlvideofx/qml/qmlvideofx/Content.qml}{Content} item is used to load the
|
||||||
appropriate input and effect type. A
|
appropriate input and effect type. A
|
||||||
|
|||||||
@@ -634,13 +634,13 @@ void QDeclarativeCamera::setDigitalZoom(qreal value)
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\qmlsignal Camera::stateChanged(state)
|
\qmlsignal Camera::cameraStateChanged(state)
|
||||||
|
|
||||||
This signal is emitted when the camera state has changed to \a state. Since the
|
This signal is emitted when the camera state has changed to \a state. Since the
|
||||||
state changes may take some time to occur this signal may arrive sometime
|
state changes may take some time to occur this signal may arrive sometime
|
||||||
after the state change has been requested.
|
after the state change has been requested.
|
||||||
|
|
||||||
The corresponding handler is \c onStateChanged.
|
The corresponding handler is \c onCameraStateChanged.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
|
|||||||
@@ -71,7 +71,7 @@ classes derived from them.
|
|||||||
|
|
||||||
Consider a developer creating, for example, a media player class called MyPlayer.
|
Consider a developer creating, for example, a media player class called MyPlayer.
|
||||||
It may have special requirements beyond ordinary media players and so may
|
It may have special requirements beyond ordinary media players and so may
|
||||||
need a custom service and a custom control. We can subclass \l QMediaServiceProvider
|
need a custom service and a custom control. We can subclass QMediaServiceProvider
|
||||||
to create our MyServiceProvider class. Also we will create a
|
to create our MyServiceProvider class. Also we will create a
|
||||||
MyMediaService, and the MyMediaControl to manipulate the media service.
|
MyMediaService, and the MyMediaControl to manipulate the media service.
|
||||||
|
|
||||||
|
|||||||
@@ -38,5 +38,5 @@
|
|||||||
QML alternatives. If your application is serving complex use cases such as
|
QML alternatives. If your application is serving complex use cases such as
|
||||||
decoding media files, accessing video or audio buffers, use the C++
|
decoding media files, accessing video or audio buffers, use the C++
|
||||||
alternative. For more details about the complex audio, video, and camera use
|
alternative. For more details about the complex audio, video, and camera use
|
||||||
cases supported by the C++ classes, refer to \l {Qt Multimedia Overview}.
|
cases supported by the C++ classes, refer to \l {Multimedia}{Multimedia Overview}.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -63,7 +63,6 @@ QAlsaAudioInput::QAlsaAudioInput(const QByteArray &device)
|
|||||||
{
|
{
|
||||||
bytesAvailable = 0;
|
bytesAvailable = 0;
|
||||||
handle = 0;
|
handle = 0;
|
||||||
ahandler = 0;
|
|
||||||
access = SND_PCM_ACCESS_RW_INTERLEAVED;
|
access = SND_PCM_ACCESS_RW_INTERLEAVED;
|
||||||
pcmformat = SND_PCM_FORMAT_S16;
|
pcmformat = SND_PCM_FORMAT_S16;
|
||||||
buffer_size = 0;
|
buffer_size = 0;
|
||||||
|
|||||||
@@ -159,7 +159,6 @@ private:
|
|||||||
unsigned int period_time;
|
unsigned int period_time;
|
||||||
snd_pcm_uframes_t buffer_frames;
|
snd_pcm_uframes_t buffer_frames;
|
||||||
snd_pcm_uframes_t period_frames;
|
snd_pcm_uframes_t period_frames;
|
||||||
snd_async_handler_t* ahandler;
|
|
||||||
snd_pcm_access_t access;
|
snd_pcm_access_t access;
|
||||||
snd_pcm_format_t pcmformat;
|
snd_pcm_format_t pcmformat;
|
||||||
snd_timestamp_t* timestamp;
|
snd_timestamp_t* timestamp;
|
||||||
|
|||||||
@@ -63,7 +63,6 @@ QAlsaAudioOutput::QAlsaAudioOutput(const QByteArray &device)
|
|||||||
{
|
{
|
||||||
bytesAvailable = 0;
|
bytesAvailable = 0;
|
||||||
handle = 0;
|
handle = 0;
|
||||||
ahandler = 0;
|
|
||||||
access = SND_PCM_ACCESS_RW_INTERLEAVED;
|
access = SND_PCM_ACCESS_RW_INTERLEAVED;
|
||||||
pcmformat = SND_PCM_FORMAT_S16;
|
pcmformat = SND_PCM_FORMAT_S16;
|
||||||
buffer_frames = 0;
|
buffer_frames = 0;
|
||||||
@@ -118,17 +117,6 @@ QAudio::State QAlsaAudioOutput::state() const
|
|||||||
return deviceState;
|
return deviceState;
|
||||||
}
|
}
|
||||||
|
|
||||||
void QAlsaAudioOutput::async_callback(snd_async_handler_t *ahandler)
|
|
||||||
{
|
|
||||||
QAlsaAudioOutput* audioOut;
|
|
||||||
|
|
||||||
audioOut = static_cast<QAlsaAudioOutput*>
|
|
||||||
(snd_async_handler_get_callback_private(ahandler));
|
|
||||||
|
|
||||||
if (audioOut && (audioOut->deviceState == QAudio::ActiveState || audioOut->resuming))
|
|
||||||
audioOut->feedback();
|
|
||||||
}
|
|
||||||
|
|
||||||
int QAlsaAudioOutput::xrun_recovery(int err)
|
int QAlsaAudioOutput::xrun_recovery(int err)
|
||||||
{
|
{
|
||||||
int count = 0;
|
int count = 0;
|
||||||
@@ -512,8 +500,7 @@ bool QAlsaAudioOutput::open()
|
|||||||
snd_pcm_prepare( handle );
|
snd_pcm_prepare( handle );
|
||||||
snd_pcm_start(handle);
|
snd_pcm_start(handle);
|
||||||
|
|
||||||
// Step 5: Setup callback and timer fallback
|
// Step 5: Setup timer
|
||||||
snd_async_add_pcm_handler(&ahandler, handle, async_callback, this);
|
|
||||||
bytesAvailable = bytesFree();
|
bytesAvailable = bytesFree();
|
||||||
|
|
||||||
// Step 6: Start audio processing
|
// Step 6: Start audio processing
|
||||||
@@ -715,21 +702,6 @@ void QAlsaAudioOutput::userFeed()
|
|||||||
deviceReady();
|
deviceReady();
|
||||||
}
|
}
|
||||||
|
|
||||||
void QAlsaAudioOutput::feedback()
|
|
||||||
{
|
|
||||||
updateAvailable();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void QAlsaAudioOutput::updateAvailable()
|
|
||||||
{
|
|
||||||
#ifdef DEBUG_AUDIO
|
|
||||||
QTime now(QTime::currentTime());
|
|
||||||
qDebug()<<now.second()<<"s "<<now.msec()<<"ms :updateAvailable()";
|
|
||||||
#endif
|
|
||||||
bytesAvailable = bytesFree();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool QAlsaAudioOutput::deviceReady()
|
bool QAlsaAudioOutput::deviceReady()
|
||||||
{
|
{
|
||||||
if(pullMode) {
|
if(pullMode) {
|
||||||
|
|||||||
@@ -107,8 +107,6 @@ public:
|
|||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
void userFeed();
|
void userFeed();
|
||||||
void feedback();
|
|
||||||
void updateAvailable();
|
|
||||||
bool deviceReady();
|
bool deviceReady();
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
@@ -126,7 +124,6 @@ private:
|
|||||||
unsigned int period_time;
|
unsigned int period_time;
|
||||||
snd_pcm_uframes_t buffer_frames;
|
snd_pcm_uframes_t buffer_frames;
|
||||||
snd_pcm_uframes_t period_frames;
|
snd_pcm_uframes_t period_frames;
|
||||||
static void async_callback(snd_async_handler_t *ahandler);
|
|
||||||
int xrun_recovery(int err);
|
int xrun_recovery(int err);
|
||||||
|
|
||||||
int setFormat();
|
int setFormat();
|
||||||
@@ -141,7 +138,6 @@ private:
|
|||||||
qint64 elapsedTimeOffset;
|
qint64 elapsedTimeOffset;
|
||||||
char* audioBuffer;
|
char* audioBuffer;
|
||||||
snd_pcm_t* handle;
|
snd_pcm_t* handle;
|
||||||
snd_async_handler_t* ahandler;
|
|
||||||
snd_pcm_access_t access;
|
snd_pcm_access_t access;
|
||||||
snd_pcm_format_t pcmformat;
|
snd_pcm_format_t pcmformat;
|
||||||
snd_timestamp_t* timestamp;
|
snd_timestamp_t* timestamp;
|
||||||
|
|||||||
@@ -234,9 +234,7 @@ void QAndroidCameraFocusControl::updateFocusZones(QCameraFocusZone::FocusZoneSta
|
|||||||
// create a focus zone (50x50 pixel) around the focus point
|
// create a focus zone (50x50 pixel) around the focus point
|
||||||
m_focusZones.clear();
|
m_focusZones.clear();
|
||||||
|
|
||||||
if (m_actualFocusPoint.isNull())
|
if (!m_actualFocusPoint.isNull()) {
|
||||||
return;
|
|
||||||
|
|
||||||
QSize viewportSize = m_session->camera()->previewSize();
|
QSize viewportSize = m_session->camera()->previewSize();
|
||||||
|
|
||||||
if (!viewportSize.isValid())
|
if (!viewportSize.isValid())
|
||||||
@@ -253,6 +251,7 @@ void QAndroidCameraFocusControl::updateFocusZones(QCameraFocusZone::FocusZoneSta
|
|||||||
QRectF area(QPointF(x, y), focusSize);
|
QRectF area(QPointF(x, y), focusSize);
|
||||||
|
|
||||||
m_focusZones.append(QCameraFocusZone(area, status));
|
m_focusZones.append(QCameraFocusZone(area, status));
|
||||||
|
}
|
||||||
|
|
||||||
emit focusZonesChanged();
|
emit focusZonesChanged();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -269,7 +269,7 @@ void QAndroidCaptureSession::stop(bool error)
|
|||||||
delete m_mediaRecorder;
|
delete m_mediaRecorder;
|
||||||
m_mediaRecorder = 0;
|
m_mediaRecorder = 0;
|
||||||
|
|
||||||
if (m_cameraSession) {
|
if (m_cameraSession && m_cameraSession->status() == QCamera::ActiveStatus) {
|
||||||
// Viewport needs to be restarted after recording
|
// Viewport needs to be restarted after recording
|
||||||
restartViewfinder();
|
restartViewfinder();
|
||||||
}
|
}
|
||||||
@@ -278,7 +278,7 @@ void QAndroidCaptureSession::stop(bool error)
|
|||||||
// if the media is saved into the standard media location, register it
|
// if the media is saved into the standard media location, register it
|
||||||
// with the Android media scanner so it appears immediately in apps
|
// with the Android media scanner so it appears immediately in apps
|
||||||
// such as the gallery.
|
// such as the gallery.
|
||||||
QString mediaPath = m_actualOutputLocation.toLocalFile();
|
QString mediaPath = m_usedOutputLocation.toLocalFile();
|
||||||
QString standardLoc = m_cameraSession ? AndroidMultimediaUtils::getDefaultMediaDirectory(AndroidMultimediaUtils::DCIM)
|
QString standardLoc = m_cameraSession ? AndroidMultimediaUtils::getDefaultMediaDirectory(AndroidMultimediaUtils::DCIM)
|
||||||
: AndroidMultimediaUtils::getDefaultMediaDirectory(AndroidMultimediaUtils::Sounds);
|
: AndroidMultimediaUtils::getDefaultMediaDirectory(AndroidMultimediaUtils::Sounds);
|
||||||
if (mediaPath.startsWith(standardLoc))
|
if (mediaPath.startsWith(standardLoc))
|
||||||
@@ -516,6 +516,7 @@ void QAndroidCaptureSession::updateStatus()
|
|||||||
if (m_cameraSession->status() == QCamera::StoppingStatus
|
if (m_cameraSession->status() == QCamera::StoppingStatus
|
||||||
|| !m_cameraSession->captureMode().testFlag(QCamera::CaptureVideo)) {
|
|| !m_cameraSession->captureMode().testFlag(QCamera::CaptureVideo)) {
|
||||||
setState(QMediaRecorder::StoppedState);
|
setState(QMediaRecorder::StoppedState);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_state == QMediaRecorder::RecordingState) {
|
if (m_state == QMediaRecorder::RecordingState) {
|
||||||
|
|||||||
@@ -487,6 +487,11 @@ QUrl CameraBinSession::outputLocation() const
|
|||||||
|
|
||||||
bool CameraBinSession::setOutputLocation(const QUrl& sink)
|
bool CameraBinSession::setOutputLocation(const QUrl& sink)
|
||||||
{
|
{
|
||||||
|
if (!sink.isRelative() && !sink.isLocalFile()) {
|
||||||
|
qWarning("Output location must be a local file");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
m_sink = m_actualSink = sink;
|
m_sink = m_actualSink = sink;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -1007,8 +1012,9 @@ void CameraBinSession::recordVideo()
|
|||||||
if (m_actualSink.isEmpty()) {
|
if (m_actualSink.isEmpty()) {
|
||||||
QString ext = m_mediaContainerControl->suggestedFileExtension(m_mediaContainerControl->actualContainerFormat());
|
QString ext = m_mediaContainerControl->suggestedFileExtension(m_mediaContainerControl->actualContainerFormat());
|
||||||
m_actualSink = QUrl::fromLocalFile(generateFileName("clip_", defaultDir(QCamera::CaptureVideo), ext));
|
m_actualSink = QUrl::fromLocalFile(generateFileName("clip_", defaultDir(QCamera::CaptureVideo), ext));
|
||||||
} else if (!m_actualSink.isLocalFile()) {
|
} else {
|
||||||
m_actualSink = QUrl::fromLocalFile(m_actualSink.toEncoded());
|
// Output location was rejected in setOutputlocation() if not a local file
|
||||||
|
m_actualSink = QUrl::fromLocalFile(QDir::currentPath()).resolved(m_actualSink);
|
||||||
}
|
}
|
||||||
|
|
||||||
QString fileName = m_actualSink.toLocalFile();
|
QString fileName = m_actualSink.toLocalFile();
|
||||||
|
|||||||
@@ -134,8 +134,10 @@ GstElement *QGstreamerCaptureSession::buildEncodeBin()
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Output location was rejected in setOutputlocation() if not a local file
|
||||||
|
QUrl actualSink = QUrl::fromLocalFile(QDir::currentPath()).resolved(m_sink);
|
||||||
GstElement *fileSink = gst_element_factory_make("filesink", "filesink");
|
GstElement *fileSink = gst_element_factory_make("filesink", "filesink");
|
||||||
g_object_set(G_OBJECT(fileSink), "location", m_sink.toString().toLocal8Bit().constData(), NULL);
|
g_object_set(G_OBJECT(fileSink), "location", QFile::encodeName(actualSink.toLocalFile()).constData(), NULL);
|
||||||
gst_bin_add_many(GST_BIN(encodeBin), muxer, fileSink, NULL);
|
gst_bin_add_many(GST_BIN(encodeBin), muxer, fileSink, NULL);
|
||||||
|
|
||||||
if (!gst_element_link(muxer, fileSink)) {
|
if (!gst_element_link(muxer, fileSink)) {
|
||||||
@@ -731,6 +733,11 @@ QUrl QGstreamerCaptureSession::outputLocation() const
|
|||||||
|
|
||||||
bool QGstreamerCaptureSession::setOutputLocation(const QUrl& sink)
|
bool QGstreamerCaptureSession::setOutputLocation(const QUrl& sink)
|
||||||
{
|
{
|
||||||
|
if (!sink.isRelative() && !sink.isLocalFile()) {
|
||||||
|
qWarning("Output location must be a local file");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
m_sink = sink;
|
m_sink = sink;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -371,7 +371,7 @@ void QGstreamerPlayerControl::setMedia(const QMediaContent &content, QIODevice *
|
|||||||
emit bufferStatusChanged(0);
|
emit bufferStatusChanged(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_stream) {
|
if (m_stream && m_stream != stream) {
|
||||||
if (m_ownStream)
|
if (m_ownStream)
|
||||||
delete m_stream;
|
delete m_stream;
|
||||||
m_stream = 0;
|
m_stream = 0;
|
||||||
|
|||||||
Reference in New Issue
Block a user