Hello community,

here is the log from the commit of package kdenlive for openSUSE:Factory 
checked in at 2016-06-25 02:01:20
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/kdenlive (Old)
 and      /work/SRC/openSUSE:Factory/.kdenlive.new (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "kdenlive"

Changes:
--------
--- /work/SRC/openSUSE:Factory/kdenlive/kdenlive.changes        2016-05-29 
03:09:46.000000000 +0200
+++ /work/SRC/openSUSE:Factory/.kdenlive.new/kdenlive.changes   2016-06-25 
02:01:22.000000000 +0200
@@ -1,0 +2,8 @@
+Fri Jun 10 17:55:36 UTC 2016 - tittiatc...@gmail.com
+
+- Update to KDE Applications 16.04.2
+   * KDE Applications 16.04.2
+   * https://www.kde.org/announcements/announce-applications-16.04.2.php
+
+
+-------------------------------------------------------------------

Old:
----
  kdenlive-16.04.1.tar.xz

New:
----
  kdenlive-16.04.2.tar.xz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ kdenlive.spec ++++++
--- /var/tmp/diff_new_pack.XXwRot/_old  2016-06-25 02:01:23.000000000 +0200
+++ /var/tmp/diff_new_pack.XXwRot/_new  2016-06-25 02:01:23.000000000 +0200
@@ -19,13 +19,13 @@
 %define mlt_version 0.9.6
 
 Name:           kdenlive
-Version:        16.04.1
+Version:        16.04.2
 Release:        0
 Summary:        Non-linear video editor
 License:        GPL-3.0+
 Group:          Productivity/Multimedia/Video/Editors and Convertors
 Url:            http://www.kdenlive.org/
-Source0:        
http://download.kde.org/stable/applications/16.04.1/src/%{name}-%{version}.tar.xz
+Source0:        
http://download.kde.org/stable/applications/16.04.2/src/%{name}-%{version}.tar.xz
 Patch1:         use-mlt_datadir.patch
 BuildRequires:  desktop-file-utils
 BuildRequires:  fdupes

++++++ kdenlive-16.04.1.tar.xz -> kdenlive-16.04.2.tar.xz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/CMakeLists.txt 
new/kdenlive-16.04.2/CMakeLists.txt
--- old/kdenlive-16.04.1/CMakeLists.txt 2016-05-02 00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/CMakeLists.txt 2016-06-09 19:50:38.000000000 +0200
@@ -6,7 +6,7 @@
 # KDE Application Version, managed by release script
 set (KDE_APPLICATIONS_VERSION_MAJOR "16")
 set (KDE_APPLICATIONS_VERSION_MINOR "04")
-set (KDE_APPLICATIONS_VERSION_MICRO "1")
+set (KDE_APPLICATIONS_VERSION_MICRO "2")
 
 set(KDENLIVE_VERSION 
${KDE_APPLICATIONS_VERSION_MAJOR}.${KDE_APPLICATIONS_VERSION_MINOR}.${KDE_APPLICATIONS_VERSION_MICRO})
 cmake_minimum_required(VERSION 2.8.12)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/bin/bin.cpp 
new/kdenlive-16.04.2/src/bin/bin.cpp
--- old/kdenlive-16.04.1/src/bin/bin.cpp        2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/bin/bin.cpp        2016-06-09 19:50:38.000000000 
+0200
@@ -176,7 +176,7 @@
     bg = scheme.background(KColorScheme::ActiveBackground).color();
     fg = scheme.foreground(KColorScheme::ActiveText).color();
     style.append(QStringLiteral("\nQPushButton:hover 
{margin:3px;padding:2px;background-color: rgb(%1, %2, %3);border-radius: 
4px;border: none;color: rgb(%4, %5, 
%6)}").arg(bg.red()).arg(bg.green()).arg(bg.blue()).arg(fg.red()).arg(fg.green()).arg(fg.blue()));
-    
+
     return style;
 }
 
@@ -1354,6 +1354,7 @@
         m_showDate->setChecked(!view->isColumnHidden(1));
         m_showDesc->setChecked(!view->isColumnHidden(2));
        connect(view->header(), SIGNAL(sectionResized(int,int,int)), this, 
SLOT(slotSaveHeaders()));
+        connect(view->header(), SIGNAL(sectionClicked(int)), this, 
SLOT(slotSaveHeaders()));
         connect(view, SIGNAL(focusView()), this, SLOT(slotGotFocus()));
     }
     else if (m_listType == BinIconView) {
@@ -2861,9 +2862,13 @@
     QString titlepath = m_doc->projectFolder().path() + QDir::separator() + 
"titles/";
     TitleWidget dia_ui(QUrl(), m_doc->timecode(), titlepath, 
pCore->monitorManager()->projectMonitor()->render, pCore->window());
     connect(&dia_ui, SIGNAL(requestBackgroundFrame()), 
pCore->monitorManager()->projectMonitor(), SLOT(slotGetCurrentImage()));
+    if (!path.isEmpty()) {
+        dia_ui.loadTitle(QUrl::fromLocalFile(path));
+    } else {
         QDomDocument doc;
         doc.setContent(clip->getProducerProperty(QStringLiteral("xmldata")));
         dia_ui.setXml(doc);
+    }
         if (dia_ui.exec() == QDialog::Accepted) {
             QMap <QString, QString> newprops;
             newprops.insert(QStringLiteral("xmldata"), 
dia_ui.xml().toString());
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/bin/generators/generators.cpp 
new/kdenlive-16.04.2/src/bin/generators/generators.cpp
--- old/kdenlive-16.04.1/src/bin/generators/generators.cpp      2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/bin/generators/generators.cpp      2016-06-09 
19:50:38.000000000 +0200
@@ -166,10 +166,12 @@
                 return getSavedClip(url.path());
             }
         }
+        Mlt::Tractor trac(*m_producer->profile());
         m_producer->set("length", m_timePos->getValue());
         m_producer->set_in_and_out(0, m_timePos->getValue() - 1);
+        trac.set_track(*m_producer, 0);
         Mlt::Consumer c(*m_producer->profile(), "xml", 
url.path().toUtf8().constData());
-        c.connect(*m_producer);
+        c.connect(trac);
         c.run();
         return url;
     }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/bin/projectclip.cpp 
new/kdenlive-16.04.2/src/bin/projectclip.cpp
--- old/kdenlive-16.04.1/src/bin/projectclip.cpp        2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/bin/projectclip.cpp        2016-06-09 
19:50:38.000000000 +0200
@@ -919,6 +919,8 @@
 void ProjectClip::slotCreateAudioThumbs()
 {
     QMutexLocker lock(&m_audioMutex);
+    if (m_audioThumbsProcess.state() != QProcess::NotRunning)
+        return;
     Mlt::Producer *prod = originalProducer();
     if (!prod || !prod->is_valid()) return;
     AudioStreamInfo *audioInfo = m_controller->audioInfo();
@@ -948,6 +950,7 @@
         updateAudioThumbnail(audioLevels);
         return;
     }
+    bool jobFinished = false;
 
     if (KdenliveSettings::ffmpegaudiothumbnails() && m_type != Playlist) {
         QStringList args;
@@ -962,6 +965,8 @@
             channelFiles << channelTmpfile;
         }
         args << QStringLiteral("-i") << 
QUrl::fromLocalFile(prod->get("resource")).path();
+        // Output progress info
+        args << QStringLiteral("-progress") << QStringLiteral("/dev/stdout");
 
         bool isFFmpeg = KdenliveSettings::ffmpegpath().contains("ffmpeg");
 
@@ -995,82 +1000,83 @@
                 }
         }
         emit updateJobStatus(AbstractClipJob::THUMBJOB, JobWaiting, 0);
-        QProcess audioThumbsProcess;
-        connect(this, SIGNAL(doAbortAudioThumbs()), &audioThumbsProcess, 
SLOT(kill()), Qt::DirectConnection);
-        audioThumbsProcess.start(KdenliveSettings::ffmpegpath(), args);
+        connect(this, SIGNAL(doAbortAudioThumbs()), &m_audioThumbsProcess, 
SLOT(kill()), Qt::DirectConnection);
+        connect(&m_audioThumbsProcess, &QProcess::readyReadStandardOutput, 
this, &ProjectClip::updateFfmpegProgress);
+        m_audioThumbsProcess.start(KdenliveSettings::ffmpegpath(), args);
         bool ffmpegError = false;
