• Skip to content
  • Skip to link menu
KDE 4.1 API Reference
  • KDE API Reference
  • kdelibs
  • Sitemap
  • Contact Us
 

KFile

kdirsortfilterproxymodel.cpp

Go to the documentation of this file.
00001 /*
00002    Copyright (C) 2006 by Peter Penz <peter.penz@gmx.at>
00003    Copyright (C) 2006 by Dominic Battre <dominic@battre.de>
00004    Copyright (C) 2006 by Martin Pool <mbp@canonical.com>
00005 
00006    Separated from Dolphin by Nick Shaforostoff <shafff@ukr.net>
00007 
00008    This library is free software; you can redistribute it and/or
00009    modify it under the terms of the GNU Library General Public
00010    License version 2 as published by the Free Software Foundation.
00011 
00012    This library is distributed in the hope that it will be useful,
00013    but WITHOUT ANY WARRANTY; without even the implied warranty of
00014    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015    Library General Public License for more details.
00016 
00017    You should have received a copy of the GNU Library General Public License
00018    along with this library; see the file COPYING.LIB.  If not, write to
00019    the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
00020    Boston, MA 02110-1301, USA.
00021 */
00022 
00023 #include "kdirsortfilterproxymodel.h"
00024 
00025 #include <kdirmodel.h>
00026 #include <kfileitem.h>
00027 #include <kdatetime.h>
00028 #include <klocale.h>
00029 #include <kstringhandler.h>
00030 #include <kdebug.h>
00031 
00032 // TODO KDE 4.1: bring Nepomuk stuff from Dolphin to kdelibs/nepomuk
00033 // in the form of a separate subclass
00034 
00035 KDirSortFilterProxyModel::KDirSortFilterProxyModel(QObject* parent)
00036     : KCategorizedSortFilterProxyModel(parent), d(0)
00037 {
00038     setDynamicSortFilter(true);
00039 
00040     // sort by the user visible string for now
00041     setSortCaseSensitivity(Qt::CaseInsensitive);
00042     sort(KDirModel::Name, Qt::AscendingOrder);
00043 
00044     setSupportedDragActions(Qt::CopyAction | Qt::MoveAction | Qt::LinkAction | Qt::IgnoreAction);
00045 }
00046 
00047 KDirSortFilterProxyModel::~KDirSortFilterProxyModel()
00048 {
00049 }
00050 
00051 bool KDirSortFilterProxyModel::hasChildren(const QModelIndex& parent) const
00052 {
00053     const QModelIndex sourceParent = mapToSource(parent);
00054     return sourceModel()->hasChildren(sourceParent);
00055 }
00056 
00057 bool KDirSortFilterProxyModel::canFetchMore(const QModelIndex& parent) const
00058 {
00059     const QModelIndex sourceParent = mapToSource(parent);
00060     return sourceModel()->canFetchMore(sourceParent);
00061 }
00062 
00063 int KDirSortFilterProxyModel::pointsForPermissions(const QFileInfo &info)
00064 {
00065     int points = 0;
00066 
00067     QFile::Permission permissionsCheck[] = { QFile::ReadUser,
00068                                              QFile::WriteUser,
00069                                              QFile::ExeUser,
00070                                              QFile::ReadGroup,
00071                                              QFile::WriteGroup,
00072                                              QFile::ExeGroup,
00073                                              QFile::ReadOther,
00074                                              QFile::WriteOther,
00075                                              QFile::ExeOther };
00076 
00077     for (int i = 0; i < 9; i++) {
00078         points += info.permission(permissionsCheck[i]) ? 1 : 0;
00079     }
00080 
00081     return points;
00082 }
00083 
00084 bool KDirSortFilterProxyModel::subSortLessThan(const QModelIndex& left,
00085                                                const QModelIndex& right) const
00086 {
00087     KDirModel* dirModel = static_cast<KDirModel*>(sourceModel());
00088 
00089     const KFileItem leftFileItem  = dirModel->itemForIndex(left);
00090     const KFileItem rightFileItem = dirModel->itemForIndex(right);
00091 
00092     // Directories and hidden files should always be on the top, independent
00093     // from the sort order.
00094     const bool isLessThan = (sortOrder() == Qt::AscendingOrder);
00095 
00096     // On our priority, folders go above regular files.
00097     if (leftFileItem.isDir() && !rightFileItem.isDir()) {
00098         return isLessThan;
00099     } else if (!leftFileItem.isDir() && rightFileItem.isDir()) {
00100         return !isLessThan;
00101     }
00102 
00103     // Hidden elements go before visible ones, if they both are
00104     // folders or files.
00105     if (leftFileItem.isHidden() && !rightFileItem.isHidden()) {
00106         return isLessThan;
00107     } else if (!leftFileItem.isHidden() && rightFileItem.isHidden()) {
00108         return !isLessThan;
00109     }
00110 
00111     switch (left.column()) {
00112     case KDirModel::Name: {
00113         return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00114     }
00115 
00116     case KDirModel::Size: {
00117         // If we have two folders, what we have to measure is the number of
00118         // items that contains each other
00119         if (leftFileItem.isDir() && rightFileItem.isDir()) {
00120             QVariant leftValue = dirModel->data(left, KDirModel::ChildCountRole);
00121             int leftCount = (leftValue.type() == QVariant::Int) ? leftValue.toInt() : KDirModel::ChildCountUnknown;
00122 
00123             QVariant rightValue = dirModel->data(right, KDirModel::ChildCountRole);
00124             int rightCount = (rightValue.type() == QVariant::Int) ? rightValue.toInt() : KDirModel::ChildCountUnknown;
00125 
00126             // In the case they two have the same child items, we sort them by
00127             // their names. So we have always everything ordered. We also check
00128             // if we are taking in count their cases.
00129             if (leftCount == rightCount) {
00130                 return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00131             }
00132 
00133             // If one of them has unknown child items, place them on the end. If we
00134             // were comparing two unknown childed items, the previous comparation
00135             // sorted them by naturalCompare between them. This case is when we
00136             // have an unknown childed item, and another known.
00137             if (leftCount == KDirModel::ChildCountUnknown) {
00138                 return false;
00139             }
00140 
00141             if (rightCount == KDirModel::ChildCountUnknown) {
00142                 return true;
00143             }
00144 
00145             // If they had different number of items, we sort them depending
00146             // on how many items had each other.
00147             return leftCount < rightCount;
00148         }
00149 
00150         // If what we are measuring is two files and they have the same size,
00151         // sort them by their file names.
00152         if (leftFileItem.size() == rightFileItem.size()) {
00153             return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00154         }
00155 
00156         // If their sizes are different, sort them by their sizes, as expected.
00157         return leftFileItem.size() < rightFileItem.size();
00158     }
00159 
00160     case KDirModel::ModifiedTime: {
00161         KDateTime leftModifiedTime = leftFileItem.time(KFileItem::ModificationTime).toLocalZone();
00162         KDateTime rightModifiedTime = rightFileItem.time(KFileItem::ModificationTime).toLocalZone();
00163 
00164         if (leftModifiedTime == rightModifiedTime) {
00165             return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00166         }
00167 
00168         return leftModifiedTime < rightModifiedTime;
00169     }
00170 
00171     case KDirModel::Permissions: {
00172         // ### You can't use QFileInfo on urls!! Use the KFileItem instead.
00173         QFileInfo leftFileInfo(leftFileItem.url().pathOrUrl());
00174         QFileInfo rightFileInfo(rightFileItem.url().pathOrUrl());
00175 
00176         int leftPermissionsPoints = pointsForPermissions(leftFileInfo);
00177         int rightPermissionsPoints = pointsForPermissions(rightFileInfo);
00178 
00179         if (leftPermissionsPoints == rightPermissionsPoints) {
00180             return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00181         }
00182 
00183         return leftPermissionsPoints > rightPermissionsPoints;
00184     }
00185 
00186     case KDirModel::Owner: {
00187         if (leftFileItem.user() == rightFileItem.user()) {
00188             return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00189         }
00190 
00191         return KStringHandler::naturalCompare(leftFileItem.user(), rightFileItem.user()) < 0;
00192     }
00193 
00194     case KDirModel::Group: {
00195         if (leftFileItem.group() == rightFileItem.group()) {
00196             return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00197         }
00198 
00199         return KStringHandler::naturalCompare(leftFileItem.group(), rightFileItem.group()) < 0;
00200     }
00201 
00202     case KDirModel::Type: {
00203         if (leftFileItem.mimetype() == rightFileItem.mimetype()) {
00204             return KStringHandler::naturalCompare(leftFileItem.name(), rightFileItem.name(), sortCaseSensitivity()) < 0;
00205         }
00206 
00207         return KStringHandler::naturalCompare(leftFileItem.mimeComment(), rightFileItem.mimeComment()) < 0;
00208     }
00209 
00210     }
00211 
00212     // We have set a SortRole and trust the ProxyModel to do
00213     // the right thing for now.
00214     return KCategorizedSortFilterProxyModel::subSortLessThan(left, right);
00215 }

KFile

Skip menu "KFile"
  • Main Page
  • Class Hierarchy
  • Alphabetical List
  • Class List
  • File List
  • Class Members
  • Related Pages

kdelibs

Skip menu "kdelibs"
  • DNSSD
  • Interfaces
  •   KHexEdit
  •   KMediaPlayer
  •   KSpeech
  •   KTextEditor
  • Kate
  • kconf_update
  • KDE3Support
  •   KUnitTest
  • KDECore
  • KDED
  • KDEsu
  • KDEUI
  • KDocTools
  • KFile
  • KHTML
  • KImgIO
  • KInit
  • KIO
  • KIOSlave
  • KJS
  •   KJS-API
  •   WTF
  • kjsembed
  • KNewStuff
  • KParts
  • Kross
  • KUtils
  • Nepomuk
  • Solid
  • Sonnet
  • ThreadWeaver
Generated for kdelibs by doxygen 1.5.4
This website is maintained by Adriaan de Groot and Allen Winter.
KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal