X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=src%2Fclipproperties.cpp;h=d1d610aa0a8dd24526b9a066a8eba94accacb30a;hb=bf1017234649f13060c2eea16488b58c8cdec8a7;hp=bae098d17c7ea6c65a75488e67cc5d554e211202;hpb=785e31f4676966fa5dcb8961054d326538a6c762;p=kdenlive diff --git a/src/clipproperties.cpp b/src/clipproperties.cpp index bae098d1..d1d610aa 100644 --- a/src/clipproperties.cpp +++ b/src/clipproperties.cpp @@ -27,6 +27,19 @@ #include #include #include +#include +#include +#include + +#ifdef USE_NEPOMUK +#if KDE_IS_VERSION(4,6,0) +#include +#include +#include +#include +#endif +#endif + #include @@ -39,6 +52,7 @@ static const int MARKERTAB = 5; static const int METATAB = 6; static const int ADVANCEDTAB = 7; + ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidget * parent) : QDialog(parent), m_clip(clip), @@ -48,51 +62,107 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_clipNeedsRefresh(false), m_clipNeedsReLoad(false) { + setAttribute(Qt::WA_DeleteOnClose, true); setFont(KGlobalSettings::toolBarFont()); m_view.setupUi(this); + + // force transparency is only for group properties, so hide it + m_view.clip_force_transparency->setHidden(true); + m_view.clip_transparency->setHidden(true); + KUrl url = m_clip->fileURL(); m_view.clip_path->setText(url.path()); m_view.clip_description->setText(m_clip->description()); - QMap props = m_clip->properties(); + connect(m_view.clip_description, SIGNAL(textChanged(QString)), this, SLOT(slotModified())); + QMap props = m_clip->properties(); m_view.clip_force_out->setHidden(true); m_view.clip_out->setHidden(true); - - if (props.contains("force_aspect_ratio") && props.value("force_aspect_ratio").toDouble() > 0) { + + // New display aspect ratio support + if (props.contains("force_aspect_num") && props.value("force_aspect_num").toInt() > 0 && + props.contains("force_aspect_den") && props.value("force_aspect_den").toInt() > 0) { m_view.clip_force_ar->setChecked(true); - m_view.clip_ar->setEnabled(true); - m_view.clip_ar->setValue(props.value("force_aspect_ratio").toDouble()); + m_view.clip_ar_num->setEnabled(true); + m_view.clip_ar_den->setEnabled(true); + m_view.clip_ar_num->setValue(props.value("force_aspect_num").toInt()); + m_view.clip_ar_den->setValue(props.value("force_aspect_den").toInt()); } + // Legacy support for pixel aspect ratio + else if (props.contains("force_aspect_ratio") && props.value("force_aspect_ratio").toDouble() > 0) { + m_view.clip_force_ar->setChecked(true); + m_view.clip_ar_num->setEnabled(true); + m_view.clip_ar_den->setEnabled(true); + if (props.contains("frame_size")) { + int width = props.value("force_aspect_ratio").toDouble() * props.value("frame_size").section('x', 0, 0).toInt(); + int height = props.value("frame_size").section('x', 1, 1).toInt(); + if (width > 0 && height > 0) { + if ((width / height * 100) == 133) { + width = 4; + height = 3; + } + else if (int(width / height * 100) == 177) { + width = 16; + height = 9; + } + m_view.clip_ar_num->setValue(width); + m_view.clip_ar_den->setValue(height); + } + } + } + connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_ar_num, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); + connect(m_view.clip_ar_den, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); if (props.contains("force_fps") && props.value("force_fps").toDouble() > 0) { m_view.clip_force_framerate->setChecked(true); m_view.clip_framerate->setEnabled(true); m_view.clip_framerate->setValue(props.value("force_fps").toDouble()); } + connect(m_view.clip_force_framerate, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_framerate, SIGNAL(valueChanged(double)), this, SLOT(slotModified())); if (props.contains("force_progressive")) { m_view.clip_force_progressive->setChecked(true); m_view.clip_progressive->setEnabled(true); m_view.clip_progressive->setValue(props.value("force_progressive").toInt()); } - + connect(m_view.clip_force_progressive, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_progressive, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); + + m_view.clip_fieldorder->addItem(i18n("Bottom first"), 0); + m_view.clip_fieldorder->addItem(i18n("Top first"), 1); + if (props.contains("force_tff")) { + m_view.clip_force_fieldorder->setChecked(true); + m_view.clip_fieldorder->setEnabled(true); + m_view.clip_fieldorder->setCurrentIndex(props.value("force_tff").toInt()); + } + connect(m_view.clip_force_fieldorder, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_fieldorder, SIGNAL(currentIndexChanged(int)), this, SLOT(slotModified())); + if (props.contains("threads") && props.value("threads").toInt() != 1) { m_view.clip_force_threads->setChecked(true); m_view.clip_threads->setEnabled(true); m_view.clip_threads->setValue(props.value("threads").toInt()); } + connect(m_view.clip_force_threads, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_threads, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); if (props.contains("video_index") && props.value("video_index").toInt() != 0) { m_view.clip_force_vindex->setChecked(true); m_view.clip_vindex->setEnabled(true); m_view.clip_vindex->setValue(props.value("video_index").toInt()); } + connect(m_view.clip_force_vindex, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_vindex, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); if (props.contains("audio_index") && props.value("audio_index").toInt() != 0) { m_view.clip_force_aindex->setChecked(true); m_view.clip_aindex->setEnabled(true); m_view.clip_aindex->setValue(props.value("audio_index").toInt()); } + connect(m_view.clip_force_aindex, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_aindex, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); if (props.contains("audio_max")) { m_view.clip_aindex->setMaximum(props.value("audio_max").toInt()); @@ -101,6 +171,24 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg if (props.contains("video_max")) { m_view.clip_vindex->setMaximum(props.value("video_max").toInt()); } + + m_view.clip_colorspace->addItem(ProfilesDialog::getColorspaceDescription(601), 601); + m_view.clip_colorspace->addItem(ProfilesDialog::getColorspaceDescription(709), 709); + m_view.clip_colorspace->addItem(ProfilesDialog::getColorspaceDescription(240), 240); + if (props.contains("force_colorspace")) { + m_view.clip_force_colorspace->setChecked(true); + m_view.clip_colorspace->setEnabled(true); + m_view.clip_colorspace->setCurrentIndex(m_view.clip_colorspace->findData(props.value("force_colorspace").toInt())); + } else if (props.contains("colorspace")) { + m_view.clip_colorspace->setCurrentIndex(m_view.clip_colorspace->findData(props.value("colorspace").toInt())); + } + connect(m_view.clip_force_colorspace, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.clip_colorspace, SIGNAL(currentIndexChanged(int)), this, SLOT(slotModified())); + + if (props.contains("full_luma")) { + m_view.clip_full_luma->setChecked(true); + } + connect(m_view.clip_full_luma, SIGNAL(toggled(bool)), this, SLOT(slotModified())); // Check for Metadata QMap meta = m_clip->metadata(); @@ -112,21 +200,56 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg ++i; } - connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), m_view.clip_ar, SLOT(setEnabled(bool))); + connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), m_view.clip_ar_num, SLOT(setEnabled(bool))); + connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), m_view.clip_ar_den, SLOT(setEnabled(bool))); connect(m_view.clip_force_framerate, SIGNAL(toggled(bool)), m_view.clip_framerate, SLOT(setEnabled(bool))); connect(m_view.clip_force_progressive, SIGNAL(toggled(bool)), m_view.clip_progressive, SLOT(setEnabled(bool))); + connect(m_view.clip_force_fieldorder, SIGNAL(toggled(bool)), m_view.clip_fieldorder, SLOT(setEnabled(bool))); connect(m_view.clip_force_threads, SIGNAL(toggled(bool)), m_view.clip_threads, SLOT(setEnabled(bool))); connect(m_view.clip_force_vindex, SIGNAL(toggled(bool)), m_view.clip_vindex, SLOT(setEnabled(bool))); connect(m_view.clip_force_aindex, SIGNAL(toggled(bool)), m_view.clip_aindex, SLOT(setEnabled(bool))); + connect(m_view.clip_force_colorspace, SIGNAL(toggled(bool)), m_view.clip_colorspace, SLOT(setEnabled(bool))); if (props.contains("audiocodec")) - m_view.clip_acodec->setText(props.value("audiocodec")); - if (props.contains("frequency")) - m_view.clip_frequency->setText(props.value("frequency")); + new QTreeWidgetItem(m_view.clip_aproperties, QStringList() << i18n("Audio codec") << props.value("audiocodec")); + if (props.contains("channels")) - m_view.clip_channels->setText(props.value("channels")); + new QTreeWidgetItem(m_view.clip_aproperties, QStringList() << i18n("Channels") << props.value("channels")); + + if (props.contains("frequency")) + new QTreeWidgetItem(m_view.clip_aproperties, QStringList() << i18n("Frequency") << props.value("frequency")); + CLIPTYPE t = m_clip->clipType(); + + if (props.contains("proxy") && props.value("proxy") != "-") { + KFileItem f(KFileItem::Unknown, KFileItem::Unknown, KUrl(props.value("proxy")), true); + QFrame* line = new QFrame(); + line->setFrameShape(QFrame::HLine); + line->setFrameShadow(QFrame::Sunken); + m_proxyContainer = new QFrame(); + m_proxyContainer->setFrameShape(QFrame::NoFrame); + QHBoxLayout *l = new QHBoxLayout; + l->addWidget(new QLabel(i18n("Proxy clip: %1", KIO::convertSize(f.size())))); + l->addStretch(5); + QPushButton *pb = new QPushButton(i18n("Delete proxy")); + l->addWidget(pb); + connect(pb, SIGNAL(clicked()), this, SLOT(slotDeleteProxy())); + m_proxyContainer->setLayout(l); + if (t == IMAGE) { + m_view.tab_image->layout()->addWidget(line); + m_view.tab_image->layout()->addWidget(m_proxyContainer); + } + else if (t == AUDIO) { + m_view.tab_audio->layout()->addWidget(line); + m_view.tab_audio->layout()->addWidget(m_proxyContainer); + } + else { + m_view.tab_video->layout()->addWidget(line); + m_view.tab_video->layout()->addWidget(m_proxyContainer); + } + } + if (t != AUDIO && t != AV) { m_view.clip_force_aindex->setEnabled(false); } @@ -144,6 +267,7 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_view.image_size->setText(props.value("frame_size")); if (props.contains("transparency")) m_view.image_transparency->setChecked(props.value("transparency").toInt()); + connect(m_view.image_transparency, SIGNAL(toggled(bool)), this, SLOT(slotModified())); int width = 180.0 * KdenliveSettings::project_display_ratio(); if (width % 2 == 1) width++; m_view.clip_thumb->setPixmap(QPixmap(url.path()).scaled(QSize(width, 180), Qt::KeepAspectRatio)); @@ -156,8 +280,8 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_view.tabWidget->removeTab(VIDEOTAB); m_view.clip_thumb->setHidden(true); m_view.clip_color->setColor(QColor('#' + props.value("colour").right(8).left(6))); + connect(m_view.clip_color, SIGNAL(changed(QColor)), this, SLOT(slotModified())); } else if (t == SLIDESHOW) { - bool isMime = true; if (url.fileName().startsWith(".all.")) { // the image sequence is defined by mimetype m_view.clip_path->setText(url.directory()); @@ -166,7 +290,6 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_view.slide_type_label->setHidden(true); m_view.image_type->setHidden(true); m_view.clip_path->setText(url.path()); - isMime = false; } m_view.tabWidget->removeTab(METATAB); @@ -182,6 +305,7 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_view.image_type->addItem("BMP (*.bmp)", "bmp"); m_view.image_type->addItem("GIF (*.gif)", "gif"); m_view.image_type->addItem("TGA (*.tga)", "tga"); + m_view.image_type->addItem("TIF (*.tif)", "tif"); m_view.image_type->addItem("TIFF (*.tiff)", "tiff"); m_view.image_type->addItem("Open EXR (*.exr)", "exr"); m_view.animation->addItem(i18n("None"), QString()); @@ -210,7 +334,7 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg } m_view.slide_duration->setText(tc.getTimecodeFromFrames(props.value("ttl").toInt())); - m_view.slide_duration_format->addItem(i18n("hh:mm:ss::ff")); + m_view.slide_duration_format->addItem(i18n("hh:mm:ss:ff")); m_view.slide_duration_format->addItem(i18n("Frames")); connect(m_view.slide_duration_format, SIGNAL(activated(int)), this, SLOT(slotUpdateDurationFormat(int))); m_view.slide_duration_frames->setHidden(true); @@ -251,31 +375,62 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg } else m_view.luma_file->setEnabled(false); slotEnableLuma(m_view.slide_fade->checkState()); slotEnableLumaFile(m_view.slide_luma->checkState()); + + connect(m_view.slide_fade, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.slide_luma, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.slide_loop, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.slide_crop, SIGNAL(toggled(bool)), this, SLOT(slotModified())); + connect(m_view.slide_duration, SIGNAL(textChanged(QString)), this, SLOT(slotModified())); + connect(m_view.slide_duration_frames, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); + connect(m_view.luma_duration, SIGNAL(textChanged(QString)), this, SLOT(slotModified())); + connect(m_view.luma_softness, SIGNAL(valueChanged(int)), this, SLOT(slotModified())); + connect(m_view.luma_file, SIGNAL(currentIndexChanged(int)), this, SLOT(slotModified())); + connect(m_view.animation, SIGNAL(currentIndexChanged(int)), this, SLOT(slotModified())); + + connect(m_view.slide_fade, SIGNAL(stateChanged(int)), this, SLOT(slotEnableLuma(int))); connect(m_view.slide_luma, SIGNAL(stateChanged(int)), this, SLOT(slotEnableLumaFile(int))); - connect(m_view.image_type, SIGNAL(currentIndexChanged(int)), this, SLOT(parseFolder())); + } else if (t != AUDIO) { m_view.tabWidget->removeTab(IMAGETAB); m_view.tabWidget->removeTab(SLIDETAB); m_view.tabWidget->removeTab(COLORTAB); - if (props.contains("frame_size")) - m_view.clip_size->setText(props.value("frame_size")); + + PropertiesViewDelegate *del1 = new PropertiesViewDelegate(this); + PropertiesViewDelegate *del2 = new PropertiesViewDelegate(this); + m_view.clip_vproperties->setItemDelegate(del1); + m_view.clip_aproperties->setItemDelegate(del2); + m_view.clip_aproperties->setStyleSheet(QString("QTreeWidget { background-color: transparent;}")); + m_view.clip_vproperties->setStyleSheet(QString("QTreeWidget { background-color: transparent;}")); + if (props.contains("videocodec")) - m_view.clip_vcodec->setText(props.value("videocodec")); + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Video codec") << props.value("videocodec")); + + if (props.contains("frame_size")) + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Frame size") << props.value("frame_size")); + if (props.contains("fps")) { - m_view.clip_fps->setText(props.value("fps")); + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Frame rate") << props.value("fps")); if (!m_view.clip_framerate->isEnabled()) m_view.clip_framerate->setValue(props.value("fps").toDouble()); } - if (props.contains("pix_fmt")) { - m_view.clip_pixfmt->setText(props.value("pix_fmt")); - } else m_view.clip_pixfmt->setEnabled(false); - if (props.contains("colorspace")) { - m_view.clip_colorspace->setText(ProfilesDialog::getColorspaceDescription(props.value("colorspace").toInt())); - } else m_view.clip_colorspace->setEnabled(false); + if (props.contains("progressive")) { + int scanning = props.value("progressive").toInt(); + QString txt = scanning == 1 ? i18n("Progressive") : i18n("Interlaced"); + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Scanning") << txt); + } + if (props.contains("aspect_ratio")) - m_view.clip_ratio->setText(props.value("aspect_ratio")); + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Pixel aspect ratio") << props.value("aspect_ratio")); + + if (props.contains("pix_fmt")) + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Pixel format") << props.value("pix_fmt")); + + if (props.contains("colorspace")) + new QTreeWidgetItem(m_view.clip_vproperties, QStringList() << i18n("Colorspace") << ProfilesDialog::getColorspaceDescription(props.value("colorspace").toInt())); + + int width = 180.0 * KdenliveSettings::project_display_ratio(); if (width % 2 == 1) width++; QPixmap pix = m_clip->thumbProducer()->getImage(url, m_clip->getClipThumbFrame(), width, 180); @@ -296,11 +451,13 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_view.clip_filesize->setHidden(true); m_view.label_size->setHidden(true); } - m_view.clip_duration->setInputMask(""); - m_view.clip_duration->setValidator(tc.validator()); + m_view.clip_duration->setInputMask(tc.mask()); m_view.clip_duration->setText(tc.getTimecode(m_clip->duration())); if (t != IMAGE && t != COLOR && t != TEXT) m_view.clip_duration->setReadOnly(true); - else connect(m_view.clip_duration, SIGNAL(editingFinished()), this, SLOT(slotCheckMaxLength())); + else { + connect(m_view.clip_duration, SIGNAL(editingFinished()), this, SLOT(slotCheckMaxLength())); + connect(m_view.clip_duration, SIGNAL(textChanged(QString)), this, SLOT(slotModified())); + } // markers m_view.marker_new->setIcon(KIcon("document-new")); @@ -310,13 +467,41 @@ ClipProperties::ClipProperties(DocClipBase *clip, Timecode tc, double fps, QWidg m_view.marker_delete->setIcon(KIcon("trash-empty")); m_view.marker_delete->setToolTip(i18n("Delete marker")); + // Check for Nepomuk metadata +#ifdef USE_NEPOMUK +#if KDE_IS_VERSION(4,6,0) + if (!url.isEmpty()) { + Nepomuk::ResourceManager::instance()->init(); + Nepomuk::Resource res( url.path() ); + // Check if file has a license + if (res.hasProperty(Nepomuk::Vocabulary::NIE::license())) { + QString ltype = res.property(Nepomuk::Vocabulary::NIE::licenseType()).toString(); + m_view.clip_license->setText(i18n("License: %1", res.property(Nepomuk::Vocabulary::NIE::license()).toString())); + if (ltype.startsWith("http")) { + m_view.clip_license->setUrl(ltype); + connect(m_view.clip_license, SIGNAL(leftClickedUrl(const QString &)), this, SLOT(slotOpenUrl(const QString &))); + } + } + else m_view.clip_license->setHidden(true); + } + else m_view.clip_license->setHidden(true); +#else + m_view.clip_license->setHidden(true); +#endif +#else + m_view.clip_license->setHidden(true); +#endif + slotFillMarkersList(); connect(m_view.marker_new, SIGNAL(clicked()), this, SLOT(slotAddMarker())); connect(m_view.marker_edit, SIGNAL(clicked()), this, SLOT(slotEditMarker())); connect(m_view.marker_delete, SIGNAL(clicked()), this, SLOT(slotDeleteMarker())); connect(m_view.markers_list, SIGNAL(doubleClicked(const QModelIndex &)), this, SLOT(slotEditMarker())); - //adjustSize(); + connect(this, SIGNAL(accepted()), this, SLOT(slotApplyProperties())); + connect(m_view.buttonBox->button(QDialogButtonBox::Apply), SIGNAL(clicked()), this, SLOT(slotApplyProperties())); + m_view.buttonBox->button(QDialogButtonBox::Apply)->setEnabled(false); + adjustSize(); } @@ -332,13 +517,18 @@ ClipProperties::ClipProperties(QList cliplist, Timecode tc, QMap { setFont(KGlobalSettings::toolBarFont()); m_view.setupUi(this); + QString title = windowTitle(); + title.append(" " + i18np("(%1 clip)", "(%1 clips)", cliplist.count())); + setWindowTitle(title); QMap props = cliplist.at(0)->properties(); m_old_props = commonproperties; - if (commonproperties.contains("force_aspect_ratio") && !commonproperties.value("force_aspect_ratio").isEmpty() && commonproperties.value("force_aspect_ratio").toDouble() > 0) { + if (commonproperties.contains("force_aspect_num") && !commonproperties.value("force_aspect_num").isEmpty() && commonproperties.value("force_aspect_den").toInt() > 0) { m_view.clip_force_ar->setChecked(true); - m_view.clip_ar->setEnabled(true); - m_view.clip_ar->setValue(commonproperties.value("force_aspect_ratio").toDouble()); + m_view.clip_ar_num->setEnabled(true); + m_view.clip_ar_den->setEnabled(true); + m_view.clip_ar_num->setValue(commonproperties.value("force_aspect_num").toInt()); + m_view.clip_ar_den->setValue(commonproperties.value("force_aspect_den").toInt()); } if (commonproperties.contains("force_fps") && !commonproperties.value("force_fps").isEmpty() && commonproperties.value("force_fps").toDouble() > 0) { @@ -353,6 +543,12 @@ ClipProperties::ClipProperties(QList cliplist, Timecode tc, QMap m_view.clip_progressive->setValue(commonproperties.value("force_progressive").toInt()); } + if (commonproperties.contains("force_tff") && !commonproperties.value("force_tff").isEmpty()) { + m_view.clip_force_fieldorder->setChecked(true); + m_view.clip_fieldorder->setEnabled(true); + m_view.clip_fieldorder->setCurrentIndex(commonproperties.value("force_tff").toInt()); + } + if (commonproperties.contains("threads") && !commonproperties.value("threads").isEmpty() && commonproperties.value("threads").toInt() != 1) { m_view.clip_force_threads->setChecked(true); m_view.clip_threads->setEnabled(true); @@ -378,13 +574,47 @@ ClipProperties::ClipProperties(QList cliplist, Timecode tc, QMap if (props.contains("video_max")) { m_view.clip_vindex->setMaximum(props.value("video_max").toInt()); } + + m_view.clip_colorspace->addItem(ProfilesDialog::getColorspaceDescription(601), 601); + m_view.clip_colorspace->addItem(ProfilesDialog::getColorspaceDescription(709), 709); + m_view.clip_colorspace->addItem(ProfilesDialog::getColorspaceDescription(240), 240); + + if (commonproperties.contains("force_colorspace") && !commonproperties.value("force_colorspace").isEmpty() && commonproperties.value("force_colorspace").toInt() != 0) { + m_view.clip_force_colorspace->setChecked(true); + m_view.clip_colorspace->setEnabled(true); + m_view.clip_colorspace->setCurrentIndex(m_view.clip_colorspace->findData(commonproperties.value("force_colorspace").toInt())); + } + + if (commonproperties.contains("full_luma") && !commonproperties.value("full_luma").isEmpty()) { + m_view.clip_full_luma->setChecked(true); + } + + if (commonproperties.contains("transparency")) { + // image transparency checkbox + int transparency = commonproperties.value("transparency").toInt(); + if (transparency == 0) { + m_view.clip_force_transparency->setChecked(true); + } + else if (transparency == 1) { + m_view.clip_force_transparency->setChecked(true); + m_view.clip_transparency->setCurrentIndex(1); + } + } + else { + m_view.clip_force_transparency->setHidden(true); + m_view.clip_transparency->setHidden(true); + } + - connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), m_view.clip_ar, SLOT(setEnabled(bool))); + connect(m_view.clip_force_transparency, SIGNAL(toggled(bool)), m_view.clip_transparency, SLOT(setEnabled(bool))); + connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), m_view.clip_ar_num, SLOT(setEnabled(bool))); + connect(m_view.clip_force_ar, SIGNAL(toggled(bool)), m_view.clip_ar_den, SLOT(setEnabled(bool))); connect(m_view.clip_force_progressive, SIGNAL(toggled(bool)), m_view.clip_progressive, SLOT(setEnabled(bool))); connect(m_view.clip_force_threads, SIGNAL(toggled(bool)), m_view.clip_threads, SLOT(setEnabled(bool))); connect(m_view.clip_force_vindex, SIGNAL(toggled(bool)), m_view.clip_vindex, SLOT(setEnabled(bool))); connect(m_view.clip_force_aindex, SIGNAL(toggled(bool)), m_view.clip_aindex, SLOT(setEnabled(bool))); connect(m_view.clip_force_out, SIGNAL(toggled(bool)), m_view.clip_out, SLOT(setEnabled(bool))); + connect(m_view.clip_force_colorspace, SIGNAL(toggled(bool)), m_view.clip_colorspace, SLOT(setEnabled(bool))); m_view.tabWidget->removeTab(METATAB); m_view.tabWidget->removeTab(MARKERTAB); @@ -417,6 +647,37 @@ ClipProperties::ClipProperties(QList cliplist, Timecode tc, QMap } } +ClipProperties::~ClipProperties() +{ + QAbstractItemDelegate *del1 = m_view.clip_vproperties->itemDelegate(); + if (del1) delete del1; + QAbstractItemDelegate *del2 = m_view.clip_aproperties->itemDelegate(); + if (del2) delete del2; +} + +void ClipProperties::slotApplyProperties() +{ + if (m_clip != NULL) { + QMap props = properties(); + emit applyNewClipProperties(m_clip->getId(), m_clip->currentProperties(props), props, needsTimelineRefresh(), needsTimelineReload()); + } + m_view.buttonBox->button(QDialogButtonBox::Apply)->setEnabled(false); +} + +void ClipProperties::disableClipId(const QString &id) +{ + if (m_clip && m_view.buttonBox->button(QDialogButtonBox::Ok)->isEnabled()) { + if (m_clip->getId() == id) { + // clip was removed from project, close this properties dialog + close(); + } + } +} + +void ClipProperties::slotModified() +{ + m_view.buttonBox->button(QDialogButtonBox::Apply)->setEnabled(true); +} void ClipProperties::slotEnableLuma(int state) @@ -495,30 +756,41 @@ const QString &ClipProperties::clipId() const QMap ClipProperties::properties() { QMap props; + QLocale locale; CLIPTYPE t = UNKNOWN; if (m_clip != NULL) { t = m_clip->clipType(); m_old_props = m_clip->properties(); } - double aspect = m_view.clip_ar->value(); + int aspectNumerator = m_view.clip_ar_num->value(); + int aspectDenominator = m_view.clip_ar_den->value(); if (m_view.clip_force_ar->isChecked()) { - if (aspect != m_old_props.value("force_aspect_ratio").toDouble()) { - props["force_aspect_ratio"] = QString::number(aspect); + if (aspectNumerator != m_old_props.value("force_aspect_num").toInt() || + aspectDenominator != m_old_props.value("force_aspect_den").toInt()) { + props["force_aspect_num"] = QString::number(aspectNumerator); + props["force_aspect_den"] = QString::number(aspectDenominator); + props["force_aspect_ratio"].clear(); + m_clipNeedsRefresh = true; + } + } else { + if (m_old_props.contains("force_aspect_num") && !m_old_props.value("force_aspect_num").isEmpty()) { + props["force_aspect_num"].clear(); + m_clipNeedsRefresh = true; + } + if (m_old_props.contains("force_aspect_den") && !m_old_props.value("force_aspect_den").isEmpty()) { + props["force_aspect_den"].clear(); m_clipNeedsRefresh = true; } - } else if (m_old_props.contains("force_aspect_ratio")) { - props["force_aspect_ratio"].clear(); - m_clipNeedsRefresh = true; } double fps = m_view.clip_framerate->value(); if (m_view.clip_force_framerate->isChecked()) { if (fps != m_old_props.value("force_fps").toDouble()) { - props["force_fps"] = QString::number(fps); + props["force_fps"] = locale.toString(fps); m_clipNeedsRefresh = true; } - } else if (m_old_props.contains("force_fps")) { + } else if (m_old_props.contains("force_fps") && !m_old_props.value("force_fps").isEmpty()) { props["force_fps"].clear(); m_clipNeedsRefresh = true; } @@ -528,16 +800,25 @@ QMap ClipProperties::properties() if (progressive != m_old_props.value("force_progressive").toInt()) { props["force_progressive"] = QString::number(progressive); } - } else if (m_old_props.contains("force_progressive")) { + } else if (m_old_props.contains("force_progressive") && !m_old_props.value("force_progressive").isEmpty()) { props["force_progressive"].clear(); } + int fieldOrder = m_view.clip_fieldorder->currentIndex(); + if (m_view.clip_force_fieldorder->isChecked()) { + if (fieldOrder != m_old_props.value("force_tff").toInt()) { + props["force_tff"] = QString::number(fieldOrder); + } + } else if (m_old_props.contains("force_tff") && !m_old_props.value("force_tff").isEmpty()) { + props["force_tff"].clear(); + } + int threads = m_view.clip_threads->value(); if (m_view.clip_force_threads->isChecked()) { if (threads != m_old_props.value("threads").toInt()) { props["threads"] = QString::number(threads); } - } else if (m_old_props.contains("threads")) { + } else if (m_old_props.contains("threads") && !m_old_props.value("threads").isEmpty()) { props["threads"].clear(); } @@ -546,7 +827,7 @@ QMap ClipProperties::properties() if (vindex != m_old_props.value("video_index").toInt()) { props["video_index"] = QString::number(vindex); } - } else if (m_old_props.contains("video_index")) { + } else if (m_old_props.contains("video_index") && !m_old_props.value("video_index").isEmpty()) { props["video_index"].clear(); } @@ -555,9 +836,33 @@ QMap ClipProperties::properties() if (aindex != m_old_props.value("audio_index").toInt()) { props["audio_index"] = QString::number(aindex); } - } else if (m_old_props.contains("audio_index")) { + } else if (m_old_props.contains("audio_index") && !m_old_props.value("audio_index").isEmpty()) { props["audio_index"].clear(); } + + int colorspace = m_view.clip_colorspace->itemData(m_view.clip_colorspace->currentIndex()).toInt(); + if (m_view.clip_force_colorspace->isChecked()) { + if (colorspace != m_old_props.value("force_colorspace").toInt()) { + props["force_colorspace"] = QString::number(colorspace); + m_clipNeedsRefresh = true; + } + } else if (m_old_props.contains("force_colorspace") && !m_old_props.value("force_colorspace").isEmpty()) { + props["force_colorspace"].clear(); + m_clipNeedsRefresh = true; + } + + if (m_view.clip_full_luma->isChecked()) { + props["full_luma"] = QString::number(1); + m_clipNeedsRefresh = true; + } else if (m_old_props.contains("full_luma") && !m_old_props.value("full_luma").isEmpty()) { + props["full_luma"].clear(); + m_clipNeedsRefresh = true; + } + + if (m_view.clip_force_transparency->isChecked()) { + QString transp = QString::number(m_view.clip_transparency->currentIndex()); + if (transp != m_old_props.value("transparency")) props["transparency"] = transp; + } // If we adjust several clips, return now if (m_clip == NULL) { @@ -620,7 +925,7 @@ QMap ClipProperties::properties() if (duration != m_old_props.value("ttl").toInt()) { m_clipNeedsRefresh = true; props["ttl"] = QString::number(duration); - props["out"] = QString::number(duration * m_count - 1); + props["length"] = QString::number(duration * m_count); } if (duration * m_count - 1 != m_old_props.value("out").toInt()) { @@ -708,6 +1013,7 @@ void ClipProperties::parseFolder() } m_count = result.count(); + m_view.buttonBox->button(QDialogButtonBox::Apply)->setEnabled(m_count > 0); if (m_count == 0) { // no images, do not accept that m_view.slide_info->setText(i18n("No image found")); @@ -759,6 +1065,20 @@ void ClipProperties::slotUpdateDurationFormat(int ix) } } +void ClipProperties::slotDeleteProxy() +{ + QString proxy = m_clip->getProperty("proxy"); + if (proxy.isEmpty()) return; + emit deleteProxy(proxy); + if (m_proxyContainer) delete m_proxyContainer; +} + +void ClipProperties::slotOpenUrl(const QString &url) +{ + new KRun(KUrl(url), this); +} + #include "clipproperties.moc" +