26 #include <QStringList>    28 #include <KLocalizedString>    48                                           const QVariantList &args)
    50      m_url(), m_pattern(), m_numbering_mode(CONTINUE),
    51      m_selection_only(true), m_block_info()
    69     selection(Q_NULLPTR, &selection_left, &selection_right, 
false);
    73     bool selected_something = (selection_left != selection_right);
    74     bool selected_all = ((selection_left == 0) &&
    76     bool enable_selection_only = selected_something && !selected_all;
    78     QString filename = 
m_url.path();
    82     QPointer<Kwave::SaveBlocksDialog> dialog =
    84             _(
"kfiledialog:///kwave_save_blocks"),
    94         if (!dialog) 
return Q_NULLPTR;
    97     connect(dialog, SIGNAL(sigSelectionChanged(QString,
   102         dialog, SLOT(setNewExample(QString)));
   105     dialog->emitUpdate();
   106     if (dialog->exec() != QDialog::Accepted) {
   111     QStringList *list = 
new(std::nothrow) QStringList();
   117         QUrl url = dialog->selectedUrl();
   123         QString 
name = url.path();
   124         QFileInfo path(name);
   127         if (!path.suffix().length()) {
   128             QString ext = dialog->selectedExtension();
   129             QStringList extensions = ext.split(
_(
" "));
   130             ext = extensions.first();
   138         int mode = 
static_cast<int>(dialog->numberingMode());
   139         bool selection_only = (enable_selection_only) ?
   144         *list << QString::number(mode);
   145         *list << QString::number(selection_only);
   148             name + 
_(
",") + pattern + 
_(
",") +
   149             QString::number(mode) + 
_(
",") +
   150             QString::number(selection_only) + 
_(
")")
   154     if (dialog) 
delete dialog;
   160     const QStringList &list,
   161     unsigned int max_entries)
 const   163     if (!max_entries || list.isEmpty()) 
return QString();
   166     unsigned int count = 0;
   168     foreach (
const QString &entry, list) {
   170             retval = 
_(
"<br><br>");
   171         if (count < max_entries)
   172             retval += entry + 
_(
"<br>");
   173         else if (count == max_entries)
   174             retval += i18n(
"...") + 
_(
"<br>");
   176         if (++count > max_entries)
   186     qDebug(
"SaveBlocksPlugin::start()");
   190     if (result) 
return result;
   192     QString filename = 
m_url.path();
   193     QFileInfo file(filename);
   194     QString path = file.absolutePath();
   195     QString ext  = file.suffix();
   202     selection(Q_NULLPTR, &selection_left, &selection_right, 
false);
   204     bool selected_something = (selection_left != selection_right);
   205     bool selected_all = ( (selection_left == 0) &&
   207     bool enable_selection_only = selected_something && !selected_all;
   209     if (!selection_only) {
   231     QList<Kwave::FileProperty> unsupported_properties;
   243     QStringList  overwritten_files;
   244     QStringList  missing_dirs;
   245     for (
unsigned int i = first; i < (first + count); i++) {
   251         name = QString::fromLatin1(QUrl::toPercentEncoding(display_name, sep));
   252         QUrl url = 
m_url.adjusted(QUrl::RemoveFilename);
   253         url.setPath(url.path(QUrl::FullyEncoded) + 
name, QUrl::StrictMode);
   255         QString p = url.path();
   263         if (!fi.dir().exists()) {
   264             QString missing_dir = fi.absolutePath();
   265             if (!missing_dirs.contains(missing_dir))
   266                 missing_dirs += missing_dir;
   271     if (!overwritten_files.isEmpty()) {
   275             i18n(
"This would overwrite the following file(s): %1" \
   276             "Do you really want to continue?",
   278             _(
"</html>") ) != KMessageBox::Yes)
   285     if (!missing_dirs.isEmpty()) {
   288             i18n(
"The following directories do not exist: %1"   289                  "Do you want to create them and continue?",
   294             _(
"saveblocks_create_missing_dirs")
   295             ) != KMessageBox::Continue)
   301         QUrl base_url = 
m_url.adjusted(QUrl::RemoveFilename);
   302         foreach (
const QString &missing, missing_dirs) {
   305                 base_url.path(QUrl::FullyEncoded) +
   306                 QString::fromLatin1(QUrl::toPercentEncoding(missing)),
   309             QString p = url.path();
   312                 qWarning(
"creating path '%s' failed", 
DBG(p));
   319     selection(Q_NULLPTR, &saved_selection_left, &saved_selection_right, 
false);
   328     for (
unsigned int index = first;;) {
   329         block_start = block_end;
   332         if ((selection_left < block_end) && (selection_right > block_start)) {
   334             Q_ASSERT(index < first + count);
   338             if (left  < selection_left)  left  = selection_left;
   339             if (right > selection_right) right = selection_right;
   340             Q_ASSERT(right > left);
   341             if (right <= left) 
break; 
   351             name = QString::fromLatin1(QUrl::toPercentEncoding(name, sep));
   352             QUrl url = 
m_url.adjusted(QUrl::RemoveFilename);
   353             url.setPath(url.path(QUrl::FullyEncoded) + 
name, QUrl::StrictMode);
   356             if (!unsupported_properties.contains(
INF_NAME)) {
   357                 QString title = orig_file_info.
get(
INF_NAME).toString();
   358                 int idx = index - first;
   361                     if (block_title.length())
   362                         title = title + 
_(
", ") + block_title;
   369             qDebug(
"saving %9lu...%9lu -> '%s'",
   370                    static_cast<unsigned long int>(left),
   371                    static_cast<unsigned long int>(right),
   372                    DBG(url.toDisplayString()));
   381             if ((index == first) && !unsupported_properties.isEmpty()) {
   383                     file_info.
set(p, QVariant());
   392         if (label.
isNull()) 
break;
   402         (saved_selection_left != saved_selection_right) ?
   403         (saved_selection_right - saved_selection_left + 1) : 0);
   415     if (params.count() != 4) {
   421     if (!
m_url.isValid()) 
return -EINVAL;
   429     int mode = param.toInt(&ok);
   431     if (!ok) 
return -EINVAL;
   440     if (!ok) 
return -EINVAL;
   458     if (selection_only) {
   459         selection(Q_NULLPTR, &selection_left, &selection_right, 
true);
   468     QString file_title = info.
get(
INF_NAME).toString();
   472     if (!file_title.length()) file_title = base;
   477         block_start = block_end;
   479         block_title = prev_title;
   480         prev_title  = (label.
isNull()) ? file_title     : label.
name();
   482         if ((block_end > selection_left) && (block_start <= selection_right)) {
   485             block.
m_length = block_end - block_start;
   491         if (label.
isNull()) 
break;
   498     const QString &ext, 
const QString &pattern,
   499     unsigned int index, 
int count, 
int total)
   501     QString p = QRegExp::escape(pattern);
   505     QRegExp rx_nr(
_(
"(\\\\\\[%(\\d*)nr\\\\\\])"), Qt::CaseInsensitive);
   506     while (rx_nr.indexIn(p) >= 0) {
   507         QString format = rx_nr.cap(1);
   508         format = format.mid(2, format.length() - 6);
   509         QString ex = 
_(
"(\\\\\\[") + format + 
_(
"nr\\\\\\])");
   510         QRegExp rx(ex, Qt::CaseInsensitive);
   512         p.replace(rx, nr.sprintf(format.toLatin1(), index));
   516     QRegExp rx_count(
_(
"(\\\\\\[%\\d*count\\\\\\])"), Qt::CaseInsensitive);
   517     while (rx_count.indexIn(p) >= 0) {
   519             QString format = rx_count.cap(1);
   520             format = format.mid(2, format.length() - 9);
   521             QString ex = 
_(
"(\\\\\\[") + format + 
_(
"count\\\\\\])");
   522             QRegExp rx(ex, Qt::CaseInsensitive);
   524             p.replace(rx, nr.sprintf(format.toLatin1(), count));
   526             p.replace(rx_count, 
_(
"(\\d+)"));
   531     QRegExp rx_total(
_(
"(\\\\\\[%\\d*total\\\\\\])"), Qt::CaseInsensitive);
   532     while (rx_total.indexIn(p) >= 0) {
   534             QString format = rx_total.cap(1);
   535             format = format.mid(2, format.length() - 9);
   536             QString ex = 
_(
"(\\\\\\[") + format + 
_(
"total\\\\\\])");
   537             QRegExp rx(ex, Qt::CaseInsensitive);
   539             p.replace(rx, nr.sprintf(format.toLatin1(), total));
   541             p.replace(rx_total, 
_(
"(\\d+)"));
   546     QRegExp rx_filename(
_(
"\\\\\\[%filename\\\\\\]"), Qt::CaseInsensitive);
   547     if (rx_filename.indexIn(p) >= 0) {
   548         p.replace(rx_filename, QRegExp::escape(base));
   553         _(
"\\\\\\[%(\\d*)fileinfo\\\\\\{([\\w\\s]+)\\\\\\}\\\\\\]"),
   557     while (rx_fileinfo.indexIn(p) >= 0) {
   558         const QString format = rx_fileinfo.cap(1);
   559         const QString 
id     = rx_fileinfo.cap(2);
   563             QVariant val = info.
get(property);
   566                 value = val.toString();
   570                 int  len = format.toUInt(&ok);
   571                 if ((len > 0) && ok) {
   572                     Kwave::FileInfo::Flags flags = info.
flags(property);
   575                         QString pad = (format.startsWith(QLatin1Char(
'0'))) ?
   577                         while (value.length() < len)
   581                         while (value.length() < len)
   582                             value = value + 
_(
" ");
   589         QString ex(
_(
"(\\\\\\[%") + format + 
_(
"fileinfo\\\\\\{") + 
id +
   590                    _(
"\\\\\\}\\\\\\])"));
   591         QRegExp rx(ex, Qt::CaseInsensitive);
   592         p.replace(rx, value);
   596     QRegExp rx_title(
_(
"\\\\\\[%title\\\\\\]"), Qt::CaseInsensitive);
   597     if (rx_title.indexIn(p) >= 0) {
   599         int idx = (index - 1) - (total - count);
   602         if (title.length()) {
   604             p.replace(rx_title, title);
   608     if (ext.length()) p += 
_(
".") + ext;
   612     QString sep = 
_(
"/");
   613     QRegExp rx_sep(
_(
"\\s*") + sep + 
_(
"\\s*"));
   614     p.replace(rx_sep, sep);
   621     const QString &base, 
const QString &ext, 
const QString &pattern,
   624     unsigned int first = 1;
   630             QDir dir(path, 
_(
"*"));
   632             files = dir.entryList();
   633             for (
unsigned int i = first; i < (first + count); i++) {
   635                 QRegExp rx(
_(
"^(") + name + 
_(
")$"),
   636                            Qt::CaseInsensitive);
   637                 QStringList matches = files.filter(rx);
   638                 if (matches.count() > 0) first = i + 1;
   649                                           const QString &pattern)
   651     QFileInfo file(filename);
   652     QString 
name = file.fileName();
   653     QString base = file.completeBaseName();
   654     QString ext  = file.suffix();
   664     QRegExp rx_nr(
_(
"\\\\\\[%\\d*nr\\\\\\]"), Qt::CaseInsensitive);
   665     QRegExp rx_count(
_(
"\\\\\\[%\\d*count\\\\\\]"), Qt::CaseInsensitive);
   666     QRegExp rx_total(
_(
"\\\\\\[%\\d*total\\\\\\]"), Qt::CaseInsensitive);
   667     QRegExp rx_filename(
_(
"\\\\\\[%filename\\\\\\]"), Qt::CaseInsensitive);
   668     QRegExp rx_fileinfo(
_(
"\\\\\\[%fileinfo\\\\\\]"), Qt::CaseInsensitive);
   669     QRegExp rx_title(
_(
"\\\\\\[%title\\\\\\]"), Qt::CaseInsensitive);
   671     QString p = QRegExp::escape(pattern);
   672     int idx_nr       = rx_nr.indexIn(p);
   673     int idx_count    = rx_count.indexIn(p);
   674     int idx_total    = rx_total.indexIn(p);
   675     int idx_filename = rx_filename.indexIn(p);
   676     int idx_fileinfo = rx_fileinfo.indexIn(p);
   677     int idx_title    = rx_fileinfo.indexIn(p);
   678     p.replace(rx_nr,       
_(
"(\\d+)"));
   679     p.replace(rx_count,    
_(
"(\\d+)"));
   680     p.replace(rx_total,    
_(
"(\\d+)"));
   681     p.replace(rx_filename, 
_(
"(.+)"));
   682     p.replace(rx_fileinfo, 
_(
"(.+)"));
   683     p.replace(rx_title,    
_(
"(.+)"));
   686     for (
int i = 0; i < pattern.length(); i++) {
   687         if (idx_nr       == max) max++;
   688         if (idx_count    == max) max++;
   689         if (idx_total    == max) max++;
   690         if (idx_filename == max) max++;
   691         if (idx_fileinfo == max) max++;
   692         if (idx_title    == max) max++;
   694         if (idx_nr       > max) idx_nr--;
   695         if (idx_count    > max) idx_count--;
   696         if (idx_total    > max) idx_total--;
   697         if (idx_filename > max) idx_filename--;
   698         if (idx_fileinfo > max) idx_fileinfo--;
   699         if (idx_title    > max) idx_title--;
   702     if (ext.length()) p += 
_(
".") + ext;
   703     QRegExp rx_current(p, Qt::CaseInsensitive);
   704     if (rx_current.indexIn(name) >= 0) {
   706         base = rx_current.cap(idx_filename + 1);
   717     QFileInfo file(filename);
   718     QString path = file.absolutePath();
   719     QString ext  = file.suffix();
   720     QString base = 
findBase(filename, pattern);
   726     unsigned int first = 
firstIndex(path, base, ext, pattern, mode, count);
   727     unsigned int total = first + count - 1;
   738     QString example = 
firstFileName(filename, pattern, mode, selection_only);
   743 #include "SaveBlocksPlugin.moc" static QString encodingFilter()
void emitCommand(const QString &command)
QString createFileName(const QString &base, const QString &ext, const QString &pattern, unsigned int index, int count, int total)
numbering_mode_t m_numbering_mode
QList< BlockInfo > m_block_info
QString findBase(const QString &filename, const QString &pattern)
virtual QStringList * setup(QStringList &previous_params) Q_DECL_OVERRIDE
void updateExample(const QString &filename, const QString &pattern, Kwave::SaveBlocksPlugin::numbering_mode_t mode, bool selection_only)
QWidget * parentWidget() const
Kwave::MetaDataList & metaData()
QVariant get(FileProperty key) const
Kwave::SignalManager & signalManager()
virtual QString name() const
virtual sample_index_t pos() const
static QString mimeTypeOf(const QUrl &url)
bool connect(Kwave::StreamObject &source, const char *output, Kwave::StreamObject &sink, const char *input)
void set(FileProperty key, const QVariant &value)
QListIterator< Kwave::Label > LabelListIterator
QString firstFileName(const QString &filename, const QString &pattern, numbering_mode_t mode, bool selection_only)
static QString unescape(const QString &text)
static QString escapeForFileName(const QString &text)
virtual QList< Kwave::FileProperty > unsupportedProperties(const QList< Kwave::FileProperty > &properties_to_check)
const QMap< FileProperty, QVariant > properties() const
FileProperty fromName(const QString &name) const
virtual QString name() const
QString createDisplayList(const QStringList &list, unsigned int max_entries) const
virtual ~SaveBlocksPlugin() Q_DECL_OVERRIDE
unsigned int firstIndex(const QString &path, const QString &base, const QString &ext, const QString &pattern, Kwave::SaveBlocksPlugin::numbering_mode_t mode, unsigned int count)
virtual sample_index_t signalLength()
static int warningYesNo(QWidget *widget, QString message, QString caption=QString(), const QString buttonYes=QString(), const QString buttonNo=QString(), const QString &dontAskAgainName=QString())
int interpreteParameters(QStringList ¶ms)
static int warningContinueCancel(QWidget *widget, QString message, QString caption=QString(), const QString buttonContinue=QString(), const QString buttonCancel=QString(), const QString &dontAskAgainName=QString())
virtual void selectRange(sample_index_t offset, sample_index_t length)
static Kwave::Encoder * encoder(const QString &mimetype_name)
#define KWAVE_PLUGIN(name, class)
Flags flags(FileProperty key) const
void sigNewExample(const QString &example)
static QString escape(const QString &text)
virtual QString description() const
void scanBlocksToSave(const QString &base, bool selection_only)
virtual int start(QStringList ¶ms) Q_DECL_OVERRIDE
virtual sample_index_t selection(QList< unsigned int > *tracks=Q_NULLPTR, sample_index_t *left=Q_NULLPTR, sample_index_t *right=Q_NULLPTR, bool expand_if_empty=false)