KItemModelBase("text", parent),
m_dirLister(nullptr),
m_sortDirsFirst(true),
+ m_sortHiddenLast(true),
m_sortRole(NameRole),
m_sortingProgressPercent(-1),
m_roles(),
return m_sortDirsFirst;
}
+void KFileItemModel::setSortHiddenLast(bool hiddenLast)
+{
+ if (hiddenLast != m_sortHiddenLast) {
+ m_sortHiddenLast = hiddenLast;
+ resortAllItems();
+ }
+}
+
+bool KFileItemModel::sortHiddenLast() const
+{
+ return m_sortHiddenLast;
+}
+
void KFileItemModel::setShowHiddenFiles(bool show)
{
m_dirLister->setShowingDotFiles(show);
// emitted during the maximum update interval.
m_maximumUpdateIntervalTimer->start();
}
+
+ Q_EMIT fileItemsChanged({KFileItem(directoryUrl)});
}
void KFileItemModel::slotItemsDeleted(const KFileItemList& items)
QVector<int> indexesToRemove;
indexesToRemove.reserve(items.count());
+ KFileItemList dirsChanged;
for (const KFileItem& item : items) {
const int indexForItem = index(item);
m_filteredItems.erase(it);
}
}
+
+ QUrl parentUrl = item.url().adjusted(QUrl::RemoveFilename | QUrl::StripTrailingSlash);
+ if (dirsChanged.findByUrl(parentUrl).isNull()) {
+ dirsChanged << KFileItem(parentUrl);
+ }
}
std::sort(indexesToRemove.begin(), indexesToRemove.end());
const KItemRangeList itemRanges = KItemRangeList::fromSortedContainer(indexesToRemove);
removeFilteredChildren(itemRanges);
removeItems(itemRanges, DeleteItemData);
+
+ Q_EMIT fileItemsChanged(dirsChanged);
}
void KFileItemModel::slotRefreshItems(const QList<QPair<KFileItem, KFileItem> >& items)
indexes.reserve(items.count());
QSet<QByteArray> changedRoles;
+ KFileItemList changedFiles;
QListIterator<QPair<KFileItem, KFileItem> > it(items);
while (it.hasNext()) {
m_items.remove(oldItem.url());
m_items.insert(newItem.url(), indexForItem);
+ changedFiles.append(newItem);
indexes.append(indexForItem);
} else {
// Check if 'oldItem' is one of the filtered items.
std::sort(indexes.begin(), indexes.end());
const KItemRangeList itemRangeList = KItemRangeList::fromSortedContainer(indexes);
emitItemsChangedAndTriggerResorting(itemRangeList, changedRoles);
+
+ Q_EMIT fileItemsChanged(changedFiles);
}
void KFileItemModel::slotClear()
}
}
+ // Show hidden files and folders last
+ if (m_sortHiddenLast) {
+ const bool isHiddenA = a->item.isHidden();
+ const bool isHiddenB = b->item.isHidden();
+ if (isHiddenA && !isHiddenB) {
+ return false;
+ } else if (!isHiddenA && isHiddenB) {
+ return true;
+ }
+ }
+
if (m_sortDirsFirst || (DetailsModeSettings::directorySizeCount() && m_sortRole == SizeRole)) {
const bool isDirA = a->item.isDir();
const bool isDirB = b->item.isDir();
auto valueB = b->values.value("count");
if (valueA.isNull()) {
if (valueB.isNull()) {
- return 0;
+ result = 0;
+ break;
} else {
- return -1;
+ result = -1;
+ break;
}
} else if (valueB.isNull()) {
- return +1;
+ result = +1;
+ break;
} else {
if (valueA.toLongLong() < valueB.toLongLong()) {
- return -1;
+ result = -1;
+ break;
+ } else if (valueA.toLongLong() > valueB.toLongLong()) {
+ result = +1;
+ break;
} else {
- return +1;
+ result = 0;
+ break;
}
}
}
}
const KFileItem& item = m_itemData.at(i)->item;
- const KIO::filesize_t fileSize = !item.isNull() ? item.size() : ~0U;
+ KIO::filesize_t fileSize = !item.isNull() ? item.size() : ~0U;
QString newGroupValue;
if (!item.isNull() && item.isDir()) {
- newGroupValue = i18nc("@title:group Size", "Folders");
- } else if (fileSize < 5 * 1024 * 1024) {
- newGroupValue = i18nc("@title:group Size", "Small");
- } else if (fileSize < 10 * 1024 * 1024) {
- newGroupValue = i18nc("@title:group Size", "Medium");
- } else {
- newGroupValue = i18nc("@title:group Size", "Big");
+ if (DetailsModeSettings::directorySizeCount() || m_sortDirsFirst) {
+ newGroupValue = i18nc("@title:group Size", "Folders");
+ } else {
+ fileSize = m_itemData.at(i)->values.value("size").toULongLong();
+ }
+ }
+
+ if (newGroupValue.isEmpty()) {
+ if (fileSize < 5 * 1024 * 1024) { // < 5 MB
+ newGroupValue = i18nc("@title:group Size", "Small");
+ } else if (fileSize < 10 * 1024 * 1024) { // < 10 MB
+ newGroupValue = i18nc("@title:group Size", "Medium");
+ } else {
+ newGroupValue = i18nc("@title:group Size", "Big");
+ }
}
if (newGroupValue != groupValue) {
if (daysDistance == 1) {
const KLocalizedString format = ki18nc("@title:group Date: "
"MMMM is full month name in current locale, and yyyy is "
- "full year number", "'Yesterday' (MMMM, yyyy)");
+ "full year number. You must keep the ' don't use any fancy \" or « or similar. The ' is not shown to the user, it's there to mark a part of the text that should not be formatted as a date", "'Yesterday' (MMMM, yyyy)");
const QString translatedFormat = format.toString();
if (translatedFormat.count(QLatin1Char('\'')) == 2) {
newGroupValue = fileTime.toString(translatedFormat);
} else if (daysDistance <= 7) {
newGroupValue = fileTime.toString(i18nc("@title:group Date: "
"The week day name: dddd, MMMM is full month name "
- "in current locale, and yyyy is full year number",
+ "in current locale, and yyyy is full year number.",
"dddd (MMMM, yyyy)"));
newGroupValue = i18nc("Can be used to script translation of "
"\"dddd (MMMM, yyyy)\" with context @title:group Date",
} else if (daysDistance <= 7 * 2) {
const KLocalizedString format = ki18nc("@title:group Date: "
"MMMM is full month name in current locale, and yyyy is "
- "full year number", "'One Week Ago' (MMMM, yyyy)");
+ "full year number. You must keep the ' don't use any fancy \" or « or similar. The ' is not shown to the user, it's there to mark a part of the text that should not be formatted as a date", "'One Week Ago' (MMMM, yyyy)");
const QString translatedFormat = format.toString();
if (translatedFormat.count(QLatin1Char('\'')) == 2) {
newGroupValue = fileTime.toString(translatedFormat);
} else if (daysDistance <= 7 * 3) {
const KLocalizedString format = ki18nc("@title:group Date: "
"MMMM is full month name in current locale, and yyyy is "
- "full year number", "'Two Weeks Ago' (MMMM, yyyy)");
+ "full year number. You must keep the ' don't use any fancy \" or « or similar. The ' is not shown to the user, it's there to mark a part of the text that should not be formatted as a date", "'Two Weeks Ago' (MMMM, yyyy)");
const QString translatedFormat = format.toString();
if (translatedFormat.count(QLatin1Char('\'')) == 2) {
newGroupValue = fileTime.toString(translatedFormat);
} else if (daysDistance <= 7 * 4) {
const KLocalizedString format = ki18nc("@title:group Date: "
"MMMM is full month name in current locale, and yyyy is "
- "full year number", "'Three Weeks Ago' (MMMM, yyyy)");
+ "full year number. You must keep the ' don't use any fancy \" or « or similar. The ' is not shown to the user, it's there to mark a part of the text that should not be formatted as a date", "'Three Weeks Ago' (MMMM, yyyy)");
const QString translatedFormat = format.toString();
if (translatedFormat.count(QLatin1Char('\'')) == 2) {
newGroupValue = fileTime.toString(translatedFormat);
} else {
const KLocalizedString format = ki18nc("@title:group Date: "
"MMMM is full month name in current locale, and yyyy is "
- "full year number", "'Earlier on' MMMM, yyyy");
+ "full year number. You must keep the ' don't use any fancy \" or « or similar. The ' is not shown to the user, it's there to mark a part of the text that should not be formatted as a date", "'Earlier on' MMMM, yyyy");
const QString translatedFormat = format.toString();
if (translatedFormat.count(QLatin1Char('\'')) == 2) {
newGroupValue = fileTime.toString(translatedFormat);