-        if (!audioThumbsProcess.waitForStarted()) {
+        if (!m_audioThumbsProcess.waitForStarted()) {
             ffmpegError = true;
         }
-        audioThumbsProcess.waitForFinished();
+        m_audioThumbsProcess.waitForFinished(-1);
         if (m_abortAudioThumb) {
             emit updateJobStatus(AbstractClipJob::THUMBJOB, JobDone, 0);
             m_abortAudioThumb = false;
             return;
         }
-        if (ffmpegError || audioThumbsProcess.exitStatus() == 
QProcess::CrashExit) {
-            emit updateJobStatus(AbstractClipJob::THUMBJOB, JobDone, 0);
-            bin()->emitMessage(i18n("Crash in %1 - creating audio thumbnails", 
KdenliveSettings::ffmpegpath()), ErrorMessage);
-            return;
-        }
 
-        int dataSize = 0;
-        QList <const qint16*> rawChannels;
-        QList <QByteArray> sourceChannels;
-        QList<qint16> data2;
-        for (int i = 0; i < channelFiles.count(); i++) {
-            channelFiles[i]->open();
-            QByteArray res = channelFiles[i]->readAll();
-            channelFiles[i]->close();
-            if (dataSize == 0) {
-                dataSize = res.size();
-            }
-            if (res.isEmpty() || res.size() != dataSize) {
-                // Something went wrong, abort
-                emit updateJobStatus(AbstractClipJob::THUMBJOB, JobDone, 0);
-                bin()->emitMessage(i18n("Error reading audio thumbnail"), 
ErrorMessage);
-                return;
-            }
-            rawChannels << (const qint16*) res.constData();
-            // We need to keep res2 alive or rawChannels data will die
-            sourceChannels << res;
-        }
-        int progress = 0;
-        QList <long> channelsData;
-        double offset = (double) dataSize / (2.0 * lengthInFrames);
-        int intraOffset = 1;
-        if (offset > 1000) {
-            intraOffset = offset / 60;
-        } else if (offset > 250) {
-            intraOffset = offset / 10;
-        }
-        double factor = 800.0 / 32768;
-        for (int i = 0; i < lengthInFrames; i++) {
-            channelsData.clear();
-            for (int k = 0; k < rawChannels.count(); k++) {
-                channelsData << 0;
-            }
-            int pos = (int) (i * offset);
-            int steps = 0;
-            for (int j = 0; j < (int) offset && (pos + j < dataSize); j += 
intraOffset) {
-                steps ++;
+        if (!ffmpegError && m_audioThumbsProcess.exitStatus() != 
QProcess::CrashExit) {
+            int dataSize = 0;
+            QList <const qint16*> rawChannels;
+            QList <QByteArray> sourceChannels;
+            QList<qint16> data2;
+            for (int i = 0; i < channelFiles.count(); i++) {
+                channelFiles[i]->open();
+                QByteArray res = channelFiles[i]->readAll();
+                channelFiles[i]->close();
+                if (dataSize == 0) {
+                    dataSize = res.size();
+                }
+                if (res.isEmpty() || res.size() != dataSize) {
+                    // Something went wrong, abort
+                    emit updateJobStatus(AbstractClipJob::THUMBJOB, JobDone, 
0);
+                    bin()->emitMessage(i18n("Error reading audio thumbnail"), 
ErrorMessage);
+                    return;
+                }
+                rawChannels << (const qint16*) res.constData();
+                // We need to keep res2 alive or rawChannels data will die
+                sourceChannels << res;
+            }
+            int progress = 0;
+            QList <long> channelsData;
+            double offset = (double) dataSize / (2.0 * lengthInFrames);
+            int intraOffset = 1;
+            if (offset > 1000) {
+                intraOffset = offset / 60;
+            } else if (offset > 250) {
+                intraOffset = offset / 10;
+            }
+            double factor = 800.0 / 32768;
+            for (int i = 0; i < lengthInFrames; i++) {
+                channelsData.clear();
                 for (int k = 0; k < rawChannels.count(); k++) {
-                    channelsData[k] += abs(rawChannels[k][pos + j]);
+                    channelsData << 0;
                 }
-
-            }
-            for (int k = 0; k < channelsData.count(); k++) {
-                if (steps) channelsData[k] /= steps;
-                audioLevels << channelsData[k] * factor;
-            }
-            int p = i * 100 / lengthInFrames;
-            if (p != progress) {
-                emit updateJobStatus(AbstractClipJob::THUMBJOB, JobWorking, p);
-                progress = p;
+                int pos = (int) (i * offset);
+                int steps = 0;
+                for (int j = 0; j < (int) offset && (pos + j < dataSize); j += 
intraOffset) {
+                    steps ++;
+                    for (int k = 0; k < rawChannels.count(); k++) {
+                        channelsData[k] += abs(rawChannels[k][pos + j]);
+                    }
+                }
+                for (int k = 0; k < channelsData.count(); k++) {
+                    if (steps) channelsData[k] /= steps;
+                    audioLevels << channelsData[k] * factor;
+                }
+                int p = 50 + (i * 50 / lengthInFrames);
+                if (p != progress) {
+                    emit updateJobStatus(AbstractClipJob::THUMBJOB, 
JobWorking, p);
+                    progress = p;
+                }
+                if (m_abortAudioThumb) break;
             }
-            if (m_abortAudioThumb) break;
+            jobFinished = true;
+        } else {
+            bin()->emitMessage(i18n("Failed to create FFmpeg audio thumbnails, 
using MLT"), ErrorMessage);
         }
-    } else {
+    }
+    if (!jobFinished && !m_abortAudioThumb) {
+        // MLT audio thumbs: slower but safer
         QString service = prod->get("mlt_service");
         if (service == QLatin1String("avformat-novalidate"))
         service = QStringLiteral("avformat");
@@ -1148,6 +1154,18 @@
     m_abortAudioThumb = false;
 }
 
+void ProjectClip::updateFfmpegProgress()
+{
+    QString result = m_audioThumbsProcess.readAllStandardOutput();
+    QStringList lines = result.split('\n');
+    foreach(const QString & data, lines) {
+        if (data.startsWith(QStringLiteral("out_time_ms"))) {
+            long ms = data.section(QLatin1Char('='), 1).toLong();
+            emit updateJobStatus(AbstractClipJob::THUMBJOB, JobWorking, (int) 
(ms / duration().ms() / 20));
+        }
+    }
+}
+
 bool ProjectClip::isTransparent() const
 {
     if (m_type == Text) return true;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/bin/projectclip.h 
new/kdenlive-16.04.2/src/bin/projectclip.h
--- old/kdenlive-16.04.1/src/bin/projectclip.h  2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/bin/projectclip.h  2016-06-09 19:50:38.000000000 
+0200
@@ -236,6 +236,7 @@
     QUrl m_temporaryUrl;
     ClipType m_type;
     Mlt::Producer *m_thumbsProducer;
+    QProcess m_audioThumbsProcess;
     QMutex m_producerMutex;
     QMutex m_thumbMutex;
     QMutex m_audioMutex;
@@ -244,6 +245,9 @@
     const QString geometryWithOffset(const QString &data, int offset);
     void doExtractImage();
 
+private slots:
+    void updateFfmpegProgress();
+
 signals:
     void gotAudioData();
     void refreshPropertiesPanel();
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/bin/projectsortproxymodel.cpp 
new/kdenlive-16.04.2/src/bin/projectsortproxymodel.cpp
--- old/kdenlive-16.04.1/src/bin/projectsortproxymodel.cpp      2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/bin/projectsortproxymodel.cpp      2016-06-09 
19:50:38.000000000 +0200
@@ -28,6 +28,7 @@
 ProjectSortProxyModel::ProjectSortProxyModel(QObject *parent)
      : QSortFilterProxyModel(parent)
 {
+    m_collator.setNumericMode(true);
     m_selection = new QItemSelectionModel(this);
     connect(m_selection, 
SIGNAL(selectionChanged(QItemSelection,QItemSelection)), this, 
SLOT(onCurrentRowChanged(QItemSelection,QItemSelection)));
     setDynamicSortFilter(true);
@@ -95,7 +96,7 @@
         if (leftData.type() == QVariant::DateTime) {
             return leftData.toDateTime() < rightData.toDateTime();
         }
-        return QSortFilterProxyModel::lessThan(right, left);
+        return m_collator.compare(leftData.toString(), rightData.toString()) < 
0;
     }
     if (sortOrder() == Qt::AscendingOrder) return leftType < rightType;
     return leftType > rightType;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/bin/projectsortproxymodel.h 
new/kdenlive-16.04.2/src/bin/projectsortproxymodel.h
--- old/kdenlive-16.04.1/src/bin/projectsortproxymodel.h        2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/bin/projectsortproxymodel.h        2016-06-09 
19:50:38.000000000 +0200
@@ -23,6 +23,7 @@
 #define PROJECTSORTPROXYMODEL_H
 
 #include <QSortFilterProxyModel>
+#include <QCollator>
 
 class QItemSelectionModel;
 
@@ -61,6 +62,7 @@
 private:
     QItemSelectionModel*m_selection;
     QString m_searchString;
+    QCollator m_collator;
 
 signals:
     /** @brief Emitted when the row changes, used to prepare action for 
selected item  */
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/definitions.cpp 
new/kdenlive-16.04.2/src/definitions.cpp
--- old/kdenlive-16.04.1/src/definitions.cpp    2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/definitions.cpp    2016-06-09 19:50:38.000000000 
+0200
@@ -115,6 +115,12 @@
     return frame_rate_num * 100 / frame_rate_den == point.frame_rate_num * 100 
/ point.frame_rate_den;
 }
 
+bool MltVideoProfile::isValid() const
+{
+    return (frame_rate_den > 0 && sample_aspect_den > 0 && display_aspect_den 
> 0 && width > 0);
+}
+
+
 const QVariantList MltVideoProfile::toList() const
 {
     QVariantList result;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/definitions.h 
new/kdenlive-16.04.2/src/definitions.h
--- old/kdenlive-16.04.1/src/definitions.h      2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/definitions.h      2016-06-09 19:50:38.000000000 
+0200
@@ -249,6 +249,7 @@
     bool operator!=(const MltVideoProfile &other) const;
     /** @brief Returns true if both profiles have same fps, and can be mixed 
with the xml producer */
     bool isCompatible(const MltVideoProfile &point) const;
+    bool isValid() const;
     const QVariantList toList() const;
     const QString descriptiveString();
 };
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/dialogs/clipcreationdialog.cpp 
new/kdenlive-16.04.2/src/dialogs/clipcreationdialog.cpp
--- old/kdenlive-16.04.1/src/dialogs/clipcreationdialog.cpp     2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/dialogs/clipcreationdialog.cpp     2016-06-09 
19:50:38.000000000 +0200
@@ -64,7 +64,7 @@
     mimeTypes << QStringLiteral("audio/x-flac") << 
QStringLiteral("audio/x-matroska") << QStringLiteral("audio/mp4") << 
QStringLiteral("audio/mpeg") << QStringLiteral("audio/x-mp3") << 
QStringLiteral("audio/ogg") << QStringLiteral("audio/x-wav") << 
QStringLiteral("audio/x-aiff") << QStringLiteral("audio/aiff") << 
QStringLiteral("application/ogg") << QStringLiteral("application/mxf") << 
QStringLiteral("application/x-shockwave-flash") << QStringLiteral("audio/ac3");
 
     // Image mimes
-    mimeTypes << QStringLiteral("image/gif") << QStringLiteral("image/jpeg") 
<< QStringLiteral("image/png") << QStringLiteral("image/x-tga") << 
QStringLiteral("image/x-bmp") << QStringLiteral("image/svg+xml") << 
QStringLiteral("image/tiff") << QStringLiteral("image/x-xcf") << 
QStringLiteral("image/x-xcf-gimp") << 
QStringLiteral("image/x-vnd.adobe.photoshop") << QStringLiteral("image/x-pcx") 
<< QStringLiteral("image/x-exr") << QStringLiteral("image/x-portable-pixmap");
+    mimeTypes << QStringLiteral("image/gif") << QStringLiteral("image/jpeg") 
<< QStringLiteral("image/png") << QStringLiteral("image/x-tga") << 
QStringLiteral("image/x-bmp") << QStringLiteral("image/svg+xml") << 
QStringLiteral("image/tiff") << QStringLiteral("image/x-xcf") << 
QStringLiteral("image/x-xcf-gimp") << 
QStringLiteral("image/x-vnd.adobe.photoshop") << QStringLiteral("image/x-pcx") 
<< QStringLiteral("image/x-exr") << QStringLiteral("image/x-portable-pixmap") 
<< QStringLiteral("application/x-krita");
 
     QMimeDatabase db;
     QStringList allExtensions;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/dialogs/profilesdialog.cpp 
new/kdenlive-16.04.2/src/dialogs/profilesdialog.cpp
--- old/kdenlive-16.04.1/src/dialogs/profilesdialog.cpp 2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/dialogs/profilesdialog.cpp 2016-06-09 
19:50:38.000000000 +0200
@@ -325,12 +325,11 @@
     QString path;
     bool isCustom = false;
     if (name.contains('/')) isCustom = true;
-
     if (!isCustom) {
         // List the Mlt profiles
         QDir mltDir(KdenliveSettings::mltpath());
-        profilesFiles = mltDir.entryList(profilesFilter, QDir::Files);
-        if (profilesFiles.contains(name)) path = mltDir.absoluteFilePath(name);
+        if (mltDir.exists(name))
+            path = mltDir.absoluteFilePath(name);
     }
     if (isCustom || path.isEmpty()) {
         path = name;
@@ -425,6 +424,8 @@
     QStringList profilesFiles = mltDir.entryList(profilesFilter, QDir::Files);
     for (int i = 0; i < profilesFiles.size(); ++i) {
         MltVideoProfile test = 
getProfileFromPath(mltDir.absoluteFilePath(profilesFiles.at(i)), 
profilesFiles.at(i));
+        if (!test.isValid())
+            continue;
         if (test == profile) {
             return profilesFiles.at(i);
         }
@@ -433,10 +434,13 @@
     // Check custom profiles
     QStringList customProfiles = 
QStandardPaths::locateAll(QStandardPaths::DataLocation, 
QStringLiteral("profiles/"), QStandardPaths::LocateDirectory);
     for (int i = 0; i < customProfiles.size(); ++i) {
-        profilesFiles = QDir(customProfiles.at(i)).entryList(profilesFilter, 
QDir::Files);
+        QDir customDir(customProfiles.at(i));
+        profilesFiles = customDir.entryList(profilesFilter, QDir::Files);
         for (int j = 0; j < profilesFiles.size(); ++j) {
-            QString path = customProfiles.at(i) + profilesFiles.at(j);
+            QString path = customDir.absoluteFilePath(profilesFiles.at(j));
             MltVideoProfile test = getProfileFromPath(path, path);
+            if (!test.isValid())
+                continue;
             if (test == profile) {
                 return path;
             }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/dialogs/renderwidget.cpp 
new/kdenlive-16.04.2/src/dialogs/renderwidget.cpp
--- old/kdenlive-16.04.1/src/dialogs/renderwidget.cpp   2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/dialogs/renderwidget.cpp   2016-06-09 
19:50:38.000000000 +0200
@@ -1763,21 +1763,38 @@
         }
         QStringList profiles = root.entryList(QDir::Files, QDir::Name);
         foreach(const QString &prof, profiles) {
-            KConfig config(root.absoluteFilePath(prof), KConfig::SimpleConfig 
);
-            KConfigGroup group = config.group(QByteArray());
-            QString extension = group.readEntry("meta.preset.extension");
-            QString note = group.readEntry("meta.preset.note");
-            QTreeWidgetItem *item = new QTreeWidgetItem(QStringList(prof));
-            item->setData(0, GroupRole, groupName);
-            item->setData(0, ExtensionRole, extension);
-            item->setData(0, RenderRole, "avformat");
+            QTreeWidgetItem *item = loadFromMltPreset(groupName, 
root.absoluteFilePath(prof), prof);
+            if (!item)
+                continue;
             item->setData(0, ParamsRole, QString("properties=stills/" + prof));
-            if (!note.isEmpty()) item->setToolTip(0, note);
+            groupItem->addChild(item);
+        }
+        // Add GIF as image sequence
+        root.cdUp();
+        QTreeWidgetItem *item = loadFromMltPreset(groupName, 
root.absoluteFilePath(QStringLiteral("GIF")), QStringLiteral("GIF"));
+        if (item) {
+            item->setData(0, ParamsRole, QString("properties=GIF"));
             groupItem->addChild(item);
         }
     }
 }
 
+QTreeWidgetItem *RenderWidget::loadFromMltPreset(const QString groupName, 
const QString path, const QString profileName)
+{
+    KConfig config(path, KConfig::SimpleConfig);
+    KConfigGroup group = config.group(QByteArray());
+    QString extension = group.readEntry("meta.preset.extension");
+    QString note = group.readEntry("meta.preset.note");
+    if (extension.isEmpty())
+        return NULL;
+    QTreeWidgetItem *item = new QTreeWidgetItem(QStringList(profileName));
+    item->setData(0, GroupRole, groupName);
+    item->setData(0, ExtensionRole, extension);
+    item->setData(0, RenderRole, "avformat");
+    if (!note.isEmpty()) item->setToolTip(0, note);
+    return item;
+}
+
 void RenderWidget::parseFile(const QString &exportFile, bool editable)
 {
     QDomDocument doc;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/dialogs/renderwidget.h 
new/kdenlive-16.04.2/src/dialogs/renderwidget.h
--- old/kdenlive-16.04.1/src/dialogs/renderwidget.h     2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/dialogs/renderwidget.h     2016-06-09 
19:50:38.000000000 +0200
@@ -208,6 +208,8 @@
     void startRendering(RenderJobItem *item);
     bool saveProfile(QDomElement newprofile);
     void errorMessage(const QString &message);
+    /** @brief Create a rendering profile from MLT preset. */
+    QTreeWidgetItem *loadFromMltPreset(const QString groupName, const QString 
path, const QString profileName);
 
 signals:
     void abortProcess(const QString &url);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/doc/kdenlivedoc.cpp 
new/kdenlive-16.04.2/src/doc/kdenlivedoc.cpp
--- old/kdenlive-16.04.1/src/doc/kdenlivedoc.cpp        2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/doc/kdenlivedoc.cpp        2016-06-09 
19:50:38.000000000 +0200
@@ -356,6 +356,8 @@
     QDomElement blk = doc.createElement(QStringLiteral("producer"));
     blk.setAttribute(QStringLiteral("in"), 0);
     blk.setAttribute(QStringLiteral("out"), 500);
+    blk.setAttribute(QStringLiteral("aspect_ratio"), 1);
+    blk.setAttribute(QStringLiteral("set.test_audio"), 0);
     blk.setAttribute(QStringLiteral("id"), QStringLiteral("black"));
 
     QDomElement property = doc.createElement(QStringLiteral("property"));
@@ -1501,9 +1503,15 @@
        path = dir.absoluteFilePath(path);
     }
     m_projectFolder = QUrl::fromLocalFile(path);
-    list = m_document.elementsByTagName(QStringLiteral("profile"));
-    if (!list.isEmpty()) {
-        m_profile = 
ProfilesDialog::getVideoProfileFromXml(list.at(0).toElement());
+    QString profile = m_documentProperties.value(QStringLiteral("profile"));
+    if (!profile.isEmpty())
+        m_profile = ProfilesDialog::getVideoProfile(profile);
+    if (!m_profile.isValid()) {
+        // try to find matching profile from MLT profile properties
+        list = m_document.elementsByTagName(QStringLiteral("profile"));
+        if (!list.isEmpty()) {
+            m_profile = 
ProfilesDialog::getVideoProfileFromXml(list.at(0).toElement());
+        }
     }
     updateProjectProfile(false);
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/effectslist/initeffects.cpp 
new/kdenlive-16.04.2/src/effectslist/initeffects.cpp
--- old/kdenlive-16.04.1/src/effectslist/initeffects.cpp        2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/effectslist/initeffects.cpp        2016-06-09 
19:50:38.000000000 +0200
@@ -156,12 +156,14 @@
         for (int i = 0; i < max; ++i)
             consumersList << consumers->get_name(i);
         delete consumers;
-        if (consumersList.contains(QStringLiteral("rtaudio"))) {
+        movit = true;
+        // Seems like with latest changes, SDL works fine with movit
+        /*if (consumersList.contains(QStringLiteral("rtaudio"))) {
             // enable movit GPU effects / display. Currently, Movit crashes 
with sdl_audio,
             // So enable only when rtaudio is available
             movit = true;
         }
-        else KdenliveSettings::setGpu_accel(false);
+        else KdenliveSettings::setGpu_accel(false);*/
     }
     else KdenliveSettings::setGpu_accel(false);
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/mainwindow.cpp 
new/kdenlive-16.04.2/src/mainwindow.cpp
--- old/kdenlive-16.04.1/src/mainwindow.cpp     2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/mainwindow.cpp     2016-06-09 19:50:38.000000000 
+0200
@@ -718,6 +718,11 @@
     loadDockActions();
     loadClipActions();
     pCore->bin()->rebuildMenu();
+    QMenu *monitorOverlay = 
static_cast<QMenu*>(factory()->container(QStringLiteral("monitor_config_overlay"),
 this));
+    if (monitorOverlay) {
+        
m_projectMonitor->setupMenu(static_cast<QMenu*>(factory()->container(QStringLiteral("monitor_go"),
 this)), monitorOverlay, m_playZone, m_loopZone, NULL, m_loopClip);
+        
m_clipMonitor->setupMenu(static_cast<QMenu*>(factory()->container(QStringLiteral("monitor_go"),
 this)), monitorOverlay, m_playZone, m_loopZone, 
static_cast<QMenu*>(factory()->container(QStringLiteral("marker_menu"), this)));
+    }
 }
 
 void MainWindow::slotReloadEffects()
@@ -2727,7 +2732,6 @@
     unplugActionList(QStringLiteral("add_effect"));
     plugActionList(QStringLiteral("add_effect"), m_effectsMenu->actions());
 
-
     QList <QAction *>clipJobActions = getExtraActions("clipjobs");
     unplugActionList("clip_jobs");
     plugActionList("clip_jobs", clipJobActions);
@@ -2755,7 +2759,7 @@
     sortedList.sort(Qt::CaseInsensitive);
     foreach(const QString &text, sortedList) {
         orderedList << sorted.value(text);
-    }    
+    }
     unplugActionList( "dock_actions" );
     plugActionList( "dock_actions", orderedList);
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/monitor/glwidget.cpp 
new/kdenlive-16.04.2/src/monitor/glwidget.cpp
--- old/kdenlive-16.04.1/src/monitor/glwidget.cpp       2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/monitor/glwidget.cpp       2016-06-09 
19:50:38.000000000 +0200
@@ -139,16 +139,16 @@
 void GLWidget::showEvent(QShowEvent * event)
 {
     QQuickView::showEvent(event);
-    initializeGL();
+    //initializeGL();
 }
 
 void GLWidget::initializeGL()
 {
-    if (m_isInitialized || !isVisible() || !openglContext()) return;
+    //if (m_isInitialized || !isVisible() || !openglContext()) return;
     if (!m_offscreenSurface.isValid()) {
         m_offscreenSurface.setFormat(openglContext()->format());
         m_offscreenSurface.create();
-        openglContext()->makeCurrent(this);
+        //openglContext()->makeCurrent(this);
     }
     initializeOpenGLFunctions();
     qDebug() << "OpenGL vendor: " << QString::fromUtf8((const char*) 
glGetString(GL_VENDOR));
@@ -478,7 +478,7 @@
         if (!m_fbo || m_fbo->size() != QSize(fullWidth, fullHeight)) {
             delete m_fbo;
             QOpenGLFramebufferObjectFormat fmt;
-            fmt.setSamples(0);
+            fmt.setSamples(1);
             fmt.setInternalTextureFormat(GL_RGB); //GL_RGBA32F);  // which one 
is the fastest ?
             m_fbo = new QOpenGLFramebufferObject(fullWidth, fullHeight, fmt); 
//GL_TEXTURE_2D);
         }
@@ -919,7 +919,8 @@
             delete m_consumer;
         }
         // Force rtaudio backend for movit, because with SDL it crashes on 
stop/start
-        QString audioBackend = m_glslManager == NULL ? 
KdenliveSettings::audiobackend() : QStringLiteral("rtaudio");
+        //QString audioBackend = m_glslManager == NULL ? 
KdenliveSettings::audiobackend() : QStringLiteral("rtaudio");
+        QString audioBackend = KdenliveSettings::audiobackend();
         if (serviceName.isEmpty() || serviceName != audioBackend) {
             m_consumer = new Mlt::FilteredConsumer(*m_monitorProfile, 
audioBackend.toUtf8().constData());
             if (m_consumer->is_valid())
@@ -1268,13 +1269,13 @@
     mlt_image_format format = mlt_image_yuv420p;
     frame.get_image(format, width, height);
     // Save this frame for future use and to keep a reference to the GL 
Texture.
-    m_frame = SharedFrame(frame);
+    m_displayFrame = SharedFrame(frame);
 
     if (m_context->isValid()) {
         m_context->makeCurrent(m_surface);
         // Upload each plane of YUV to a texture.
         QOpenGLFunctions* f = m_context->functions();
-        uploadTextures(m_context, m_frame, m_renderTexture);
+        uploadTextures(m_context, m_displayFrame, m_renderTexture);
         f->glBindTexture(GL_TEXTURE_2D, 0);
         check_error(f);
         f->glFinish();
@@ -1286,7 +1287,7 @@
 
         // The frame is now done being modified and can be shared with the rest
         // of the application.
-        emit frameDisplayed(m_frame);
+        emit frameDisplayed(m_displayFrame);
 
         if (sendAudioForAnalysis) {
             // TODO: use mlt audiospectrum filter
@@ -1313,7 +1314,7 @@
 
 void FrameRenderer::showGLFrame(Mlt::Frame frame)
 {
-    if (m_context->isValid()) {
+    if (m_context && m_context->isValid()) {
         int width = 0;
         int height = 0;
 
@@ -1350,7 +1351,8 @@
 
         // The frame is now done being modified and can be shared with the rest
         // of the application.
-        emit frameDisplayed(m_frame);
+        qSwap(m_frame, m_displayFrame);
+        emit frameDisplayed(m_displayFrame);
 
        if (sendAudioForAnalysis) {
             // TODO: use mlt audiospectrum filter
@@ -1396,7 +1398,8 @@
 
         // The frame is now done being modified and can be shared with the rest
         // of the application.
-        emit frameDisplayed(m_frame);
+        qSwap(m_frame, m_displayFrame);
+        emit frameDisplayed(m_displayFrame);
     }
     m_semaphore.release();
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/monitor/glwidget.h 
new/kdenlive-16.04.2/src/monitor/glwidget.h
--- old/kdenlive-16.04.1/src/monitor/glwidget.h 2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/monitor/glwidget.h 2016-06-09 19:50:38.000000000 
+0200
@@ -231,6 +231,7 @@
 private:
     QSemaphore m_semaphore;
     SharedFrame m_frame;
+    SharedFrame m_displayFrame;
     QOpenGLContext* m_context;
     QSurface* m_surface;
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/monitor/monitor.cpp 
new/kdenlive-16.04.2/src/monitor/monitor.cpp
--- old/kdenlive-16.04.1/src/monitor/monitor.cpp        2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/monitor/monitor.cpp        2016-06-09 
19:50:38.000000000 +0200
@@ -407,6 +407,8 @@
 
 void Monitor::setupMenu(QMenu *goMenu, QMenu *overlayMenu, QAction *playZone, 
QAction *loopZone, QMenu *markerMenu, QAction *loopClip)
 {
+    if (m_contextMenu)
+        delete m_contextMenu;
     m_contextMenu = new QMenu(this);
     m_contextMenu->addMenu(m_playMenu);
     if (goMenu)
@@ -1057,21 +1059,23 @@
     slotActivateMonitor();
     if (speed == 0) {
         double currentspeed = render->playSpeed();
-       if (currentspeed >= 0) render->play(-1);
+       if (currentspeed >= 0) 
+            speed = -1;
        else switch((int) currentspeed) {
            case -1:
-               render->play(-2);
+               speed = -2;
                break;
            case -2:
-               render->play(-3);
+               speed = -3;
                break;
            case -3:
-               render->play(-5);
+               speed = -5;
                break;
            default:
-               render->play(-8);
+               speed = -8;
        }
-    } else render->play(speed);
+    } 
+    render->switchPlay(true, speed);
     m_playAction->setActive(true);
 }
 
@@ -1080,23 +1084,22 @@
     slotActivateMonitor();
     if (speed == 0) {
         double currentspeed = render->playSpeed();
-        if (currentspeed <= 0) render->play(1);
+        if (currentspeed <= 0) speed = 1;
         else switch((int) currentspeed) {
         case 1:
-            render->play(2);
+            speed = 2;
             break;
         case 2:
-            render->play(3);
+            speed = 3;
             break;
         case 3:
-            render->play(5);
+            speed = 5;
             break;
         default:
-            render->play(8);
+            speed = 8;
         }
-    } else {
-        render->play(speed);
     }
+    render->switchPlay(true, speed);
     m_playAction->setActive(true);
 }
 
@@ -1191,7 +1194,7 @@
 {
     if (render == NULL) return;
     slotActivateMonitor();
-    render->pause();
+    render->switchPlay(false);
     m_playAction->setActive(false);
 }
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/monitor/monitormanager.cpp 
new/kdenlive-16.04.2/src/monitor/monitormanager.cpp
--- old/kdenlive-16.04.1/src/monitor/monitormanager.cpp 2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/monitor/monitormanager.cpp 2016-06-09 
19:50:38.000000000 +0200
@@ -529,3 +529,4 @@
         m_projectMonitor->slotSetZoneEnd();
     }
 }
+
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/monitor/monitormanager.h 
new/kdenlive-16.04.2/src/monitor/monitormanager.h
--- old/kdenlive-16.04.1/src/monitor/monitormanager.h   2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/monitor/monitormanager.h   2016-06-09 
19:50:38.000000000 +0200
@@ -92,7 +92,7 @@
     void slotZoneEnd();
     void slotSetInPoint();
     void slotSetOutPoint();
-    
+
     /** @brief Switch current monitor to fullscreen. */
     void slotSwitchFullscreen();
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kdenlive-16.04.1/src/monitor/scopes/monitoraudiolevel.cpp 
new/kdenlive-16.04.2/src/monitor/scopes/monitoraudiolevel.cpp
--- old/kdenlive-16.04.1/src/monitor/scopes/monitoraudiolevel.cpp       
2016-05-02 00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/monitor/scopes/monitoraudiolevel.cpp       
2016-06-09 19:50:38.000000000 +0200
@@ -31,6 +31,7 @@
 #include <QVBoxLayout>
 #include <QFont>
 #include <QDebug>
+#include <math.h>
 
 const double log_factor = 1.0 / log10(1.0/127);
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/project/jobs/filterjob.cpp 
new/kdenlive-16.04.2/src/project/jobs/filterjob.cpp
--- old/kdenlive-16.04.1/src/project/jobs/filterjob.cpp 2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/project/jobs/filterjob.cpp 2016-06-09 
19:50:38.000000000 +0200
@@ -86,8 +86,7 @@
             jobs.insert(clip, job);
         }
         return jobs;
-    }
-    if (filterName == QLatin1String("motion_est")) {
+    } else if (filterName == QLatin1String("motion_est")) {
         // Show config dialog
         QPointer<QDialog> d = new QDialog(QApplication::activeWindow());
         Ui::SceneCutDialog_UI ui;
@@ -176,8 +175,7 @@
             jobs.insert(clip, job);
         }
         return jobs;
-    }
-    if (filterName == QLatin1String("vidstab")) {
+    } else if (filterName == QLatin1String("vidstab") || filterName == 
QLatin1String("videostab2") || filterName == QLatin1String("videostab")) {
         // vidstab 
         QPointer<ClipStabilize> d = new ClipStabilize(sources, filterName);
         if (d->exec() == QDialog::Accepted) {
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/renderer.cpp 
new/kdenlive-16.04.2/src/renderer.cpp
--- old/kdenlive-16.04.1/src/renderer.cpp       2016-05-02 00:32:52.000000000 
+0200
+++ new/kdenlive-16.04.2/src/renderer.cpp       2016-06-09 19:50:38.000000000 
+0200
@@ -81,6 +81,8 @@
         m_blackClip = new Mlt::Producer(*m_qmlView->profile(), "colour:black");
         m_blackClip->set("id", "black");
         m_blackClip->set("mlt_type", "producer");
+        m_blackClip->set("aspect_ratio", 1);
+        m_blackClip->set("set.test_audio", 0);
         m_mltProducer = m_blackClip->cut(0, 1);
         m_qmlView->setProducer(m_mltProducer);
         m_mltConsumer = qmlView->consumer();
@@ -689,7 +691,7 @@
     m_isRefreshing = false;
 }
 
-void Render::pause()
+/*void Render::pause()
 {
     requestedSeekPosition = SEEK_INACTIVE;
     if (!m_mltProducer || !m_mltConsumer || !m_isActive)
@@ -697,14 +699,14 @@
     m_mltProducer->set_speed(0.0);
     //if (!m_mltConsumer->is_stopped()) m_mltConsumer->stop();
     //m_mltProducer->seek(m_mltConsumer->position());
-}
+}*/
 
 void Render::setActiveMonitor()
 {
     if (!m_isActive) emit activateMonitor(m_name);
 }
 
-void Render::switchPlay(bool play)
+void Render::switchPlay(bool play, double speed)
 {
     QMutexLocker locker(&m_mutex);
     requestedSeekPosition = SEEK_INACTIVE;
@@ -712,6 +714,7 @@
         return;
     if (m_isZoneMode) resetZoneMode();
     if (play) {
+        double currentSpeed = m_mltProducer->get_speed();
         if (m_name == Kdenlive::ClipMonitor && m_mltConsumer->position() == 
m_mltProducer->get_out()) m_mltProducer->seek(0);
         if (m_mltConsumer->get_int("real_time") != m_qmlView->realTime()) {
             m_mltConsumer->set("real_time", m_qmlView->realTime());
@@ -722,10 +725,14 @@
                 m_mltConsumer->stop();
             }
         }
-        m_mltConsumer->start();
-        m_isRefreshing = true;
-        m_mltConsumer->set("refresh", 1);
-        m_mltProducer->set_speed(1.0);
+        if (currentSpeed == 0) {
+            m_mltConsumer->start();
+            m_isRefreshing = true;
+            m_mltConsumer->set("refresh", 1);
+        } else {
+            m_mltConsumer->purge();
+        }
+        m_mltProducer->set_speed(speed);
     } else {
         m_mltConsumer->purge();
         m_mltProducer->set_speed(0.0);
@@ -744,15 +751,21 @@
     double current_speed = m_mltProducer->get_speed();
     if (current_speed == speed) return;
     if (m_isZoneMode) resetZoneMode();
-    // if (speed == 0.0) m_mltProducer->set("out", m_mltProducer->get_length() 
- 1);
-    m_mltProducer->set_speed(speed);
-    if (m_mltConsumer->is_stopped() && speed != 0) {
-        m_mltConsumer->start();
+    if (speed != 0 && m_mltConsumer->get_int("real_time") != 
m_qmlView->realTime()) {
+        m_mltConsumer->set("real_time", m_qmlView->realTime());
+        m_mltConsumer->set("buffer", 25);
+        m_mltConsumer->set("prefill", 1);
+        // Changes to real_time require a consumer restart if running.
+        if (!m_mltConsumer->is_stopped()) {
+            m_mltConsumer->stop();
+        }
     }
-    if (current_speed == 0 && speed != 0) {
+    if (current_speed == 0) {
+        m_mltConsumer->start();
         m_isRefreshing = true;
         m_mltConsumer->set("refresh", 1);
     }
+    m_mltProducer->set_speed(speed);
 }
 
 void Render::play(const GenTime & startTime)
@@ -2076,7 +2089,7 @@
 }
 
 //Updates all transitions
-QList <TransitionInfo> Render::mltInsertTrack(int ix, const QString &name, 
bool videoTrack)
+QList <TransitionInfo> Render::mltInsertTrack(int ix, const QString &name, 
bool videoTrack, int lowestVideoTrack)
 {
     QList <TransitionInfo> transitionInfos;
     // Track add / delete was only added recently in MLT (pre 0.9.8 release).
@@ -2095,8 +2108,21 @@
     blockSignals(true);
     service.lock();
     Mlt::Tractor tractor(service);
+    // Find available track name
+    QStringList trackNames;
+    for (int i = 0; i < tractor.count(); i++) {
+        QScopedPointer<Mlt::Producer> track(tractor.track(i));
+        trackNames << track->get("id"); 
+    }
+    QString newName = QStringLiteral("playlist0");
+    int i = 1;
+    while (trackNames.contains(newName)) {
+        newName = QString("playlist%1").arg(i);
+        i++;
+    }
     Mlt::Playlist playlist(*service.profile());
     playlist.set("kdenlive:track_name", name.toUtf8().constData());
+    playlist.set("id", newName.toUtf8().constData());
     int ct = tractor.count();
     if (ix > ct) {
         //qDebug() << "// ERROR, TRYING TO insert TRACK " << ix << ", max: " 
<< ct;
@@ -2113,62 +2139,6 @@
     tractor.refresh();
 
     Mlt::Field *field = tractor.field();
-    // Move transitions
-    /*mlt_service serv = m_mltProducer->parent().get_service();
-    mlt_service nextservice = mlt_service_get_producer(serv);
-    mlt_properties properties = MLT_SERVICE_PROPERTIES(nextservice);
-    QString mlt_type = mlt_properties_get(properties, "mlt_type");
-    QString resource = mlt_properties_get(properties, "mlt_service");
-    QList <Mlt::Transition *> trList;
-
-    while (mlt_type == "transition") {
-        if (resource != "mix") {
-            Mlt::Transition transition((mlt_transition) nextservice);
-            nextservice = mlt_service_producer(nextservice);
-            int currentbTrack = transition.get_b_track();
-            int currentaTrack = transition.get_a_track();
-            bool trackChanged = false;
-            bool forceTransitionTrack = false;
-            if (currentbTrack >= ix) {
-                if (currentbTrack == ix && currentaTrack < ix) 
forceTransitionTrack = true;
-                currentbTrack++;
-                trackChanged = true;
-            }
-            if (currentaTrack >= ix) {
-                currentaTrack++;
-                trackChanged = true;
-            }
-            //qDebug()<<"// Newtrans: "<<currentaTrack<<"/"<<currentbTrack;
-
-            // disconnect all transitions
-            Mlt::Properties trans_props(transition.get_properties());
-            Mlt::Transition *cp = new Mlt::Transition(*m_qmlView->profile(), 
transition.get("mlt_service"));
-            Mlt::Properties new_trans_props(cp->get_properties());
-            cloneProperties(new_trans_props, trans_props);
-            //new_trans_props.inherit(trans_props);
-
-            if (trackChanged) {
-                // Transition track needs to be adjusted
-                cp->set("a_track", currentaTrack);
-                cp->set("b_track", currentbTrack);
-                // Check if transition track was changed and needs to be forced
-                if (forceTransitionTrack) cp->set("force_track", 1);
-                TransitionInfo trInfo;
-                trInfo.startPos = GenTime(transition.get_in(), m_fps);
-                trInfo.a_track = currentaTrack;
-                trInfo.b_track = currentbTrack;
-                trInfo.forceTrack = cp->get_int("force_track");
-                transitionInfos.append(trInfo);
-            }
-            trList.append(cp);
-            field->disconnect_service(transition);
-        }
-        else nextservice = mlt_service_producer(nextservice);
-        if (nextservice == NULL) break;
-        properties = MLT_SERVICE_PROPERTIES(nextservice);
-        mlt_type = mlt_properties_get(properties, "mlt_type");
-        resource = mlt_properties_get(properties, "mlt_service");
-    }*/
 
     // Add audio mix transition to last track
     Mlt::Transition mix(*m_qmlView->profile(), "mix");
@@ -2180,14 +2150,17 @@
     field->plant_transition(mix, 0, ix);
 
     if (videoTrack) {
-        Mlt::Transition composite(*m_qmlView->profile(), 
KdenliveSettings::gpu_accel() ? "movit.overlay" : "frei0r.cairoblend");
-        if (composite.is_valid()) {
-            composite.set("a_track", ix - 1);
-            composite.set("b_track", ix);
-            composite.set("internal_added", 237);
-            field->plant_transition(composite, ix - 1, ix);
-        }
-        //mltPlantTransition(field, composite, ct-1, ct);
+       if (ix <= lowestVideoTrack) {
+           // Track was inserted as lowest video track, it should not have a 
composite, but previous lowest should
+           ix = lowestVideoTrack + 1;
+       }
+       Mlt::Transition composite(*m_qmlView->profile(), 
KdenliveSettings::gpu_accel() ? "movit.overlay" : "frei0r.cairoblend");
+       if (composite.is_valid()) {
+           composite.set("a_track", ix - 1);
+           composite.set("b_track", ix);
+           composite.set("internal_added", 237);
+           field->plant_transition(composite, ix - 1, ix);
+       }
     }
 
     /*
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/renderer.h 
new/kdenlive-16.04.2/src/renderer.h
--- old/kdenlive-16.04.1/src/renderer.h 2016-05-02 00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/renderer.h 2016-06-09 19:50:38.000000000 +0200
@@ -138,8 +138,7 @@
      * The speed is relative to normal playback, e.g. 1.0 is normal speed, 0.0
      * is paused, -1.0 means play backwards. It does not specify start/stop */
     void play(double speed);
-    void switchPlay(bool play);
-    void pause();
+    void switchPlay(bool play, double speed = 1.0);
 
     /** @brief Stops playing.
      * @param startTime time to seek to */
@@ -230,7 +229,7 @@
     void mltMoveEffect(int track, const GenTime &position, int oldPos, int 
newPos);
     void mltMoveTrackEffect(int track, int oldPos, int newPos);
 
-    QList <TransitionInfo> mltInsertTrack(int ix, const QString &name, bool 
videoTrack);
+    QList <TransitionInfo> mltInsertTrack(int ix, const QString &name, bool 
videoTrack, int lowestVideoTrack);
 
     //const QList <Mlt::Producer *> producersList();
     void setDropFrames(bool show);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/clipitem.cpp 
new/kdenlive-16.04.2/src/timeline/clipitem.cpp
--- old/kdenlive-16.04.1/src/timeline/clipitem.cpp      2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/clipitem.cpp      2016-06-09 
19:50:38.000000000 +0200
@@ -954,7 +954,7 @@
     const double scale = projectScene()->scale().x();
     double maximumOffset = 8 / scale;
     if (isSelected() || (parentItem() && parentItem()->isSelected())) {
-        int kf = m_keyframeView.mouseOverKeyFrames(rect(), pos, maximumOffset, 
scale);
+        int kf = m_keyframeView.mouseOverKeyFrames(rect(), pos, scale);
         if (kf != -1) {
             return KeyFrame;
         }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/customtrackview.cpp 
new/kdenlive-16.04.2/src/timeline/customtrackview.cpp
--- old/kdenlive-16.04.1/src/timeline/customtrackview.cpp       2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/customtrackview.cpp       2016-06-09 
19:50:38.000000000 +0200
@@ -602,7 +602,7 @@
                     m_scrollTimer.stop();
                 }
             } else if (m_moveOpMode == ResizeStart) {
-                m_document->renderer()->pause();
+                m_document->renderer()->switchPlay(false);
                 if (!m_controlModifier && m_dragItem->type() == AVWidget && 
m_dragItem->parentItem() && m_dragItem->parentItem() != m_selectionGroup) {
                     AbstractGroupItem *parent = static_cast <AbstractGroupItem 
*>(m_dragItem->parentItem());
                     if (parent)
@@ -615,7 +615,7 @@
                 QString offset = 
m_document->timecode().getDisplayTimecode(m_dragItem->cropStart() - 
m_dragItemInfo.cropStart, KdenliveSettings::frametimecode());
                 emit displayMessage(i18n("Crop from start:") + ' ' + crop + ' 
' + i18n("Duration:") + ' ' + duration + ' ' + i18n("Offset:") + ' ' + offset, 
InformationMessage);
             } else if (m_moveOpMode == ResizeEnd) {
-                m_document->renderer()->pause();
+                m_document->renderer()->switchPlay(false);
                 if (!m_controlModifier && m_dragItem->type() == AVWidget && 
m_dragItem->parentItem() && m_dragItem->parentItem() != m_selectionGroup) {
                     AbstractGroupItem *parent = static_cast <AbstractGroupItem 
*>(m_dragItem->parentItem());
                     if (parent) {
@@ -888,7 +888,7 @@
         }
         if (m_tool != RazorTool) activateMonitor();
         else if (m_document->renderer()->isPlaying()) {
-            m_document->renderer()->pause();
+            m_document->renderer()->switchPlay(false);
             return;
         }
     }
@@ -1065,7 +1065,7 @@
             if (m_dragItem->type() == TransitionWidget) {
                 emit displayMessage(i18n("Cannot cut a transition"), 
ErrorMessage);
             } else {
-                m_document->renderer()->pause();
+                m_document->renderer()->switchPlay(false);
                 if (m_dragItem->parentItem() && m_dragItem->parentItem() != 
m_selectionGroup) {
                     
razorGroup(static_cast<AbstractGroupItem*>(m_dragItem->parentItem()), cutPos);
                 } else {
@@ -3201,6 +3201,7 @@
     if (ix == -1 || ix > m_timeline->tracksCount()) {
         ix = m_timeline->tracksCount() + 1;
     }
+    int lowestVideoTrack = m_timeline->getLowestVideoTrack();
 
     // Prepare groups for reload
     QDomDocument doc;
@@ -3227,7 +3228,7 @@
     }
 
     // insert track in MLT's playlist
-    transitionInfos = m_document->renderer()->mltInsertTrack(ix,  
type.trackName, type.type == VideoTrack);
+    transitionInfos = m_document->renderer()->mltInsertTrack(ix,  
type.trackName, type.type == VideoTrack, lowestVideoTrack);
     Mlt::Tractor *tractor = m_document->renderer()->lockService();
     // When adding a track, MLT sometimes incorrectly updates transition's 
tracks
     if (ix < m_timeline->tracksCount()) {
@@ -3242,6 +3243,8 @@
     m_document->renderer()->unlockService(tractor);
     // Reload timeline and m_tracks structure from MLT's playlist
     reloadTimeline();
+    // Check we have correct audio mix
+    m_timeline->fixAudioMixing();
     loadGroups(groups);
 }
 
@@ -3322,9 +3325,12 @@
 
     // Delete track in MLT playlist
     tractor->remove_track(ix);
+    // Make sure lowest video track has no composite
     m_timeline->updateComposites();
     m_document->renderer()->unlockService(tractor);
     reloadTimeline();
+    // Check we have correct audio mix
+    m_timeline->fixAudioMixing();
     loadGroups(groups);
 }
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/headertrack.cpp 
new/kdenlive-16.04.2/src/timeline/headertrack.cpp
--- old/kdenlive-16.04.1/src/timeline/headertrack.cpp   2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/headertrack.cpp   2016-06-09 
19:50:38.000000000 +0200
@@ -120,6 +120,8 @@
     } else if (event->type() == QEvent::MouseButtonDblClick) {
         // Allow editing on double click
         track_number->setEnabled(true);
+        track_number->setFocus(Qt::MouseFocusReason);
+        event->accept();
     }
     return QWidget::eventFilter(obj, event);
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/keyframeview.cpp 
new/kdenlive-16.04.2/src/timeline/keyframeview.cpp
--- old/kdenlive-16.04.1/src/timeline/keyframeview.cpp  2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/keyframeview.cpp  2016-06-09 
19:50:38.000000000 +0200
@@ -22,6 +22,7 @@
 
 #include <QPainter>
 #include <QAction>
+#include <QApplication>
 
 #include "klocalizedstring.h"
 
@@ -462,11 +463,11 @@
 }
 
 
-int KeyframeView::mouseOverKeyFrames(QRectF br, QPointF pos, double maxOffset, 
double scale)
+int KeyframeView::mouseOverKeyFrames(QRectF br, QPointF pos, double scale)
 {
     if (m_keyframeType == NoKeyframe)
         return -1;
-    pos.setX((pos.x() - m_offset)*scale);
+    pos.setX((pos.x() - m_offset) * scale);
     int previousEdit = activeKeyframe;
     for(int i = 0; i < m_keyAnim.key_count(); ++i) {
         int key = m_keyAnim.key_get_frame(i);
@@ -475,10 +476,10 @@
         }
         double value = 
m_keyProperties.anim_get_double(m_inTimeline.toUtf8().constData(), key, 
duration - m_offset);
         QPointF p = keyframeMap(br, key, value);
-        p.setX(p.x()*scale);
+        p.setX(p.x() * scale);
         if (m_keyframeType == GeometryKeyframe)
             p.setY(br.bottom() - br.height() / 2);
-        if ((pos - p).manhattanLength() < maxOffset) {
+        if ((pos - p).manhattanLength() <= m_handleSize / 2) {
            //TODO
             /*setToolTip('[' + QString::number((GenTime(key, m_fps) - 
cropStart()).seconds(), 'f', 2)
                        + i18n("seconds") + ", " + QString::number(value, 'f', 
1) + ']');*/
@@ -487,9 +488,10 @@
                 updateKeyframes();
             }
             return key;
-        } /*else if (p.x() > pos.x() + maxOffset) {
+        }
+        if (p.x() > pos.x()) {
             break;
-        }*/
+        }
     }
     //setToolTip(QString());
     activeKeyframe = -1;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/keyframeview.h 
new/kdenlive-16.04.2/src/timeline/keyframeview.h
--- old/kdenlive-16.04.1/src/timeline/keyframeview.h    2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/keyframeview.h    2016-06-09 
19:50:38.000000000 +0200
@@ -89,7 +89,7 @@
     void drawKeyFrames(QRectF br, int length, bool active, QPainter *painter, 
const QTransform &transformation);
     /** @brief Draw the x, y, w, h channels of an animated geometry */
     void drawKeyFrameChannels(QRectF br, int in, int out, QPainter *painter, 
QList <QPoint> maximas, int limitKeyframes, QColor textColor);
-    int mouseOverKeyFrames(QRectF br, QPointF pos, double maxOffset, double 
scale);
+    int mouseOverKeyFrames(QRectF br, QPointF pos, double scale);
     void showMenu(QWidget *parent, QPoint pos);
     QAction *parseKeyframeActions(QList <QAction *>actions);
     static QString cutAnimation(const QString &animation, int start, int 
duration, int fullduration, bool doCut = true);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/timeline.cpp 
new/kdenlive-16.04.2/src/timeline/timeline.cpp
--- old/kdenlive-16.04.1/src/timeline/timeline.cpp      2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/timeline.cpp      2016-06-09 
19:50:38.000000000 +0200
@@ -775,10 +775,11 @@
 
 int Timeline::getLowestVideoTrack()
 {
-    for (int i = 1; i < m_tracks.count(); ++i) {
-        if (track(i)->type == VideoTrack) {
+    for (int i = 1; i < m_tractor->count(); ++i) {
+        QScopedPointer<Mlt::Producer> track(m_tractor->track(i));
+        Mlt::Playlist playlist(*track);
+        if (playlist.get_int("kdenlive:audio_track") != 1)
             return i;
-        }
     }
     return -1;
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/timeline.h 
new/kdenlive-16.04.2/src/timeline/timeline.h
--- old/kdenlive-16.04.1/src/timeline/timeline.h        2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/timeline.h        2016-06-09 
19:50:38.000000000 +0200
@@ -149,6 +149,8 @@
     void connectOverlayTrack(bool enable);
     /** @brief Update composite transitions's tracks */
     void updateComposites();
+    /** @brief find lowest video track in timeline. */
+    int getLowestVideoTrack();
 
 protected:
     void keyPressEvent(QKeyEvent * event);
@@ -197,8 +199,6 @@
     void adjustparameterValue(QDomNodeList clipeffectparams, const QString 
&paramname, const QString &paramvalue);
     /** @brief Enable/disable track actions depending on number of tracks */
     void refreshTrackActions();
-    /** @brief find lowest video track in timeline. */
-    int getLowestVideoTrack();
 
 private slots:
     void slotSwitchTrackComposite(int trackIndex, bool enable);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/timeline/transitionhandler.cpp 
new/kdenlive-16.04.2/src/timeline/transitionhandler.cpp
--- old/kdenlive-16.04.1/src/timeline/transitionhandler.cpp     2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/timeline/transitionhandler.cpp     2016-06-09 
19:50:38.000000000 +0200
@@ -518,6 +518,7 @@
     QList <Mlt::Transition *>composites;
     QList <int> disabled;
     QScopedPointer<Mlt::Service> service(m_tractor->field());
+    Mlt::Field *field = m_tractor->field();
     // Get the list of composite transitions
     while (service && service->is_valid()) {
         if (service->type() == transition_type) {
@@ -539,6 +540,11 @@
     for (int i = 0; i < composites.count(); i++) {
         Mlt::Transition *tr = composites.at(i);
         int bTrack = tr->get_int("b_track");
+       if (bTrack == lowestVideoTrack) {
+           // Disable lowest video track transition
+           field->disconnect_service(*tr);
+           continue;
+       }
         if (disabled.contains(bTrack)) {
             // transition disabled, pass
             continue;
@@ -551,5 +557,6 @@
         }
         tr->set("a_track", aTrack);
     }
+    delete field;
     qDeleteAll(composites);
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/titler/titledocument.cpp 
new/kdenlive-16.04.2/src/titler/titledocument.cpp
--- old/kdenlive-16.04.1/src/titler/titledocument.cpp   2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/titler/titledocument.cpp   2016-06-09 
19:50:38.000000000 +0200
@@ -229,7 +229,7 @@
                 cursor.select(QTextCursor::Document);
                 QColor fontcolor = cursor.charFormat().foreground().color();
                 content.setAttribute(QStringLiteral("font-color"), 
colorToString(fontcolor));
-                if (!t->data(TitleDocument::OutlineWidth).isNull()) 
content.setAttribute(QStringLiteral("font-outline"), 
QString::number(t->data(TitleDocument::OutlineWidth).toInt()));
+                if (!t->data(TitleDocument::OutlineWidth).isNull()) 
content.setAttribute(QStringLiteral("font-outline"), 
QString::number(t->data(TitleDocument::OutlineWidth).toDouble()));
                 if (!t->data(TitleDocument::OutlineColor).isNull()) {
                     QVariant variant = t->data(TitleDocument::OutlineColor);
                     QColor outlineColor = variant.value<QColor>();
@@ -382,7 +382,6 @@
 
     int maxZValue = 0;
     if (titles.size()) {
-
         QDomNodeList items = titles.item(0).childNodes();
         for (int i = 0; i < items.count(); ++i) {
             QGraphicsItem *gitem = NULL;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kdenlive-16.04.1/src/titler/titlewidget.cpp 
new/kdenlive-16.04.2/src/titler/titlewidget.cpp
--- old/kdenlive-16.04.1/src/titler/titlewidget.cpp     2016-05-02 
00:32:52.000000000 +0200
+++ new/kdenlive-16.04.2/src/titler/titlewidget.cpp     2016-06-09 
19:50:38.000000000 +0200
@@ -1833,6 +1833,9 @@
     if (!url.isValid()) url = QFileDialog::getOpenFileUrl(this, i18n("Load 
Title"), QUrl(m_projectTitlePath), i18n("Kdenlive title (*.kdenlivetitle)"));
     if (url.isValid()) {
         QList<QGraphicsItem *> items = m_scene->items();
+        items.removeAll(m_frameBorder);
+        items.removeAll(m_frameBackground);
+        items.removeAll(m_frameImage);
         for (int i = 0; i < items.size(); ++i) {
             if (items.at(i)->zValue() > -1000) delete items.at(i);
         }


Reply via email to