Скрыть элементы QFileSystemModel / QTreeView с помощью индексов, используя определенное правило

#c #qt #qtreeview #qfilesystemmodel #qsortfilterproxymodel

#c #qt #qtreeview #qfilesystemmodel #qsortfilterproxymodel

Вопрос:

Я отображаю содержимое папки в моей программе Qt, используя QTreeView QFileSystemModel.

Теперь я хочу скрыть определенные элементы этого представления. Правило отображения не основано на именах файлов, поэтому я не могу использовать setNameFilters(). У меня есть простой список QModelIndex, содержащий все элементы, которые я хочу скрыть. Есть ли способ фильтрации представления, используя только этот список?

В своем исследовании я наткнулся на класс QSortFilterProxyModel, но я не мог понять, как его использовать, чтобы достичь того, чего я хочу. Любая помощь была бы оценена.

Ответ №1:

Подкласс QSortFilterProxyModel и переопределите метод filterAcceptsRow , чтобы задать логику фильтра.

Например, для фильтрации по разрешениям текущего пользователя на запись :

 class PermissionsFilterProxy: public QSortFilterProxyModel
{
public:
    PermissionsFilterProxy(QObject* parent=nullptr): QSortFilterProxyModel(parent)
    {}

    bool filterAcceptsRow(int sourceRow,
            const QModelIndex amp;sourceParent) const
    {
        QModelIndex index = sourceModel()->index(sourceRow, 0, sourceParent);
        QFileDevice::Permissions permissions = static_cast<QFileDevice::Permissions>(index.data(QFileSystemModel::FilePermissions).toInt());
        return permissions.testFlag(QFileDevice::WriteUser); // Ok if user can write
    }
};

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

    QFileSystemModel* model = new QFileSystemModel();
    model->setRootPath(".");

    QTreeView* view = new QTreeView();
    PermissionsFilterProxy* proxy = new PermissionsFilterProxy();
    proxy->setSourceModel(model);
    view->setModel(proxy);
    view->show();
    return app.exec();
}
  

Комментарии:

1. Большое вам спасибо! Это работает, но фильтр не обновляется каждый раз, когда я изменяю условия. В моем случае элементы, которые должны быть скрыты, хранятся в списке. Вы знаете, как я могу автоматически обновлять фильтры при обновлении списка?

2. Забудьте об этом, я только что выяснил. Мне просто пришлось использовать sourceModel()-> dataChanged() при изменении условий. Еще раз, большое вам спасибо!

3. Вы также можете вызвать QSortFilterProxyModel::invalidateFilter() , когда хотите изменить параметры фильтра.