View Issue Details
ID | Project | Category | View Status | Date Submitted | Last Update |
---|---|---|---|---|---|
0011776 | Scribus | Import / Export | public | 2013-10-09 21:36 | 2019-11-24 10:34 |
Reporter | pygmee | Assigned To | ale | ||
Priority | normal | Severity | feature | Reproducibility | N/A |
Status | closed | Resolution | duplicate | ||
Platform | x86 | OS | Debian | OS Version | wheezy |
Product Version | 1.5.0svn | ||||
Fixed in Version | 1.5.6.svn | ||||
Summary | 0011776: [PATCH]: Missing linked ressources improvement | ||||
Description | Actually when a linked ressource (font or image) is not found, the user has to define a replacement or do a search for each. We could provide simple Ui improvement to make things easier : 1. On font, we should provide a "choose directory" button that could let the user select a directory where the font are placed. The content of this folder would be listed and if other fonts missing are found there, add them automatically. 2. for pictures, in manage images, if the user choose a directory to search in, Scribus should compare all missing images with the content of this directory and relinked to those that could have been found there. | ||||
Tags | No tags attached. | ||||
Patch | Yes | ||||
|
See common ideas and more in 0011558: 3 Efficiency Features to improve Image Manager |
|
Add2 - done in ScribusECE http://www.git.scribus-ece.info/?p=ScribusECE;a=commitdiff;h=06635e5a8cea5d5cd4d6a4c5bbec223fc4251c2f;hp=68b0eef2e4f1398d75e486543458fdb6f19dc376 Scribus checks if external files exist on loading doc or on importing page. User can select directory for searching of missing files in it or stop searching and warning at all leaving epmty frames. |
|
cezaryce, pach proposed in 0011791 . I guess it would be nice to have it within the image manager too :) I did not test with fonts |
|
related to 0011791 |
|
Jluc, can you help me find where cez's patch is now in https://github.com/AlterScribus/ece15 ? |
|
i moved the fonts part to 0015873 . |
|
i almost forgot to upload the patch... here is the merge request: https://gitlab.com/scribus/scribus/merge_requests/13 and here how it "currently" works https://peertube.social/videos/watch/5d853734-bc08-4ff7-a7df-8b60f1e2feba the dialog can and should be further improved, this is a first step... manage-images.diff (20,942 bytes)
diff --git a/scribus/ui/picsearch.cpp b/scribus/ui/picsearch.cpp index 7e530eb5b..d922d64ee 100644 --- a/scribus/ui/picsearch.cpp +++ b/scribus/ui/picsearch.cpp @@ -20,7 +20,8 @@ for which a new license (GPL+exception) is in place. -PicSearch::PicSearch(QWidget* parent, const QString & fileName, const QStringList & avalableFiles) : QDialog(parent), currentImage(QString()) +PicSearch::PicSearch(QWidget* parent, const QString & fileName, const QStringList & avalableFiles, bool brokenLinksOnly) : + QDialog(parent), brokenLinksOnly{brokenLinksOnly} { setupUi(this); setModal(true); @@ -28,13 +29,18 @@ PicSearch::PicSearch(QWidget* parent, const QString & fileName, const QStringLis previewLabel->hide(); fileNameLabel->setText(fileName); - for (int i = 0; i < avalableFiles.count(); ++i) - foundFilesBox->addItem( QDir::toNativeSeparators(avalableFiles[i]) ); + for (const auto& file: avalableFiles) + foundFilesBox->addItem(QDir::toNativeSeparators(file)); + + foundFilesBox->setCurrentRow(0); + + matchWarningLabel->setVisible(false); // signals and slots connections connect(cancelButton, SIGNAL( clicked() ), this, SLOT( reject() ) ); connect(useButton, SIGNAL( clicked() ), this, SLOT( accept() ) ); connect(previewCheckBox, SIGNAL( clicked() ), this, SLOT( previewCheckBox_clicked() ) ); + connect(matchCheckBox, SIGNAL( clicked() ), this, SLOT( matchCheckBox_clicked() ) ); connect(foundFilesBox, SIGNAL(itemClicked(QListWidgetItem*)), this, SLOT(foundFilesBox_clicked(QListWidgetItem*))); } @@ -43,25 +49,28 @@ void PicSearch::previewCheckBox_clicked() if (previewCheckBox->isChecked()) { previewLabel->show(); - if (!currentImage.isEmpty()) - createPreview(); + createPreview(); } else previewLabel->hide(); } +void PicSearch::matchCheckBox_clicked() +{ + matchWarningLabel->setVisible(brokenLinksOnly && matchCheckBox->isChecked()); +} + void PicSearch::foundFilesBox_clicked(QListWidgetItem *c) { if (c == nullptr) return; - currentImage = QDir::fromNativeSeparators(c->text()); if (previewCheckBox->isChecked()) createPreview(); - useButton->setEnabled(true); } void PicSearch::createPreview() { + const auto currentImage = foundFilesBox->currentItem()->text(); QPixmap pm(200, 200); QFileInfo fi = QFileInfo(currentImage); int w = 200; diff --git a/scribus/ui/picsearch.h b/scribus/ui/picsearch.h index 90eded0a8..136db135e 100644 --- a/scribus/ui/picsearch.h +++ b/scribus/ui/picsearch.h @@ -24,7 +24,7 @@ for which a new license (GPL+exception) is in place. It's called after image search Extras/Manage Pictures/ Click [Search] button for chosen image frame item. */ class SCRIBUS_API PicSearch : public QDialog, Ui::PicSearch -{ +{ Q_OBJECT public: @@ -35,11 +35,13 @@ public: \param fileName QString name of image \param avalableFiles QStringList List of Paths where an Image with the given Name is present */ - PicSearch( QWidget* parent, const QString & fileName, const QStringList & avalableFiles); + PicSearch( QWidget* parent, const QString & fileName, const QStringList & avalableFiles, bool brokenLinksOnly); ~PicSearch() {}; - //! \brief Currently selected image with its full path - QString currentImage; + //! \brief Selected image with its full path + QString getSelectedImage() { return foundFilesBox->currentItem()->text(); } + //! \brief Matching images should also be replaced? + bool isApplyToMatchingImages() { return matchCheckBox->isChecked(); } private slots: /*! @@ -48,6 +50,11 @@ private slots: */ void previewCheckBox_clicked(); /*! + \author Ale Rimoldi + \brief If matching is desired (checked) then show a warning when only broken linked images are matched. + */ + void matchCheckBox_clicked(); + /*! \author Franz Schmid \brief When image is selected from the ListBox then the image preview may be shown and the Use button is enabled. \param c QListBoxItem @@ -63,8 +70,9 @@ signals: //! \brief Emitted when the pic for a row is replaced. Arg is row index. void rowPicChanged(unsigned int); -protected: +private: QSize minS; + bool brokenLinksOnly; }; #endif // PICSEARCH_H diff --git a/scribus/ui/picsearch.ui b/scribus/ui/picsearch.ui index fe1ff2445..135b4afb9 100644 --- a/scribus/ui/picsearch.ui +++ b/scribus/ui/picsearch.ui @@ -1,60 +1,77 @@ -<ui version="4.0" > - <author>Petr Vanek <petr@scribus.info></author> +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <author>Petr Vanek <petr@scribus.info></author> <class>PicSearch</class> - <widget class="QDialog" name="PicSearch" > - <property name="geometry" > + <widget class="QDialog" name="PicSearch"> + <property name="geometry"> <rect> <x>0</x> <y>0</y> - <width>499</width> - <height>263</height> + <width>516</width> + <height>292</height> </rect> </property> - <property name="windowTitle" > + <property name="windowTitle"> <string>Result</string> </property> - <layout class="QVBoxLayout" > - <property name="margin" > + <layout class="QVBoxLayout"> + <property name="spacing"> + <number>5</number> + </property> + <property name="leftMargin"> <number>10</number> </property> - <property name="spacing" > - <number>5</number> + <property name="topMargin"> + <number>10</number> + </property> + <property name="rightMargin"> + <number>10</number> + </property> + <property name="bottomMargin"> + <number>10</number> </property> <item> - <layout class="QHBoxLayout" > - <property name="margin" > + <layout class="QHBoxLayout"> + <property name="spacing"> + <number>5</number> + </property> + <property name="leftMargin"> <number>0</number> </property> - <property name="spacing" > - <number>5</number> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> </property> <item> - <widget class="QLabel" name="textLabel1" > - <property name="text" > + <widget class="QLabel" name="textLabel1"> + <property name="text"> <string>Search Results for: </string> </property> - <property name="wordWrap" > + <property name="wordWrap"> <bool>false</bool> </property> </widget> </item> <item> - <widget class="QLabel" name="fileNameLabel" > - <property name="sizePolicy" > - <sizepolicy> - <hsizetype>7</hsizetype> - <vsizetype>5</vsizetype> + <widget class="QLabel" name="fileNameLabel"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> <horstretch>0</horstretch> <verstretch>0</verstretch> </sizepolicy> </property> - <property name="frameShape" > + <property name="frameShape"> <enum>QFrame::Box</enum> </property> - <property name="text" > + <property name="text"> <string/> </property> - <property name="wordWrap" > + <property name="wordWrap"> <bool>false</bool> </property> </widget> @@ -62,43 +79,61 @@ </layout> </item> <item> - <layout class="QHBoxLayout" > - <property name="margin" > + <layout class="QHBoxLayout"> + <property name="spacing"> + <number>5</number> + </property> + <property name="leftMargin"> <number>0</number> </property> - <property name="spacing" > - <number>5</number> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> </property> <item> - <widget class="QListWidget" name="foundFilesBox" /> + <widget class="QListWidget" name="foundFilesBox"/> </item> <item> - <layout class="QVBoxLayout" > - <property name="margin" > + <layout class="QVBoxLayout"> + <property name="spacing"> + <number>5</number> + </property> + <property name="leftMargin"> <number>0</number> </property> - <property name="spacing" > - <number>5</number> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> </property> <item> - <widget class="QCheckBox" name="previewCheckBox" > - <property name="text" > + <widget class="QCheckBox" name="previewCheckBox"> + <property name="text"> <string>&Preview</string> </property> - <property name="shortcut" > + <property name="shortcut"> <string>Alt+P</string> </property> </widget> </item> <item> <spacer> - <property name="orientation" > + <property name="orientation"> <enum>Qt::Vertical</enum> </property> - <property name="sizeType" > + <property name="sizeType"> <enum>QSizePolicy::Expanding</enum> </property> - <property name="sizeHint" > + <property name="sizeHint" stdset="0"> <size> <width>21</width> <height>81</height> @@ -106,73 +141,59 @@ </property> </spacer> </item> - <item> - <widget class="QPushButton" name="useButton" > - <property name="enabled" > - <bool>false</bool> - </property> - <property name="text" > - <string>&Select</string> - </property> - <property name="shortcut" > - <string>Alt+S</string> - </property> - <property name="default" > - <bool>true</bool> - </property> - </widget> - </item> - <item> - <widget class="QPushButton" name="cancelButton" > - <property name="text" > - <string>Cancel</string> - </property> - </widget> - </item> </layout> </item> <item> - <layout class="QVBoxLayout" > - <property name="margin" > + <layout class="QVBoxLayout"> + <property name="spacing"> + <number>5</number> + </property> + <property name="leftMargin"> <number>0</number> </property> - <property name="spacing" > - <number>5</number> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> </property> <item> - <widget class="QLabel" name="previewLabel" > - <property name="minimumSize" > + <widget class="QLabel" name="previewLabel"> + <property name="minimumSize"> <size> <width>210</width> <height>210</height> </size> </property> - <property name="maximumSize" > + <property name="maximumSize"> <size> <width>210</width> <height>210</height> </size> </property> - <property name="frameShape" > + <property name="frameShape"> <enum>QFrame::Box</enum> </property> - <property name="alignment" > + <property name="alignment"> <set>Qt::AlignCenter</set> </property> - <property name="wordWrap" > + <property name="wordWrap"> <bool>false</bool> </property> </widget> </item> <item> <spacer> - <property name="orientation" > + <property name="orientation"> <enum>Qt::Vertical</enum> </property> - <property name="sizeType" > + <property name="sizeType"> <enum>QSizePolicy::Expanding</enum> </property> - <property name="sizeHint" > + <property name="sizeHint" stdset="0"> <size> <width>20</width> <height>40</height> @@ -184,9 +205,78 @@ </item> </layout> </item> + <item> + <widget class="QCheckBox" name="matchCheckBox"> + <property name="text"> + <string>Apply to all &Matching Images</string> + </property> + <property name="shortcut"> + <string>Alt+M</string> + </property> + </widget> + </item> + <item> + <widget class="QLabel" name="matchWarningLabel"> + <property name="enabled"> + <bool>true</bool> + </property> + <property name="sizePolicy"> + <sizepolicy hsizetype="Preferred" vsizetype="MinimumExpanding"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string>Since you selected an image with a broken link, only image frames with invalid links will be modified.</string> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> + </item> + <item> + <layout class="QHBoxLayout" name="horizontalLayout"> + <item> + <spacer name="horizontalSpacer"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + <item> + <widget class="QPushButton" name="useButton"> + <property name="enabled"> + <bool>true</bool> + </property> + <property name="text"> + <string>&Select</string> + </property> + <property name="shortcut"> + <string>Alt+S</string> + </property> + <property name="default"> + <bool>true</bool> + </property> + </widget> + </item> + <item> + <widget class="QPushButton" name="cancelButton"> + <property name="text"> + <string>Cancel</string> + </property> + </widget> + </item> + </layout> + </item> </layout> </widget> - <layoutdefault spacing="6" margin="11" /> + <layoutdefault spacing="6" margin="11"/> <resources/> <connections/> </ui> diff --git a/scribus/ui/picsearchoptions.cpp b/scribus/ui/picsearchoptions.cpp index fa7984306..a5384f622 100644 --- a/scribus/ui/picsearchoptions.cpp +++ b/scribus/ui/picsearchoptions.cpp @@ -89,7 +89,7 @@ void PicSearchOptions::slotChangeSearchDir() #else // TODO: and on _WIN32 workDir is ... ? #endif - QString searchBase = QFileDialog::getExistingDirectory(this, tr("Select a base directory for search"), workDir); + QString searchBase = QFileDialog::getExistingDirectory(this, tr("Select a base directory to search for ") + fileEdit->text(), workDir); if (searchBase.isEmpty() || !QDir().exists(searchBase)) return; m_strLastDirSearched = searchBase; diff --git a/scribus/ui/picstatus.cpp b/scribus/ui/picstatus.cpp index 26c93c42b..5926c67e2 100644 --- a/scribus/ui/picstatus.cpp +++ b/scribus/ui/picstatus.cpp @@ -36,8 +36,6 @@ for which a new license (GPL+exception) is in place. #include <QScopedPointer> #include <QToolButton> -#include <cstdio> - #include "commonstrings.h" #include "effectsdialog.h" #include "extimageprops.h" @@ -201,14 +199,13 @@ void PicStatus::fillTable() void PicStatus::sortByName() { - QListWidgetItem *firstItem = nullptr; QMap<QString, PicItem*> sorted; int num = imageViewArea->count(); if (num == 0) return; - firstItem = imageViewArea->currentItem(); + auto firstItem = imageViewArea->currentItem(); for (int a = num-1; a > -1; --a) { QListWidgetItem *ite = imageViewArea->takeItem(a); @@ -233,14 +230,13 @@ void PicStatus::sortByName() void PicStatus::sortByPage() { - QListWidgetItem *firstItem = nullptr; QMap<int, PicItem*> sorted; int num = imageViewArea->count(); if (num == 0) return; - firstItem = imageViewArea->currentItem(); + auto firstItem = imageViewArea->currentItem(); for (int a = num-1; a > -1; --a) { QListWidgetItem *ite = imageViewArea->takeItem(a); @@ -446,18 +442,18 @@ void PicStatus::SelectPic() emit selectElementByItem(currItem, true, 1); } -bool PicStatus::loadPict(const QString & newFilePath) +bool PicStatus::loadPict(PageItem* item, const QString & newFilePath) { // Hack to fool the LoadPict function - currItem->Pfile = newFilePath; - bool masterPageMode = !currItem->OnMasterPage.isEmpty(); + item->Pfile = newFilePath; + bool masterPageMode = !item->OnMasterPage.isEmpty(); bool oldMasterPageMode = m_Doc->masterPageMode(); if (masterPageMode != oldMasterPageMode) m_Doc->setMasterPageMode(masterPageMode); - m_Doc->loadPict(newFilePath, currItem, true); + m_Doc->loadPict(newFilePath, item, true); if (masterPageMode != oldMasterPageMode) m_Doc->setMasterPageMode(oldMasterPageMode); - return currItem->imageIsAvailable; + return item->imageIsAvailable; } void PicStatus::SearchPic() @@ -483,16 +479,24 @@ void PicStatus::SearchPic() return; } - QScopedPointer<PicSearch> dia2(new PicSearch(this, dia->getFileName(), dia->getMatches())); + auto item = static_cast<PicItem*>(imageViewArea->currentItem()); + bool brokenLink = !(item->PageItemObject->imageIsAvailable); + + QScopedPointer<PicSearch> dia2(new PicSearch(this, dia->getFileName(), dia->getMatches(), brokenLink)); if (dia2->exec() != QDialog::Accepted) return; - Q_ASSERT(!dia2->currentImage.isEmpty()); - loadPict(dia2->currentImage); + + auto source = QFileInfo(currItem->Pfile); + + loadPict(currItem, dia2->getSelectedImage()); refreshItem(currItem); - QFileInfo fi = QFileInfo(currItem->Pfile); - imageViewArea->currentItem()->setText(fi.fileName()); - imageViewArea->currentItem()->setIcon(createImgIcon(currItem)); + auto target = QFileInfo(currItem->Pfile); + item->setText(target.fileName()); + item->setIcon(createImgIcon(currItem)); imageSelected(imageViewArea->currentItem()); + + if (dia2->isApplyToMatchingImages()) + relinkMatchingImages(source, target, brokenLink); } void PicStatus::FileManager() @@ -515,7 +519,7 @@ void PicStatus::doImageEffects() if (dia->exec()) { currItem->effectsInUse = dia->effectsList; - loadPict(currItem->Pfile); + loadPict(currItem, currItem->Pfile); refreshItem(currItem); imageViewArea->currentItem()->setIcon(createImgIcon(currItem)); } @@ -530,7 +534,7 @@ void PicStatus::doImageExtProp() ExtImageProps dia(this, &currItem->pixm.imgInfo, currItem, m_Doc->view()); if (dia.exec()) { - loadPict(currItem->Pfile); + loadPict(currItem, currItem->Pfile); refreshItem(currItem); imageViewArea->currentItem()->setIcon(createImgIcon(currItem)); } @@ -543,3 +547,31 @@ void PicStatus::doEditImage() SelectPic(); ScCore->primaryMainWindow()->callImageEditor(); } + +/** + * Relink all matching images. + * Images match if they have the same path as the pattern. + * If the "pattern" was a broken link, only images with broken links will match. + */ +void PicStatus::relinkMatchingImages(const QFileInfo& source, const QFileInfo& target, bool brokenLink) +{ + for (int i = 0; i < imageViewArea->count(); i++) + { + auto item = static_cast<PicItem*>(imageViewArea->item(i)); + + if (brokenLink && item->PageItemObject->imageIsAvailable) + continue; + + auto fi = QFileInfo(item->PageItemObject->Pfile); + + if (fi.path() != source.path()) + continue; + if (fi.fileName() == target.fileName()) + continue; + + loadPict(item->PageItemObject, QDir(target.path()).filePath(fi.fileName())); + refreshItem(item->PageItemObject); + item->setText(fi.fileName()); + item->setIcon(createImgIcon(item->PageItemObject)); + } +} diff --git a/scribus/ui/picstatus.h b/scribus/ui/picstatus.h index 455e79e79..900d5f868 100644 --- a/scribus/ui/picstatus.h +++ b/scribus/ui/picstatus.h @@ -11,6 +11,8 @@ for which a new license (GPL+exception) is in place. #include "ui_picstatus.h" #include <QListWidgetItem> +class QFileInfo; + class ScribusDoc; class PageItem; @@ -82,6 +84,11 @@ private slots: void FileManager(); void doImageEffects(); void doImageExtProp(); + /*! + \author Ale Rimoldi + \brief Relink all images matching pattern. + */ + void relinkMatchingImages(const QFileInfo& source, const QFileInfo& target, bool brokenLink); void doEditImage(); signals: @@ -96,7 +103,7 @@ protected: /*! \brief Load the image specified into the PageItem \param newFilePath a file path */ - bool loadPict(const QString & newFilePath); + bool loadPict(PageItem* item, const QString & newFilePath); private: ScribusDoc *m_Doc; |
|
i've moved the font parts to 0015873 and "manage image" can now replace similar links in one go. |
Date Modified | Username | Field | Change |
---|---|---|---|
2013-10-09 21:36 | pygmee | New Issue | |
2013-10-10 20:51 | JLuc | Note Added: 0030707 | |
2013-10-11 07:27 | pygmee | Relationship added | duplicate of 0011558 |
2013-10-11 08:46 | cezaryece | Note Added: 0030718 | |
2013-10-11 08:53 | cezaryece | Note Edited: 0030718 | |
2013-10-15 21:55 | pygmee | Note Added: 0030733 | |
2014-06-13 00:46 | Kunda | Note Added: 0032127 | |
2014-06-13 05:28 | ale | Relationship added | related to 0011791 |
2016-02-14 14:04 | Kunda | Note Added: 0038717 | |
2019-10-24 15:55 | ale | Relationship added | parent of 0015873 |
2019-10-24 16:07 | ale | Note Added: 0046854 | |
2019-11-09 11:21 | ale | File Added: manage-images.diff | |
2019-11-09 11:21 | ale | Note Added: 0047044 | |
2019-11-09 11:22 | ale | Summary | Missing linked ressources improvement => [PATCH]: Missing linked ressources improvement |
2019-11-09 11:22 | ale | Patch | => Yes |
2019-11-22 08:33 | ale | Relationship added | related to 0009154 |
2019-11-24 10:31 | ale | Relationship deleted | parent of 0015873 |
2019-11-24 10:32 | ale | Relationship added | related to 0015873 |
2019-11-24 10:34 | ale | Assigned To | => ale |
2019-11-24 10:34 | ale | Status | new => closed |
2019-11-24 10:34 | ale | Resolution | open => duplicate |
2019-11-24 10:34 | ale | Fixed in Version | => 1.5.6.svn |
2019-11-24 10:34 | ale | Note Added: 0047126 |