Changeset View
Changeset View
Standalone View
Standalone View
src/widgets/kurlcompletion.cpp
Show All 33 Lines | |||||
34 | #include <QtCore/QTimer> | 34 | #include <QtCore/QTimer> | ||
35 | #include <QtCore/QDir> | 35 | #include <QtCore/QDir> | ||
36 | #include <QtCore/QDirIterator> | 36 | #include <QtCore/QDirIterator> | ||
37 | #include <QtCore/QFile> | 37 | #include <QtCore/QFile> | ||
38 | #include <QtCore/QTextStream> | 38 | #include <QtCore/QTextStream> | ||
39 | #include <QtCore/QThread> | 39 | #include <QtCore/QThread> | ||
40 | #include <QtCore/QUrl> | 40 | #include <QtCore/QUrl> | ||
41 | #include <QtCore/QDebug> | 41 | #include <QtCore/QDebug> | ||
42 | #include <QMimeDatabase> | ||||
42 | #include <QProcessEnvironment> | 43 | #include <QProcessEnvironment> | ||
43 | #include <qplatformdefs.h> // QT_LSTAT, QT_STAT, QT_STATBUF | 44 | #include <qplatformdefs.h> // QT_LSTAT, QT_STAT, QT_STATBUF | ||
44 | 45 | | |||
45 | #include <kurlauthorized.h> | 46 | #include <kurlauthorized.h> | ||
46 | #include <kio/job.h> | 47 | #include <kio/job.h> | ||
47 | #include <kprotocolmanager.h> | 48 | #include <kprotocolmanager.h> | ||
48 | #include <kconfig.h> | 49 | #include <kconfig.h> | ||
49 | #include <ksharedconfig.h> | 50 | #include <ksharedconfig.h> | ||
▲ Show 20 Lines • Show All 146 Lines • ▼ Show 20 Line(s) | 115 | public: | |||
196 | 197 | | |||
197 | // Filters for files read with kio | 198 | // Filters for files read with kio | ||
198 | bool list_urls_only_exe; // true = only list executables | 199 | bool list_urls_only_exe; // true = only list executables | ||
199 | bool list_urls_no_hidden; | 200 | bool list_urls_no_hidden; | ||
200 | QString list_urls_filter; // filter for listed files | 201 | QString list_urls_filter; // filter for listed files | ||
201 | 202 | | |||
202 | CompletionThread *userListThread; | 203 | CompletionThread *userListThread; | ||
203 | CompletionThread *dirListThread; | 204 | CompletionThread *dirListThread; | ||
205 | | ||||
206 | QStringList mimeTypeFilters; | ||||
204 | }; | 207 | }; | ||
205 | 208 | | |||
206 | class CompletionThread : public QThread | 209 | class CompletionThread : public QThread | ||
207 | { | 210 | { | ||
208 | Q_OBJECT | 211 | Q_OBJECT | ||
209 | protected: | 212 | protected: | ||
210 | CompletionThread(KUrlCompletionPrivate *receiver) : | 213 | CompletionThread(KUrlCompletionPrivate *receiver) : | ||
211 | QThread(), | 214 | QThread(), | ||
▲ Show 20 Lines • Show All 91 Lines • ▼ Show 20 Line(s) | |||||
303 | 306 | | |||
304 | class DirectoryListThread : public CompletionThread | 307 | class DirectoryListThread : public CompletionThread | ||
305 | { | 308 | { | ||
306 | Q_OBJECT | 309 | Q_OBJECT | ||
307 | public: | 310 | public: | ||
308 | DirectoryListThread(KUrlCompletionPrivate *receiver, | 311 | DirectoryListThread(KUrlCompletionPrivate *receiver, | ||
309 | const QStringList &dirList, | 312 | const QStringList &dirList, | ||
310 | const QString &filter, | 313 | const QString &filter, | ||
314 | const QStringList &mimeTypeFilters, | ||||
311 | bool onlyExe, | 315 | bool onlyExe, | ||
312 | bool onlyDir, | 316 | bool onlyDir, | ||
313 | bool noHidden, | 317 | bool noHidden, | ||
314 | bool appendSlashToDir) : | 318 | bool appendSlashToDir) : | ||
315 | CompletionThread(receiver), | 319 | CompletionThread(receiver), | ||
316 | m_dirList(dirList), | 320 | m_dirList(dirList), | ||
317 | m_filter(filter), | 321 | m_filter(filter), | ||
322 | m_mimeTypeFilters(mimeTypeFilters), | ||||
318 | m_onlyExe(onlyExe), | 323 | m_onlyExe(onlyExe), | ||
319 | m_onlyDir(onlyDir), | 324 | m_onlyDir(onlyDir), | ||
320 | m_noHidden(noHidden), | 325 | m_noHidden(noHidden), | ||
321 | m_appendSlashToDir(appendSlashToDir) | 326 | m_appendSlashToDir(appendSlashToDir) | ||
322 | {} | 327 | {} | ||
323 | 328 | | |||
324 | void run() Q_DECL_OVERRIDE; | 329 | void run() Q_DECL_OVERRIDE; | ||
325 | 330 | | |||
326 | private: | 331 | private: | ||
327 | QStringList m_dirList; | 332 | QStringList m_dirList; | ||
328 | QString m_filter; | 333 | QString m_filter; | ||
334 | QStringList m_mimeTypeFilters; | ||||
329 | bool m_onlyExe; | 335 | bool m_onlyExe; | ||
330 | bool m_onlyDir; | 336 | bool m_onlyDir; | ||
331 | bool m_noHidden; | 337 | bool m_noHidden; | ||
332 | bool m_appendSlashToDir; | 338 | bool m_appendSlashToDir; | ||
333 | }; | 339 | }; | ||
334 | 340 | | |||
335 | void DirectoryListThread::run() | 341 | void DirectoryListThread::run() | ||
336 | { | 342 | { | ||
337 | //qDebug() << "Entered DirectoryListThread::run(), m_filter=" << m_filter << ", m_onlyExe=" << m_onlyExe << ", m_onlyDir=" << m_onlyDir << ", m_appendSlashToDir=" << m_appendSlashToDir << ", m_dirList.size()=" << m_dirList.size(); | 343 | //qDebug() << "Entered DirectoryListThread::run(), m_filter=" << m_filter << ", m_onlyExe=" << m_onlyExe << ", m_onlyDir=" << m_onlyDir << ", m_appendSlashToDir=" << m_appendSlashToDir << ", m_dirList.size()=" << m_dirList.size(); | ||
338 | 344 | | |||
339 | QDir::Filters iterator_filter = (m_noHidden ? QDir::Filter(0) : QDir::Hidden) | QDir::Readable | QDir::NoDotAndDotDot; | 345 | QDir::Filters iterator_filter = (m_noHidden ? QDir::Filter(0) : QDir::Hidden) | QDir::Readable | QDir::NoDotAndDotDot; | ||
340 | if (m_onlyExe) { | 346 | if (m_onlyExe) { | ||
341 | iterator_filter |= (QDir::Dirs | QDir::Files | QDir::Executable); | 347 | iterator_filter |= (QDir::Dirs | QDir::Files | QDir::Executable); | ||
342 | } else if (m_onlyDir) { | 348 | } else if (m_onlyDir) { | ||
343 | iterator_filter |= QDir::Dirs; | 349 | iterator_filter |= QDir::Dirs; | ||
344 | } else { | 350 | } else { | ||
345 | iterator_filter |= (QDir::Dirs | QDir::Files); | 351 | iterator_filter |= (QDir::Dirs | QDir::Files); | ||
346 | } | 352 | } | ||
347 | 353 | | |||
354 | QMimeDatabase mimeTypes; | ||||
355 | | ||||
348 | const QStringList::const_iterator end = m_dirList.constEnd(); | 356 | const QStringList::const_iterator end = m_dirList.constEnd(); | ||
349 | for (QStringList::const_iterator it = m_dirList.constBegin(); | 357 | for (QStringList::const_iterator it = m_dirList.constBegin(); | ||
350 | it != end && !terminationRequested(); | 358 | it != end && !terminationRequested(); | ||
351 | ++it) { | 359 | ++it) { | ||
352 | //qDebug() << "Scanning directory" << *it; | 360 | //qDebug() << "Scanning directory" << *it; | ||
353 | 361 | | |||
354 | QDirIterator current_dir_iterator(*it, iterator_filter); | 362 | QDirIterator current_dir_iterator(*it, iterator_filter); | ||
355 | 363 | | |||
356 | while (current_dir_iterator.hasNext() && !terminationRequested()) { | 364 | while (current_dir_iterator.hasNext() && !terminationRequested()) { | ||
357 | current_dir_iterator.next(); | 365 | current_dir_iterator.next(); | ||
358 | 366 | | |||
359 | QFileInfo file_info = current_dir_iterator.fileInfo(); | 367 | QFileInfo file_info = current_dir_iterator.fileInfo(); | ||
360 | const QString file_name = file_info.fileName(); | 368 | const QString file_name = file_info.fileName(); | ||
361 | 369 | | |||
362 | //qDebug() << "Found" << file_name; | 370 | //qDebug() << "Found" << file_name; | ||
363 | 371 | | |||
364 | if (m_filter.isEmpty() || file_name.startsWith(m_filter)) { | 372 | if (!m_filter.isEmpty() && !file_name.startsWith(m_filter)) { | ||
373 | continue; | ||||
374 | } | ||||
375 | | ||||
376 | if (!m_mimeTypeFilters.isEmpty() && !file_info.isDir()) { | ||||
377 | auto mimeType = mimeTypes.mimeTypeForFile(file_info); | ||||
378 | if (!m_mimeTypeFilters.contains(mimeType.name())) { | ||||
379 | continue; | ||||
380 | } | ||||
381 | } | ||||
365 | 382 | | |||
366 | QString toAppend = file_name; | 383 | QString toAppend = file_name; | ||
367 | // Add '/' to directories | 384 | // Add '/' to directories | ||
368 | if (m_appendSlashToDir && file_info.isDir()) { | 385 | if (m_appendSlashToDir && file_info.isDir()) { | ||
369 | toAppend.append(QLatin1Char('/')); | 386 | toAppend.append(QLatin1Char('/')); | ||
370 | } | 387 | } | ||
371 | 388 | | |||
372 | if (m_complete_url) { | 389 | if (m_complete_url) { | ||
373 | QUrl info(m_prepend); | 390 | QUrl info(m_prepend); | ||
374 | info = addPathToUrl(info, toAppend); | 391 | info = addPathToUrl(info, toAppend); | ||
375 | addMatch(info.toDisplayString()); | 392 | addMatch(info.toDisplayString()); | ||
376 | } else { | 393 | } else { | ||
377 | addMatch(m_prepend + toAppend); | 394 | addMatch(m_prepend + toAppend); | ||
378 | } | 395 | } | ||
379 | } | 396 | } | ||
380 | } | 397 | } | ||
381 | } | | |||
382 | 398 | | |||
383 | done(); | 399 | done(); | ||
384 | } | 400 | } | ||
385 | 401 | | |||
386 | KUrlCompletionPrivate::~KUrlCompletionPrivate() | 402 | KUrlCompletionPrivate::~KUrlCompletionPrivate() | ||
387 | { | 403 | { | ||
388 | } | 404 | } | ||
389 | 405 | | |||
▲ Show 20 Lines • Show All 212 Lines • ▼ Show 20 Line(s) | |||||
602 | 618 | | |||
603 | /* | 619 | /* | ||
604 | * makeCompletion() | 620 | * makeCompletion() | ||
605 | * | 621 | * | ||
606 | * Entry point for file name completion | 622 | * Entry point for file name completion | ||
607 | */ | 623 | */ | ||
608 | QString KUrlCompletion::makeCompletion(const QString &text) | 624 | QString KUrlCompletion::makeCompletion(const QString &text) | ||
609 | { | 625 | { | ||
610 | qCDebug(KIO_WIDGETS) << text << "d->cwd=" << d->cwd; | 626 | qCDebug(KIO_WIDGETS) << text << "d->cwd=" << d->cwd; | ||
dfaure: Please revert -- and use kdebugsettings next time, to enable categorized debug output ;)… | |||||
611 | 627 | | |||
612 | KUrlCompletionPrivate::MyURL url(text, d->cwd); | 628 | KUrlCompletionPrivate::MyURL url(text, d->cwd); | ||
613 | 629 | | |||
614 | d->compl_text = text; | 630 | d->compl_text = text; | ||
615 | 631 | | |||
616 | // Set d->prepend to the original URL, with the filename [and ref/query] stripped. | 632 | // Set d->prepend to the original URL, with the filename [and ref/query] stripped. | ||
617 | // This is what gets prepended to the directory-listing matches. | 633 | // This is what gets prepended to the directory-listing matches. | ||
618 | if (url.isURL()) { | 634 | if (url.isURL()) { | ||
▲ Show 20 Lines • Show All 490 Lines • ▼ Show 20 Line(s) | 1123 | for (QStringList::ConstIterator it = dirList.constBegin(); | |||
1109 | ++it) { | 1125 | ++it) { | ||
1110 | QUrl url = QUrl::fromLocalFile(*it); | 1126 | QUrl url = QUrl::fromLocalFile(*it); | ||
1111 | if (KUrlAuthorized::authorizeUrlAction(QStringLiteral("list"), QUrl(), url)) { | 1127 | if (KUrlAuthorized::authorizeUrlAction(QStringLiteral("list"), QUrl(), url)) { | ||
1112 | dirs.append(*it); | 1128 | dirs.append(*it); | ||
1113 | } | 1129 | } | ||
1114 | } | 1130 | } | ||
1115 | 1131 | | |||
1116 | Q_ASSERT(!dirListThread); // caller called stop() | 1132 | Q_ASSERT(!dirListThread); // caller called stop() | ||
1117 | dirListThread = new DirectoryListThread(this, dirs, filter, only_exe, only_dir, | 1133 | dirListThread = new DirectoryListThread(this, dirs, filter, mimeTypeFilters, | ||
1118 | no_hidden, append_slash_to_dir); | 1134 | only_exe, only_dir, no_hidden, | ||
1135 | append_slash_to_dir); | ||||
1119 | QObject::connect(dirListThread, &CompletionThread::completionThreadDone, | 1136 | QObject::connect(dirListThread, &CompletionThread::completionThreadDone, | ||
1120 | q, [this](QThread *thread, const QStringList &matches){ slotCompletionThreadDone(thread, matches); }); | 1137 | q, [this](QThread *thread, const QStringList &matches){ slotCompletionThreadDone(thread, matches); }); | ||
1121 | dirListThread->start(); | 1138 | dirListThread->start(); | ||
1122 | dirListThread->wait(initialWaitDuration()); | 1139 | dirListThread->wait(initialWaitDuration()); | ||
1123 | qCDebug(KIO_WIDGETS) << "Adding initial matches:" << dirListThread->matches(); | 1140 | qCDebug(KIO_WIDGETS) << "Adding initial matches:" << dirListThread->matches(); | ||
1124 | addMatches(dirListThread->matches()); | 1141 | addMatches(dirListThread->matches()); | ||
1125 | 1142 | | |||
1126 | return finished(); | 1143 | return finished(); | ||
▲ Show 20 Lines • Show All 89 Lines • ▼ Show 20 Line(s) | 1214 | for (; it != end; ++it) { | |||
1216 | } | 1233 | } | ||
1217 | 1234 | | |||
1218 | const bool isDir = entry.isDir(); | 1235 | const bool isDir = entry.isDir(); | ||
1219 | 1236 | | |||
1220 | if (mode == KUrlCompletion::DirCompletion && !isDir) { | 1237 | if (mode == KUrlCompletion::DirCompletion && !isDir) { | ||
1221 | continue; | 1238 | continue; | ||
1222 | } | 1239 | } | ||
1223 | 1240 | | |||
1224 | if (filter_len == 0 || entry_name.left(filter_len) == filter) { | 1241 | if (filter_len != 0 && entry_name.left(filter_len) != filter) { | ||
1242 | continue; | ||||
1243 | } | ||||
1244 | | ||||
1245 | if (!mimeTypeFilters.isEmpty() && !isDir && | ||||
1246 | !mimeTypeFilters.contains(entry.stringValue(KIO::UDSEntry::UDS_MIME_TYPE))) { | ||||
1247 | continue; | ||||
1248 | } | ||||
1225 | 1249 | | |||
1226 | QString toAppend = entry_name; | 1250 | QString toAppend = entry_name; | ||
1227 | 1251 | | |||
1228 | if (isDir) { | 1252 | if (isDir) { | ||
1229 | toAppend.append(QLatin1Char('/')); | 1253 | toAppend.append(QLatin1Char('/')); | ||
1230 | } | 1254 | } | ||
1231 | 1255 | | |||
1232 | if (!list_urls_only_exe || | 1256 | if (!list_urls_only_exe || | ||
1233 | (entry.numberValue(KIO::UDSEntry::UDS_ACCESS) & MODE_EXE) // true if executable | 1257 | (entry.numberValue(KIO::UDSEntry::UDS_ACCESS) & MODE_EXE) // true if executable | ||
1234 | ) { | 1258 | ) { | ||
1235 | if (complete_url) { | 1259 | if (complete_url) { | ||
1236 | QUrl url(prepend); | 1260 | QUrl url(prepend); | ||
1237 | url = addPathToUrl(url, toAppend); | 1261 | url = addPathToUrl(url, toAppend); | ||
1238 | matchList.append(url.toDisplayString()); | 1262 | matchList.append(url.toDisplayString()); | ||
1239 | } else { | 1263 | } else { | ||
1240 | matchList.append(prepend + toAppend); | 1264 | matchList.append(prepend + toAppend); | ||
1241 | } | 1265 | } | ||
1242 | } | 1266 | } | ||
1243 | } | 1267 | | ||
1244 | } | 1268 | } | ||
1245 | 1269 | | |||
1246 | addMatches(matchList); | 1270 | addMatches(matchList); | ||
1247 | } | 1271 | } | ||
1248 | 1272 | | |||
1249 | /* | 1273 | /* | ||
1250 | * _k_slotIOFinished | 1274 | * _k_slotIOFinished | ||
1251 | * | 1275 | * | ||
▲ Show 20 Lines • Show All 139 Lines • ▼ Show 20 Line(s) | 1404 | { | |||
1391 | return url.dir() + url.file(); | 1415 | return url.dir() + url.file(); | ||
1392 | } | 1416 | } | ||
1393 | 1417 | | |||
1394 | QString KUrlCompletion::replacedPath(const QString &text) const | 1418 | QString KUrlCompletion::replacedPath(const QString &text) const | ||
1395 | { | 1419 | { | ||
1396 | return replacedPath(text, d->replace_home, d->replace_env); | 1420 | return replacedPath(text, d->replace_home, d->replace_env); | ||
1397 | } | 1421 | } | ||
1398 | 1422 | | |||
1423 | void KUrlCompletion::setMimeTypeFilters(const QStringList &mimeTypeFilters) | ||||
1424 | { | ||||
1425 | d->mimeTypeFilters = mimeTypeFilters; | ||||
1426 | } | ||||
1427 | | ||||
1428 | QStringList KUrlCompletion::mimeTypeFilters() const | ||||
1429 | { | ||||
1430 | return d->mimeTypeFilters; | ||||
1431 | } | ||||
1432 | | ||||
1399 | ///////////////////////////////////////////////////////// | 1433 | ///////////////////////////////////////////////////////// | ||
1400 | ///////////////////////////////////////////////////////// | 1434 | ///////////////////////////////////////////////////////// | ||
1401 | // Static functions | 1435 | // Static functions | ||
1402 | 1436 | | |||
1403 | /* | 1437 | /* | ||
1404 | * expandEnv | 1438 | * expandEnv | ||
1405 | * | 1439 | * | ||
1406 | * Expand environment variables in text. Escaped '$' are ignored. | 1440 | * Expand environment variables in text. Escaped '$' are ignored. | ||
▲ Show 20 Lines • Show All 131 Lines • Show Last 20 Lines |
Please revert -- and use kdebugsettings next time, to enable categorized debug output ;)
(repeats)