Mixxx

/home/maxime/Projets/Mixxx/1.10/mixxx/src/library/browse/foldertreemodel.cpp

Go to the documentation of this file.
00001 #if defined (__WINDOWS__)
00002 #include <windows.h>
00003 #include <Shellapi.h>
00004 #include <Shobjidl.h>
00005 #else
00006 #include <sys/types.h>
00007 #include <sys/stat.h>
00008 #include <dirent.h>
00009 #include <unistd.h>
00010 #include <errno.h>
00011 #endif
00012 
00013 #include <QtGui>
00014 #include <QDirModel>
00015 #include <QStringList>
00016 #include <QFileInfo>
00017 #include <QDesktopServices>
00018 
00019 #include "library/treeitem.h"
00020 #include "library/browse/foldertreemodel.h"
00021 #include "library/browse/browsefeature.h"
00022 
00023 FolderTreeModel::FolderTreeModel(QObject *parent)
00024         : TreeItemModel(parent) {
00025 }
00026 
00027 FolderTreeModel::~FolderTreeModel() {
00028 }
00029 
00030 /* A tree model of the filesystem should be initialized lazy.
00031  * It will take the universe to iterate over all files over filesystem
00032  * hasChildren() returns true if a folder has subfolders although
00033  * we do not know the precise number of subfolders.
00034  *
00035  * Note that BrowseFeature inserts folder trees dynamically and rowCount()
00036  * is only called if necessary.
00037  */
00038 bool FolderTreeModel::hasChildren( const QModelIndex & parent) const
00039 {
00040 
00041     TreeItem *item = static_cast<TreeItem*>(parent.internalPointer());
00042     /* Usually the child count is 0 becuase we do lazy initalization
00043      * However, for, buid-in items such as 'Quick Links' there exist
00044      * child items at init time
00045      */
00046     if(item->dataPath().toString() == QUICK_LINK_NODE)
00047         return true;
00048     //Can only happen on Windows
00049     if(item->dataPath().toString() == DEVICE_NODE)
00050         return true;
00051 
00052     //In all other cases the dataPath() points to a folder
00053 
00054     QString folder = item->dataPath().toString();
00055 
00056     /*
00057      *  The following code is too expensive, general and SLOW since
00058      *  QDIR::EntryInfoList returns a full QFileInfolist
00059      *
00060      *
00061      *  QDir dir(item->dataPath().toString());
00062      *  QFileInfoList all = dir.entryInfoList(QDir::Dirs | QDir::NoDotAndDotDot);
00063      *  return (all.count() > 0);
00064      *
00065      *  We can benefit from low-level filesystem APIs, i.e.,
00066      *  Windows API or SystemCalls
00067      */
00068 
00069 #if defined (__WINDOWS__)
00070     folder.replace("/","\\");
00071 
00072     //quick subfolder test
00073     SHFILEINFOW sfi;
00074     SHGetFileInfo((LPCWSTR) folder.constData(), NULL, &sfi, sizeof(sfi), SHGFI_ATTRIBUTES);
00075     return (sfi.dwAttributes & SFGAO_HASSUBFOLDER);
00076 #else
00077     // For OS X and Linux
00078     // http://stackoverflow.com/questions/2579948/checking-if-subfolders-exist-linux
00079 
00080     std::string dot("."), dotdot("..");
00081     bool found_subdir = false;
00082     QByteArray ba = folder.toLocal8Bit();
00083     DIR *directory = opendir(ba);
00084 
00085     if (directory == NULL){
00086         return false;
00087     }
00088     struct dirent *entry;
00089     while (!found_subdir && ((entry = readdir(directory)) != NULL)) {
00090         if (entry->d_name != dot && entry->d_name != dotdot)
00091         {
00092             found_subdir = (entry->d_type == DT_DIR || entry->d_type == DT_LNK);
00093             //qDebug() << "Subfolder of " << folder << " : " << entry->d_name << "type :" << entry->d_type;
00094 
00095         }
00096     }
00097     closedir(directory);
00098     return found_subdir;
00099 
00100 #endif
00101 
00102 }
00103 
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Defines