From kde-commits Wed Dec 31 21:10:50 2014 From: Jean-Baptiste Mardelle Date: Wed, 31 Dec 2014 21:10:50 +0000 To: kde-commits Subject: [kdenlive/frameworks] src: Basic work on clip properties panel, fix crash on folder double click Message-Id: X-MARC-Message: https://marc.info/?l=kde-commits&m=142006025907678 Git commit dc64f03d4d4006233c903a69dd90e61ad64119d4 by Jean-Baptiste Mardel= le. Committed on 31/12/2014 at 21:10. Pushed by mardelle into branch 'frameworks'. Basic work on clip properties panel, fix crash on folder double click M +80 -49 src/bin/bin.cpp M +7 -2 src/bin/bin.h M +15 -2 src/bin/projectclip.cpp M +1 -1 src/bin/projectclip.h M +1 -1 src/mainwindow.cpp http://commits.kde.org/kdenlive/dc64f03d4d4006233c903a69dd90e61ad64119d4 diff --git a/src/bin/bin.cpp b/src/bin/bin.cpp index 773f122..6fe0560 100644 --- a/src/bin/bin.cpp +++ b/src/bin/bin.cpp @@ -43,7 +43,7 @@ along with this program. If not, see . #include #include #include - +#include = EventEater::EventEater(QObject *parent) : QObject(parent) { @@ -167,10 +167,22 @@ Bin::Bin(QWidget* parent) : m_splitter =3D new QSplitter(this); m_headerInfo =3D QByteArray::fromBase64(KdenliveSettings::treeviewhead= ers().toLatin1()); = - connect(m_eventEater, SIGNAL(editItem(QModelIndex)), this, SLOT(showCl= ipProperties(QModelIndex)), Qt::UniqueConnection); + connect(m_eventEater, SIGNAL(editItem(QModelIndex)), this, SLOT(slotSw= itchClipProperties(QModelIndex)), Qt::UniqueConnection); connect(m_eventEater, SIGNAL(showMenu(QString)), this, SLOT(showClipMe= nu(QString)), Qt::UniqueConnection); = layout->addWidget(m_splitter); + m_propertiesPanel =3D new QWidget(m_splitter); + QVBoxLayout *lay =3D new QVBoxLayout; + m_propertiesPanel->setLayout(lay); + m_propertiesTable =3D new QTableWidget(this); + m_propertiesTable->setColumnCount(2); + QHeaderView *header =3D m_propertiesTable->horizontalHeader(); + header->setStretchLastSection(true); + lay->addWidget(m_propertiesTable); + + m_splitter->addWidget(m_propertiesPanel); + m_collapser =3D new KSplitterCollapserButton(m_propertiesPanel, m_spli= tter); + connect(m_collapser, SIGNAL(clicked(bool)), this, SLOT(slotRefreshClip= Properties())); } = Bin::~Bin() @@ -395,9 +407,18 @@ void Bin::selectProxyModel(const QModelIndex &id) if (id.isValid()) { ProjectClip *currentItem =3D static_cast(m_proxyMode= l->mapToSource(id).internalPointer()); if (currentItem) { - m_openedProducer =3D currentItem->clipId(); - currentItem->setCurrent(true); - m_editAction->setEnabled(true); + if (!currentItem->isFolder()) { + m_openedProducer =3D currentItem->clipId(); + currentItem->setCurrent(true); + m_editAction->setEnabled(true); + if (m_propertiesPanel->width() > 0) { + // if info panel is displayed, update info + if (!currentItem->isFolder()) showClipProperties(curre= ntItem); + } + } else { + // A folder was selected, disable editing clip + m_editAction->setEnabled(false); + } m_deleteAction->setEnabled(true); } else { m_editAction->setEnabled(false); @@ -452,11 +473,11 @@ void Bin::slotInitView(QAction *action) } m_listType =3D static_cast(viewType); } - = + if (m_itemView) { delete m_itemView; } - = + switch (m_listType) { case BinIconView: m_itemView =3D new QListView(m_splitter); @@ -471,6 +492,9 @@ void Bin::slotInitView(QAction *action) m_itemView->setModel(m_proxyModel); m_itemView->setSelectionModel(m_proxyModel->selectionModel()); m_splitter->addWidget(m_itemView); + m_splitter->insertWidget(2, m_propertiesPanel); + m_splitter->setSizes(QList () << 4 << 2); + m_collapser->collapse(); = // setup some default view specific parameters if (m_listType =3D=3D BinTreeView) { @@ -504,7 +528,6 @@ void Bin::slotSetIconSize(int size) QSize zoom =3D m_iconSize; zoom =3D zoom * (size / 4.0); m_itemView->setIconSize(zoom); - m_itemModel->setIconSize(zoom); } = = @@ -520,8 +543,8 @@ void Bin::slotMarkersNeedUpdate(const QString &id, cons= t QList &markers) = void Bin::closeEditing() { - delete m_propertiesPanel; - m_propertiesPanel =3D NULL; + //delete m_propertiesPanel; + //m_propertiesPanel =3D NULL; } = = @@ -548,63 +571,71 @@ void Bin::contextMenuEvent(QContextMenuEvent *event) m_menu->exec(event->globalPos()); } = -void Bin::slotShowClipProperties() + +void Bin::slotRefreshClipProperties() { QModelIndex current =3D m_proxyModel->selectionModel()->currentIndex(); if (current.isValid()) { - ProjectClip *currentItem =3D static_cast(m_proxyMod= el->mapToSource(current).internalPointer()); - showClipProperties(currentItem); + ProjectClip *clip =3D static_cast(m_proxyModel->map= ToSource(current).internalPointer()); + if (clip && !clip->isFolder()) { + showClipProperties(clip); + } } } = -void Bin::showClipProperties(const QModelIndex &ix) +void Bin::slotSwitchClipProperties() { - ProjectClip *clip =3D static_cast(m_proxyModel->mapToSo= urce(ix).internalPointer()); - showClipProperties(clip); + QModelIndex current =3D m_proxyModel->selectionModel()->currentIndex(); + slotSwitchClipProperties(current); +} + +void Bin::slotSwitchClipProperties(const QModelIndex &ix) +{ + if (ix.isValid()) { + if (m_collapser->isWidgetCollapsed()) { + ProjectClip *clip =3D static_cast(m_proxyModel-= >mapToSource(ix).internalPointer()); + if (clip && !clip->isFolder()) { + m_collapser->restore(); + showClipProperties(clip); + } + } + else m_collapser->collapse(); + } + else m_collapser->collapse(); } = void Bin::showClipProperties(ProjectClip *clip) { closeEditing(); - if (!clip) return; - m_propertiesPanel =3D new QWidget(m_splitter); - QVBoxLayout *lay =3D new QVBoxLayout; - m_propertiesPanel->setLayout(lay); + if (!clip || m_propertiesPanel->width() =3D=3D 0) return; + QMap props =3D clip->properties(); + m_propertiesTable->clearContents(); + if (props.isEmpty()) { + // Producer for this clip is not ready yet or no properties in thi= s clip + return; + } // TODO: Build proper clip properties widget //PropertiesView *view =3D new PropertiesView(clip, m_propertiesPanel); - QTableWidget *table =3D new QTableWidget(this); - table->setColumnCount(2); - table->setRowCount(2); - table->horizontalHeader()->hide(); - table->verticalHeader()->hide(); - QTableWidgetItem *key; - QTableWidgetItem *value; - Mlt::Properties *props =3D clip->properties(); - int video_index =3D props->get_int("video_index"); - int audio_index =3D props->get_int("audio_index"); - QString codecKey =3D "meta.media." + QString::number(video_index) + ".= codec.long_name"; - QString codec =3D props->get(codecKey.toUtf8().constData()); - key =3D new QTableWidgetItem(i18n("Video codec")); - table->setItem(0, 0, key); - value =3D new QTableWidgetItem(codec); - table->setItem(0, 1, value); - = - codecKey =3D "meta.media." + QString::number(audio_index) + ".codec.lo= ng_name"; - codec =3D props->get(codecKey.toUtf8().constData()); - key =3D new QTableWidgetItem(i18n("Audio codec")); - table->setItem(1, 0, key); - value =3D new QTableWidgetItem(codec); - table->setItem(1, 1, value); - = + + m_propertiesTable->setRowCount(props.size()); + m_propertiesTable->horizontalHeader()->hide(); + m_propertiesTable->verticalHeader()->hide(); + QTableWidgetItem *keyitem; + QTableWidgetItem *valueitem; + QMapIterator i(props); + int ix =3D 0; + while (i.hasNext()) { + i.next(); + keyitem =3D new QTableWidgetItem(i.key()); + m_propertiesTable->setItem(ix, 0, keyitem); + valueitem =3D new QTableWidgetItem(i.value()); + m_propertiesTable->setItem(ix, 1, valueitem); + ix++; + } //m_editedProducer=3D new Producer(producer, desc, pCore->clipPluginMa= nager()); //connect(m_editedProducer, SIGNAL(updateClip()), this, SLOT(refreshEd= itedClip())); //connect(m_editedProducer, SIGNAL(reloadClip(QString)), this, SLOT(re= loadClip(QString))); //connect(m_editedProducer, SIGNAL(editingDone()), this, SLOT(closeEdi= ting())); - = - lay->addWidget(table); - m_splitter->addWidget(m_propertiesPanel); - m_splitter->setStretchFactor(m_splitter->indexOf(m_itemView), 1); - m_splitter->setStretchFactor(m_splitter->indexOf(m_propertiesPanel), 2= 0); } = void Bin::reloadClip(const QString &id) diff --git a/src/bin/bin.h b/src/bin/bin.h index 13a4e42..9317e9e 100644 --- a/src/bin/bin.h +++ b/src/bin/bin.h @@ -35,6 +35,7 @@ along with this program. If not, see . class KdenliveDoc; class QSplitter; class KToolBar; +class KSplitterCollapserButton; class QMenu; class ProjectItemModel; class ProjectClip; @@ -44,6 +45,7 @@ class Monitor; class QItemSelectionModel; class ProjectSortProxyModel; class JobManager; +class QTableWidget; = namespace Mlt { class Producer; @@ -302,7 +304,6 @@ private slots: void slotSaveHeaders(); = public slots: - void showClipProperties(const QModelIndex &ix); void slotThumbnailReady(const QString &id, const QImage &img); /** @brief The producer for this clip is ready. * @param id the clip id @@ -311,7 +312,9 @@ public slots: */ void slotProducerReady(requestClipInfo info, Mlt::Producer *producer); void slotDeleteClip(); - void slotShowClipProperties(); + void slotRefreshClipProperties(); + void slotSwitchClipProperties(const QModelIndex &ix); + void slotSwitchClipProperties(); void slotAddFolder(); = protected: @@ -339,6 +342,8 @@ private: QByteArray m_headerInfo; EventEater *m_eventEater; QWidget *m_propertiesPanel; + QTableWidget *m_propertiesTable; + KSplitterCollapserButton *m_collapser; Monitor *m_monitor; QMenu *m_menu; QAction *m_openAction; diff --git a/src/bin/projectclip.cpp b/src/bin/projectclip.cpp index de32a5b..348a090 100644 --- a/src/bin/projectclip.cpp +++ b/src/bin/projectclip.cpp @@ -243,9 +243,22 @@ bool ProjectClip::hasProducer() const return m_producer!=3D NULL; } = -Mlt::Properties *ProjectClip::properties() +QMap ProjectClip::properties() { - return new Mlt::Properties(m_producer->get_properties()); + //TODO: move into its own class that creates its own widget (reuse cli= pproperties) + QMap result; + if (m_producer) { + mlt_properties props =3D m_producer->get_properties(); + QString key =3D "video_index"; + int video_index =3D mlt_properties_get_int(props, key.toUtf8().con= stData()); + QString codecKey =3D "meta.media." + QString::number(video_index) = + ".codec.long_name"; + result.insert(i18n("Video codec"), mlt_properties_get(props, codec= Key.toUtf8().constData())); + key =3D "audio_index"; + int audio_index =3D mlt_properties_get_int(props, key.toUtf8().con= stData()); + codecKey =3D "meta.media." + QString::number(audio_index) + ".code= c.long_name"; + result.insert(i18n("Audio codec"), mlt_properties_get(props, codec= Key.toUtf8().constData())); + } + return result; } = void ProjectClip::setZone(const QPoint &zone) diff --git a/src/bin/projectclip.h b/src/bin/projectclip.h index 7a4582f..0b276a1 100644 --- a/src/bin/projectclip.h +++ b/src/bin/projectclip.h @@ -130,7 +130,7 @@ public: Mlt::Producer *producer(); = //TODO - Mlt::Properties *properties(); + QMap properties(); = /** @brief Set properties on this clip. TODO: should we store all in M= LT or use extra m_properties ?. */ void setProperties(QMap properties); diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp index a77a64c..3a84445 100644 --- a/src/mainwindow.cpp +++ b/src/mainwindow.cpp @@ -1133,7 +1133,7 @@ void MainWindow::setupActions() addClips->addAction(addAction("download_resource", i18n("Online Resour= ces"), this, SLOT(slotDownloadResources()), QIcon::fromTheme("download"))); = - QAction *clipProperties =3D addAction("clip_properties", i18n("Clip Pr= operties"), pCore->bin(), SLOT(slotShowClipProperties()), QIcon::fromTheme(= "document-edit")); + QAction *clipProperties =3D addAction("clip_properties", i18n("Clip Pr= operties"), pCore->bin(), SLOT(slotSwitchClipProperties()), QIcon::fromThem= e("document-edit")); clipProperties->setData("clip_properties"); clipProperties->setEnabled(false); =20