QFileSystemModel and QTreeView showing dirs only. How to hide expansion marks against the empty dirs?

StackOverflow https://stackoverflow.com/questions/14545711

Question

I'm building somewhat like standard file explorer - left pane is for folders tree, and the right one to display files within selected folder.

QTreeView with QFileSystemModel is used to display folders. Model's filter is set to QDir::Dirs | QDir::NoDotAndDotDot to list dirs only, no files. I want to display expansion marks only against the folders with subfolders, i. e. if some dir is empty or contains only files, it shouldn't be expandable. But instead, tree view keeps expansion marks against the empty dir. And that's the question: how to hide them?

I've searched the solution here, in the google, in the QT examples - no success. While the question, I think, is very easy to answer. The only solution I came for at the moment is to subclass QAbstractItemModel. That's pain.

QT 4.8, QT Creator, C++.

Here's code to demonstrate:

#include <QApplication>

#include <QFileSystemModel>
#include <QTreeView>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);

    QTreeView w;

    QFileSystemModel m;
    m.setFilter(QDir::Dirs | QDir::NoDotAndDotDot);
    m.setRootPath("C:\\");

    w.setModel(&m);
    w.setRootIndex(m.index(m.rootPath()));
    w.hideColumn(3);
    w.hideColumn(2);
    w.hideColumn(1);

    w.show();

    return a.exec();
}
Was it helpful?

Solution

I have solved this issue using

QFileSystemModel::fetchMore

on each QModelIndex of the current level. To know if a folder has been loaded into the model, you can use the signal

void directoryLoaded ( const QString & path )

OTHER TIPS

Simplest way: juste implements hasChildren like that:

/*!
 * Returns true if parent has any children and haven't the Qt::ItemNeverHasChildren flag set;
 * otherwise returns false.
 *
 *
 * \remarks Reimplemented to avoid empty directories to be collapsables
 *          and to implement the \c Qt::ItemNeverHasChildren flag.
 * \see     rowCount()
 * \see     child()
 *
 */
bool YourModelName::hasChildren(const QModelIndex &parent) const
{
    // return false if item cant have children
    if (parent.flags() &  Qt::ItemNeverHasChildren) {
        return false;
    }
    // return if at least one child exists
    return QDirIterator(
                filePath(parent),
                filter() | QDir::NoDotAndDotDot,
                QDirIterator::NoIteratorFlags
            ).hasNext();
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top