Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
add proxy model to filter the settings tree
  • Loading branch information
3nids committed Apr 27, 2023
1 parent 2d28f1e commit 0b8ef93
Show file tree
Hide file tree
Showing 6 changed files with 190 additions and 7 deletions.
36 changes: 36 additions & 0 deletions python/gui/auto_generated/settings/qgssettingstreemodel.sip.in
Expand Up @@ -47,6 +47,7 @@ Apply pending changes in the model to the corresponding settings




virtual QModelIndex index( int row, int column, const QModelIndex &parent ) const;

virtual QModelIndex parent( const QModelIndex &child ) const;
Expand All @@ -64,6 +65,41 @@ Apply pending changes in the model to the corresponding settings
virtual bool setData( const QModelIndex &index, const QVariant &value, int role );


};

class QgsSettingsTreeProxyModel : QSortFilterProxyModel
{
%Docstring(signature="appended")
:py:class:`QgsSettingsTreeProxyModel` allows filtering the settings tree

.. versionadded:: 3.32
%End

%TypeHeaderCode
#include "qgssettingstreemodel.h"
%End
public:
QgsSettingsTreeProxyModel( QgsSettingsTreeNode *rootNode = 0, QObject *parent = 0 );
%Docstring
Constructor
%End

void applyChanges();
%Docstring
Apply pending changes in the model to the corresponding settings
%End

public slots:
void setFilterText( const QString &filterText = QString() );
%Docstring
Sets the filter text
%End


protected:
virtual bool filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const;


};

/************************************************************************
Expand Down
10 changes: 9 additions & 1 deletion python/gui/auto_generated/settings/qgssettingstreewidget.sip.in
Expand Up @@ -11,7 +11,8 @@



class QgsSettingsTreeWidget : QWidget

class QgsSettingsTreeWidget : QWidget, QgsOptionsDialogHighlightWidget
{
%Docstring(signature="appended")
:py:class:`QgsSettingsTreeWidget` is a widget with the settings tree to visualize, search and edit settings
Expand All @@ -34,6 +35,13 @@ Constructor
Apply changes to settings value
%End

protected:
virtual bool searchText( const QString &text );

virtual bool highlightText( const QString &text );

virtual void reset();

};

/************************************************************************
Expand Down
75 changes: 75 additions & 0 deletions src/gui/settings/qgssettingstreemodel.cpp
Expand Up @@ -195,6 +195,18 @@ QgsSettingsTreeModelNodeData *QgsSettingsTreeModel::index2node( const QModelInde
return qobject_cast<QgsSettingsTreeModelNodeData *>( obj );
}

QModelIndex QgsSettingsTreeModel::node2index( QgsSettingsTreeModelNodeData *node ) const
{
if ( !node || !node->parent() )
return QModelIndex(); // this is the only root item -> invalid index

QModelIndex parentIndex = node2index( node->parent() );

int row = node->parent()->children().indexOf( node );
Q_ASSERT( row >= 0 );
return index( row, static_cast<int>( Column::Name ), parentIndex );
}


QModelIndex QgsSettingsTreeModel::index( int row, int column, const QModelIndex &parent ) const
{
Expand Down Expand Up @@ -432,3 +444,66 @@ void QgsSettingsTreeItemDelegate::setModelData( QWidget *editor, QAbstractItemMo





QgsSettingsTreeProxyModel::QgsSettingsTreeProxyModel( QgsSettingsTreeNode *rootNode, QObject *parent )
: QSortFilterProxyModel( parent )
{
mSourceModel = new QgsSettingsTreeModel( rootNode, parent );
QSortFilterProxyModel::setSourceModel( mSourceModel );
}

void QgsSettingsTreeProxyModel::setFilterText( const QString &filterText )
{
if ( filterText == mFilterText )
return;

mFilterText = filterText;
invalidateFilter();
}

bool QgsSettingsTreeProxyModel::filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const
{
QgsSettingsTreeModelNodeData *node = mSourceModel->index2node( mSourceModel->index( source_row, static_cast<int>( QgsSettingsTreeModel::Column::Name ), source_parent ) );
return nodeShown( node );
}

bool QgsSettingsTreeProxyModel::nodeShown( QgsSettingsTreeModelNodeData *node ) const
{
if ( !node )
return false;
if ( node->type() == QgsSettingsTreeModelNodeData::Type::Setting )
{
if ( node->name().contains( mFilterText, Qt::CaseInsensitive ) )
return true;

// also returns settings for which the parent nodes have a match
QModelIndex index = mSourceModel->node2index( node ).parent();
while ( ( index.isValid() ) )
{
QgsSettingsTreeModelNodeData *parentNode = mSourceModel->index2node( mSourceModel->index( index.row(), static_cast<int>( QgsSettingsTreeModel::Column::Name ), index.parent() ) );
if ( parentNode->name().contains( mFilterText, Qt::CaseInsensitive ) )
return true;

index = index.parent();
}
return false;
}
else
{
// show all children if name of node matches
if ( node->name().contains( mFilterText, Qt::CaseInsensitive ) )
return true;

const auto constChildren = node->children();
for ( QgsSettingsTreeModelNodeData *child : constChildren )
{
if ( nodeShown( child ) )
{
return true;
}
}
return false;
}
}

37 changes: 37 additions & 0 deletions src/gui/settings/qgssettingstreemodel.h
Expand Up @@ -21,6 +21,7 @@
#include "qgis_gui.h"

#include <QAbstractItemModel>
#include <QSortFilterProxyModel>
#include <QItemDelegate>

class QgsSettingsEntryBase;
Expand Down Expand Up @@ -164,6 +165,7 @@ class GUI_EXPORT QgsSettingsTreeItemDelegate : public QItemDelegate
*/
class GUI_EXPORT QgsSettingsTreeModel : public QAbstractItemModel
{
Q_OBJECT
public:

//! Columns
Expand All @@ -187,6 +189,9 @@ class GUI_EXPORT QgsSettingsTreeModel : public QAbstractItemModel
*/
QgsSettingsTreeModelNodeData *index2node( const QModelIndex &index ) const SIP_SKIP;

//! Returns the index from the settings tree node
QModelIndex node2index( QgsSettingsTreeModelNodeData *node ) const SIP_SKIP;


QModelIndex index( int row, int column, const QModelIndex &parent ) const override;
QModelIndex parent( const QModelIndex &child ) const override;
Expand All @@ -204,4 +209,36 @@ class GUI_EXPORT QgsSettingsTreeModel : public QAbstractItemModel

};

