Changeset View
Changeset View
Standalone View
Standalone View
src/kitemviews/private/kdirectorycontentscounterworker.cpp
Show All 22 Lines | |||||
23 | // Required includes for subItemsCount(): | 23 | // Required includes for subItemsCount(): | ||
24 | #ifdef Q_OS_WIN | 24 | #ifdef Q_OS_WIN | ||
25 | #include <QDir> | 25 | #include <QDir> | ||
26 | #else | 26 | #else | ||
27 | #include <QFile> | 27 | #include <QFile> | ||
28 | #include <qplatformdefs.h> | 28 | #include <qplatformdefs.h> | ||
29 | #endif | 29 | #endif | ||
30 | 30 | | |||
31 | #include "dolphin_detailsmodesettings.h" | ||||
32 | | ||||
31 | KDirectoryContentsCounterWorker::KDirectoryContentsCounterWorker(QObject* parent) : | 33 | KDirectoryContentsCounterWorker::KDirectoryContentsCounterWorker(QObject* parent) : | ||
32 | QObject(parent) | 34 | QObject(parent) | ||
33 | { | 35 | { | ||
34 | qRegisterMetaType<KDirectoryContentsCounterWorker::Options>(); | 36 | qRegisterMetaType<KDirectoryContentsCounterWorker::Options>(); | ||
35 | } | 37 | } | ||
36 | 38 | | |||
37 | int KDirectoryContentsCounterWorker::subItemsCount(const QString& path, Options options) | 39 | KDirectoryContentsCounterWorker::CountResult walkDir(const QString &dirPath, | ||
40 | const bool countHiddenFiles, | ||||
41 | const bool countDirectoriesOnly, | ||||
42 | QT_DIRENT *dirEntry, | ||||
43 | const uint allowedRecursiveLevel) | ||||
38 | { | 44 | { | ||
39 | const bool countHiddenFiles = options & CountHiddenFiles; | | |||
40 | const bool countDirectoriesOnly = options & CountDirectoriesOnly; | | |||
41 | | ||||
42 | #ifdef Q_OS_WIN | | |||
43 | QDir dir(path); | | |||
44 | QDir::Filters filters = QDir::NoDotAndDotDot | QDir::System; | | |||
45 | if (countHiddenFiles) { | | |||
46 | filters |= QDir::Hidden; | | |||
47 | } | | |||
48 | if (countDirectoriesOnly) { | | |||
49 | filters |= QDir::Dirs; | | |||
50 | } else { | | |||
51 | filters |= QDir::AllEntries; | | |||
52 | } | | |||
53 | return dir.entryList(filters).count(); | | |||
54 | #else | | |||
55 | // Taken from kio/src/widgets/kdirmodel.cpp | | |||
56 | // Copyright (C) 2006 David Faure <faure@kde.org> | | |||
57 | | ||||
58 | int count = -1; | 45 | int count = -1; | ||
59 | auto dir = QT_OPENDIR(QFile::encodeName(path)); | 46 | long size = -1; | ||
47 | auto dir = QT_OPENDIR(QFile::encodeName(dirPath)); | ||||
elvisangelaccio: Why `toLocal8Bit()` ? | |||||
meven: QtCreator was giving me a weird warning. | |||||
60 | if (dir) { | 48 | if (dir) { | ||
61 | count = 0; | 49 | count = 0; | ||
62 | QT_DIRENT *dirEntry = nullptr; | 50 | QT_STATBUF buf; | ||
51 | | ||||
63 | while ((dirEntry = QT_READDIR(dir))) { | 52 | while ((dirEntry = QT_READDIR(dir))) { | ||
elvisangelaccio: These can be declared below, where they are actually used. | |||||
64 | if (dirEntry->d_name[0] == '.') { | 53 | if (dirEntry->d_name[0] == '.') { | ||
65 | if (dirEntry->d_name[1] == '\0' || !countHiddenFiles) { | 54 | if (dirEntry->d_name[1] == '\0' || !countHiddenFiles) { | ||
66 | // Skip "." or hidden files | 55 | // Skip "." or hidden files | ||
67 | continue; | 56 | continue; | ||
68 | } | 57 | } | ||
69 | if (dirEntry->d_name[1] == '.' && dirEntry->d_name[2] == '\0') { | 58 | if (dirEntry->d_name[1] == '.' && dirEntry->d_name[2] == '\0') { | ||
70 | // Skip ".." | 59 | // Skip ".." | ||
71 | continue; | 60 | continue; | ||
72 | } | 61 | } | ||
73 | } | 62 | } | ||
74 | 63 | | |||
75 | // If only directories are counted, consider an unknown file type and links also | 64 | // If only directories are counted, consider an unknown file type and links also | ||
76 | // as directory instead of trying to do an expensive stat() | 65 | // as directory instead of trying to do an expensive stat() | ||
77 | // (see bugs 292642 and 299997). | 66 | // (see bugs 292642 and 299997). | ||
78 | const bool countEntry = !countDirectoriesOnly || | 67 | const bool countEntry = !countDirectoriesOnly || | ||
79 | dirEntry->d_type == DT_DIR || | 68 | dirEntry->d_type == DT_DIR || | ||
80 | dirEntry->d_type == DT_LNK || | 69 | dirEntry->d_type == DT_LNK || | ||
81 | dirEntry->d_type == DT_UNKNOWN; | 70 | dirEntry->d_type == DT_UNKNOWN; | ||
82 | if (countEntry) { | 71 | if (countEntry) { | ||
83 | ++count; | 72 | ++count; | ||
84 | } | 73 | } | ||
74 | | ||||
75 | if (allowedRecursiveLevel > 0) { | ||||
76 | | ||||
elvisangelaccio: `QStringLiteral` | |||||
77 | bool linkFound = false; | ||||
78 | QString nameBuf = QStringLiteral("%1/%2").arg(dirPath, dirEntry->d_name); | ||||
79 | | ||||
80 | if (dirEntry->d_type == DT_REG || dirEntry->d_type == DT_LNK) { | ||||
81 | if (QT_STAT(nameBuf.toLocal8Bit(), &buf) == 0) { | ||||
82 | if (S_ISDIR(buf.st_mode)) { | ||||
83 | // was a dir link, recurse | ||||
84 | linkFound = true; | ||||
85 | } | ||||
86 | size += buf.st_size; | ||||
87 | } | ||||
88 | } | ||||
89 | if (dirEntry->d_type == DT_DIR || linkFound) { | ||||
90 | // recursion for dirs and dir links | ||||
91 | size += walkDir(nameBuf, countHiddenFiles, countDirectoriesOnly, dirEntry, allowedRecursiveLevel - 1).size; | ||||
92 | } | ||||
93 | } | ||||
85 | } | 94 | } | ||
86 | QT_CLOSEDIR(dir); | 95 | QT_CLOSEDIR(dir); | ||
87 | } | 96 | } | ||
88 | return count; | 97 | return KDirectoryContentsCounterWorker::CountResult{count, size}; | ||
98 | } | ||||
99 | | ||||
100 | KDirectoryContentsCounterWorker::CountResult KDirectoryContentsCounterWorker::subItemsCount(const QString& path, Options options) | ||||
101 | { | ||||
102 | const bool countHiddenFiles = options & CountHiddenFiles; | ||||
103 | const bool countDirectoriesOnly = options & CountDirectoriesOnly; | ||||
104 | | ||||
105 | #ifdef Q_OS_WIN | ||||
106 | QDir dir(path); | ||||
107 | QDir::Filters filters = QDir::NoDotAndDotDot | QDir::System; | ||||
108 | if (countHiddenFiles) { | ||||
109 | filters |= QDir::Hidden; | ||||
110 | } | ||||
111 | if (countDirectoriesOnly) { | ||||
112 | filters |= QDir::Dirs; | ||||
113 | } else { | ||||
114 | filters |= QDir::AllEntries; | ||||
115 | } | ||||
116 | return {dir.entryList(filters).count(), 0}; | ||||
117 | #else | ||||
118 | | ||||
119 | const uint maxRecursiveLevel = DetailsModeSettings::directorySizeCount() ? 1 : DetailsModeSettings::recursiveDirectorySizeLimit(); | ||||
anthonyfieroni: Same, don't allow value more than 128. | |||||
meven: Btw The UI currently max it at 20 viewsettingstab.cpp:123 | |||||
120 | | ||||
elvisangelaccio: Why call `QFile::encodeName()` here and not inside `walkDir()` ? | |||||
121 | QT_DIRENT *dirEntry = nullptr; | ||||
122 | | ||||
123 | auto res = walkDir(QFile::encodeName(path), countHiddenFiles, countDirectoriesOnly, dirEntry, maxRecursiveLevel); | ||||
124 | | ||||
125 | return res; | ||||
89 | #endif | 126 | #endif | ||
90 | } | 127 | } | ||
91 | 128 | | |||
92 | void KDirectoryContentsCounterWorker::countDirectoryContents(const QString& path, Options options) | 129 | void KDirectoryContentsCounterWorker::countDirectoryContents(const QString& path, Options options) | ||
93 | { | 130 | { | ||
94 | emit result(path, subItemsCount(path, options)); | 131 | auto res = subItemsCount(path, options); | ||
132 | emit result(path, res.count, res.size); | ||||
95 | } | 133 | } |
Why toLocal8Bit() ?