/**
* \ingroup gui
* \class QgsSettingsTreeProxyModel
* \brief QgsSettingsTreeProxyModel allows filtering the settings tree
*
* \since QGIS 3.32
*/
class GUI_EXPORT QgsSettingsTreeProxyModel : public QSortFilterProxyModel
{
Q_OBJECT
public:
//! Constructor
QgsSettingsTreeProxyModel( QgsSettingsTreeNode *rootNode = nullptr, QObject *parent = nullptr );

//! Apply pending changes in the model to the corresponding settings
void applyChanges() {mSourceModel->applyChanges();}

public slots:
//! Sets the filter text
void setFilterText( const QString &filterText = QString() );


protected:
bool filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const override;

private:
QgsSettingsTreeModel *mSourceModel = nullptr;

bool nodeShown( QgsSettingsTreeModelNodeData *node ) const;
QString mFilterText;
};

#endif // QGSSETTINGSTREEMODEL_H
24 changes: 22 additions & 2 deletions src/gui/settings/qgssettingstreewidget.cpp
Expand Up @@ -25,15 +25,18 @@

QgsSettingsTreeWidget::QgsSettingsTreeWidget( QWidget *parent )
: QWidget( parent )
, QgsOptionsDialogHighlightWidget( this )
{
setObjectName( QStringLiteral( "mSettingsTreeWidget" ) );

QVBoxLayout *mainLayout = new QVBoxLayout( this );
mainLayout->setContentsMargins( 0, 0, 0, 0 );

mTreeModel = new QgsSettingsTreeModel( QgsSettingsTree::treeRoot() );
mTreeModel = new QgsSettingsTreeProxyModel( QgsSettingsTree::treeRoot() );

mTreeView = new QTreeView( this );
mTreeView->setModel( mTreeModel );
mTreeView->setItemDelegate( new QgsSettingsTreeItemDelegate( mTreeModel, this ) );
mTreeView->setItemDelegate( new QgsSettingsTreeItemDelegate( qobject_cast<QgsSettingsTreeModel *>( mTreeModel->sourceModel() ), parent ) );
mTreeView->setSizePolicy( QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding );
mTreeView->setMinimumWidth( 400 );
mTreeView->resizeColumnToContents( 0 );
Expand All @@ -46,3 +49,20 @@ void QgsSettingsTreeWidget::applyChanges() const
mTreeModel->applyChanges();
}


bool QgsSettingsTreeWidget::searchText( const QString &text )
{
mTreeModel->setFilterText( text );
return mTreeModel->rowCount() > 0;
}

bool QgsSettingsTreeWidget::highlightText( const QString &text )
{
Q_UNUSED( text );
return true;
}

void QgsSettingsTreeWidget::reset()
{
mTreeModel->setFilterText( QString() );
}
15 changes: 11 additions & 4 deletions src/gui/settings/qgssettingstreewidget.h
Expand Up @@ -18,11 +18,12 @@

#include "qgis_gui.h"

#include "qwidget.h"
#include "qgsoptionsdialoghighlightwidget.h"


class QTreeView;

class QgsSettingsTreeModel;
class QgsSettingsTreeProxyModel;

/**
* \ingroup gui
Expand All @@ -31,7 +32,7 @@ class QgsSettingsTreeModel;
*
* \since QGIS 3.32
*/
class GUI_EXPORT QgsSettingsTreeWidget : public QWidget
class GUI_EXPORT QgsSettingsTreeWidget : public QWidget, public QgsOptionsDialogHighlightWidget
{

public:
Expand All @@ -43,9 +44,15 @@ class GUI_EXPORT QgsSettingsTreeWidget : public QWidget
void applyChanges() const;

private:
QgsSettingsTreeModel *mTreeModel = nullptr;
QgsSettingsTreeProxyModel *mTreeModel = nullptr;
QTreeView *mTreeView = nullptr;


// QgsOptionsDialogHighlightWidget interface
protected:
bool searchText( const QString &text ) override;
bool highlightText( const QString &text ) override;
void reset() override;
};

#endif // QGSSETTINGSTREEWIDGET_H

0 comments on commit 0b8ef93

Please sign in to comment.