mirror of
https://github.com/qgis/QGIS.git
synced 2025-10-16 00:05:45 -04:00
field proxy model to filter fields on their type (also fix #10181)
This commit is contained in:
parent
003374f77d
commit
09a9a6171a
@ -32,6 +32,7 @@
|
|||||||
%Include qgsfieldexpressionwidget.sip
|
%Include qgsfieldexpressionwidget.sip
|
||||||
%Include qgsfieldmodel.sip
|
%Include qgsfieldmodel.sip
|
||||||
%Include qgsfieldvalidator.sip
|
%Include qgsfieldvalidator.sip
|
||||||
|
%Include qgsfieldproxymodel.sip
|
||||||
%Include qgsfiledropedit.sip
|
%Include qgsfiledropedit.sip
|
||||||
%Include qgsfilterlineedit.sip
|
%Include qgsfilterlineedit.sip
|
||||||
%Include qgsformannotationitem.sip
|
%Include qgsformannotationitem.sip
|
||||||
|
@ -19,6 +19,12 @@ class QgsFieldComboBox : QComboBox
|
|||||||
*/
|
*/
|
||||||
explicit QgsFieldComboBox( QWidget *parent /TransferThis/ = 0 );
|
explicit QgsFieldComboBox( QWidget *parent /TransferThis/ = 0 );
|
||||||
|
|
||||||
|
//! setFilters allows fitering according to the type of field
|
||||||
|
void setFilters( QgsFieldProxyModel::Filters filters );
|
||||||
|
|
||||||
|
//! currently used filter on list of fields
|
||||||
|
QgsFieldProxyModel::Filters filters();
|
||||||
|
|
||||||
//! return the currently selected field
|
//! return the currently selected field
|
||||||
QString currentField();
|
QString currentField();
|
||||||
|
|
||||||
|
@ -14,12 +14,18 @@ class QgsFieldExpressionWidget : QWidget
|
|||||||
//! define the title used in the expression dialog
|
//! define the title used in the expression dialog
|
||||||
void setExpressionDialogTitle( QString title );
|
void setExpressionDialogTitle( QString title );
|
||||||
|
|
||||||
//! set the geometry calculator used in the expression dialog
|
//! setFilters allows fitering according to the type of field
|
||||||
void setGeomCalculator( const QgsDistanceArea &da );
|
void setFilters( QgsFieldProxyModel::Filters filters );
|
||||||
|
|
||||||
|
//! currently used filter on list of fields
|
||||||
|
QgsFieldProxyModel::Filters filters();
|
||||||
|
|
||||||
//! return the title used for the expression dialog
|
//! return the title used for the expression dialog
|
||||||
const QString expressionDialogTitle();
|
const QString expressionDialogTitle();
|
||||||
|
|
||||||
|
//! set the geometry calculator used in the expression dialog
|
||||||
|
void setGeomCalculator( const QgsDistanceArea &da );
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief currentField returns the currently selected field or expression if allowed
|
* @brief currentField returns the currently selected field or expression if allowed
|
||||||
* @param isExpression determines if the string returned is the name of a field or an expression
|
* @param isExpression determines if the string returned is the name of a field or an expression
|
||||||
|
@ -18,7 +18,8 @@ class QgsFieldModel : QAbstractItemModel
|
|||||||
FieldIndexRole = 34, /* return field index if index corresponds to a field */
|
FieldIndexRole = 34, /* return field index if index corresponds to a field */
|
||||||
ExpressionRole = 35, /* return field name or expression */
|
ExpressionRole = 35, /* return field name or expression */
|
||||||
IsExpressionRole = 36, /* return if index corresponds to an expression */
|
IsExpressionRole = 36, /* return if index corresponds to an expression */
|
||||||
ExpressionValidityRole = 37 /* return if expression is valid or not */
|
ExpressionValidityRole = 37, /* return if expression is valid or not */
|
||||||
|
FieldTypeRole = 38 /* return the field type (if a field, return QVariant if expression) */
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
47
python/gui/qgsfieldproxymodel.sip
Normal file
47
python/gui/qgsfieldproxymodel.sip
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
/**
|
||||||
|
* @brief The QgsMapLayerProxModel class provides an easy to use model to display the list of layers in widgets.
|
||||||
|
* @note added in 2.3
|
||||||
|
*/
|
||||||
|
class QgsFieldProxyModel : QSortFilterProxyModel
|
||||||
|
{
|
||||||
|
|
||||||
|
%TypeHeaderCode
|
||||||
|
#include "qgsfieldproxymodel.h"
|
||||||
|
%End
|
||||||
|
|
||||||
|
public:
|
||||||
|
enum Filter
|
||||||
|
{
|
||||||
|
String = 1,
|
||||||
|
Int = 2,
|
||||||
|
LongLong = 4,
|
||||||
|
Double = 8,
|
||||||
|
Numeric = 14,
|
||||||
|
Date = 16,
|
||||||
|
All = 31
|
||||||
|
};
|
||||||
|
typedef QFlags<QgsFieldProxyModel::Filter> Filters;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QgsFieldProxModel creates a proxy model with a QgsFieldModel as source model.
|
||||||
|
* It can be used to filter the fields based on their types.
|
||||||
|
*/
|
||||||
|
explicit QgsFieldProxyModel( QObject *parent /TransferThis/ = 0 );
|
||||||
|
|
||||||
|
//! sourceFieldModel returns the QgsFieldModel used in this QSortFilterProxyModel
|
||||||
|
QgsFieldModel* sourceFieldModel() ;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief setFilters set flags that affect how fields are filtered
|
||||||
|
* @param filters are Filter flags
|
||||||
|
* @note added in 2.3
|
||||||
|
*/
|
||||||
|
QgsFieldProxyModel* setFilters( Filters filters );
|
||||||
|
const Filters& filters() const ;
|
||||||
|
|
||||||
|
// QSortFilterProxyModel interface
|
||||||
|
public:
|
||||||
|
bool filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const;
|
||||||
|
bool lessThan( const QModelIndex &left, const QModelIndex &right ) const;
|
||||||
|
};
|
||||||
|
|
@ -92,6 +92,7 @@ qgsfieldcombobox.cpp
|
|||||||
qgsfieldexpressionwidget.cpp
|
qgsfieldexpressionwidget.cpp
|
||||||
qgsfieldmodel.cpp
|
qgsfieldmodel.cpp
|
||||||
qgsfieldvalidator.cpp
|
qgsfieldvalidator.cpp
|
||||||
|
qgsfieldproxymodel.cpp
|
||||||
qgsfiledropedit.cpp
|
qgsfiledropedit.cpp
|
||||||
qgsfilterlineedit.cpp
|
qgsfilterlineedit.cpp
|
||||||
qgsformannotationitem.cpp
|
qgsformannotationitem.cpp
|
||||||
@ -238,6 +239,7 @@ qgsfieldcombobox.h
|
|||||||
qgsfieldexpressionwidget.h
|
qgsfieldexpressionwidget.h
|
||||||
qgsfieldmodel.h
|
qgsfieldmodel.h
|
||||||
qgsfieldvalidator.h
|
qgsfieldvalidator.h
|
||||||
|
qgsfieldproxymodel.h
|
||||||
qgsfilterlineedit.h
|
qgsfilterlineedit.h
|
||||||
qgsformannotationitem.h
|
qgsformannotationitem.h
|
||||||
qgsgenericprojectionselector.h
|
qgsgenericprojectionselector.h
|
||||||
@ -310,6 +312,7 @@ qgsfieldcombobox.h
|
|||||||
qgsfieldexpressionwidget.h
|
qgsfieldexpressionwidget.h
|
||||||
qgsfieldmodel.h
|
qgsfieldmodel.h
|
||||||
qgsfieldvalidator.h
|
qgsfieldvalidator.h
|
||||||
|
qgsfieldproxymodel.h
|
||||||
qgsfiledropedit.h
|
qgsfiledropedit.h
|
||||||
qgsfilterlineedit.h
|
qgsfilterlineedit.h
|
||||||
qgsgenericprojectionselector.h
|
qgsgenericprojectionselector.h
|
||||||
|
@ -14,18 +14,24 @@
|
|||||||
***************************************************************************/
|
***************************************************************************/
|
||||||
|
|
||||||
#include "qgsfieldcombobox.h"
|
#include "qgsfieldcombobox.h"
|
||||||
#include "qgsfieldmodel.h"
|
#include "qgsfieldproxymodel.h"
|
||||||
#include "qgsmaplayer.h"
|
#include "qgsmaplayer.h"
|
||||||
|
#include "qgsvectorlayer.h"
|
||||||
|
|
||||||
QgsFieldComboBox::QgsFieldComboBox( QWidget *parent ) :
|
QgsFieldComboBox::QgsFieldComboBox( QWidget *parent ) :
|
||||||
QComboBox( parent )
|
QComboBox( parent )
|
||||||
{
|
{
|
||||||
mFieldModel = new QgsFieldModel( this );
|
mFieldProxyModel = new QgsFieldProxyModel( this );
|
||||||
setModel( mFieldModel );
|
setModel( mFieldProxyModel );
|
||||||
|
|
||||||
connect( this, SIGNAL( currentIndexChanged( int ) ), this, SLOT( indexChanged( int ) ) );
|
connect( this, SIGNAL( currentIndexChanged( int ) ), this, SLOT( indexChanged( int ) ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void QgsFieldComboBox::setFilters( QgsFieldProxyModel::Filters filters )
|
||||||
|
{
|
||||||
|
mFieldProxyModel->setFilters( filters );
|
||||||
|
}
|
||||||
|
|
||||||
void QgsFieldComboBox::setLayer( QgsMapLayer *layer )
|
void QgsFieldComboBox::setLayer( QgsMapLayer *layer )
|
||||||
{
|
{
|
||||||
QgsVectorLayer* vl = dynamic_cast<QgsVectorLayer*>( layer );
|
QgsVectorLayer* vl = dynamic_cast<QgsVectorLayer*>( layer );
|
||||||
@ -37,38 +43,46 @@ void QgsFieldComboBox::setLayer( QgsMapLayer *layer )
|
|||||||
|
|
||||||
void QgsFieldComboBox::setLayer( QgsVectorLayer *layer )
|
void QgsFieldComboBox::setLayer( QgsVectorLayer *layer )
|
||||||
{
|
{
|
||||||
mFieldModel->setLayer( layer );
|
mFieldProxyModel->sourceFieldModel()->setLayer( layer );
|
||||||
}
|
}
|
||||||
|
|
||||||
QgsVectorLayer *QgsFieldComboBox::layer()
|
QgsVectorLayer *QgsFieldComboBox::layer()
|
||||||
{
|
{
|
||||||
return mFieldModel->layer();
|
return mFieldProxyModel->sourceFieldModel()->layer();
|
||||||
}
|
}
|
||||||
|
|
||||||
void QgsFieldComboBox::setField( QString fieldName )
|
void QgsFieldComboBox::setField( QString fieldName )
|
||||||
{
|
{
|
||||||
QModelIndex idx = mFieldModel->indexFromName( fieldName );
|
QModelIndex idx = mFieldProxyModel->sourceFieldModel()->indexFromName( fieldName );
|
||||||
if ( idx.isValid() )
|
if ( idx.isValid() )
|
||||||
{
|
{
|
||||||
setCurrentIndex( idx.row() );
|
QModelIndex proxyIdx = mFieldProxyModel->mapFromSource( idx );
|
||||||
}
|
if ( proxyIdx.isValid() )
|
||||||
else
|
|
||||||
{
|
{
|
||||||
setCurrentIndex( -1 );
|
setCurrentIndex( idx.row() );
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
setCurrentIndex( -1 );
|
||||||
|
}
|
||||||
|
|
||||||
QString QgsFieldComboBox::currentField()
|
QString QgsFieldComboBox::currentField()
|
||||||
{
|
{
|
||||||
int i = currentIndex();
|
int i = currentIndex();
|
||||||
|
|
||||||
const QModelIndex index = mFieldModel->index( i, 0 );
|
const QModelIndex proxyIndex = mFieldProxyModel->index( i, 0 );
|
||||||
|
if ( !proxyIndex.isValid() )
|
||||||
|
{
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
|
||||||
|
const QModelIndex index = mFieldProxyModel->mapToSource( proxyIndex );
|
||||||
if ( !index.isValid() )
|
if ( !index.isValid() )
|
||||||
{
|
{
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
QString name = mFieldModel->data( index, QgsFieldModel::FieldNameRole ).toString();
|
QString name = mFieldProxyModel->data( index, QgsFieldModel::FieldNameRole ).toString();
|
||||||
return name;
|
return name;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -18,7 +18,8 @@
|
|||||||
|
|
||||||
#include <QComboBox>
|
#include <QComboBox>
|
||||||
|
|
||||||
class QgsFieldModel;
|
#include "qgsfieldproxymodel.h"
|
||||||
|
|
||||||
class QgsMapLayer;
|
class QgsMapLayer;
|
||||||
class QgsVectorLayer;
|
class QgsVectorLayer;
|
||||||
|
|
||||||
@ -32,6 +33,8 @@ class QgsVectorLayer;
|
|||||||
class GUI_EXPORT QgsFieldComboBox : public QComboBox
|
class GUI_EXPORT QgsFieldComboBox : public QComboBox
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
Q_PROPERTY( QgsFieldProxyModel::Filters filters READ filters WRITE setFilters )
|
||||||
|
|
||||||
public:
|
public:
|
||||||
/**
|
/**
|
||||||
* @brief QgsFieldComboBox creates a combo box to display the fields of a layer.
|
* @brief QgsFieldComboBox creates a combo box to display the fields of a layer.
|
||||||
@ -39,6 +42,12 @@ class GUI_EXPORT QgsFieldComboBox : public QComboBox
|
|||||||
*/
|
*/
|
||||||
explicit QgsFieldComboBox( QWidget *parent = 0 );
|
explicit QgsFieldComboBox( QWidget *parent = 0 );
|
||||||
|
|
||||||
|
//! setFilters allows fitering according to the type of field
|
||||||
|
void setFilters( QgsFieldProxyModel::Filters filters );
|
||||||
|
|
||||||
|
//! currently used filter on list of fields
|
||||||
|
QgsFieldProxyModel::Filters filters() { return mFieldProxyModel->filters(); }
|
||||||
|
|
||||||
//! return the currently selected field
|
//! return the currently selected field
|
||||||
QString currentField();
|
QString currentField();
|
||||||
|
|
||||||
@ -63,7 +72,7 @@ class GUI_EXPORT QgsFieldComboBox : public QComboBox
|
|||||||
void indexChanged( int i );
|
void indexChanged( int i );
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QgsFieldModel* mFieldModel;
|
QgsFieldProxyModel* mFieldProxyModel;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // QGSFIELDCOMBOBOX_H
|
#endif // QGSFIELDCOMBOBOX_H
|
||||||
|
@ -19,7 +19,7 @@
|
|||||||
#include "qgsapplication.h"
|
#include "qgsapplication.h"
|
||||||
#include "qgsfieldexpressionwidget.h"
|
#include "qgsfieldexpressionwidget.h"
|
||||||
#include "qgsexpressionbuilderdialog.h"
|
#include "qgsexpressionbuilderdialog.h"
|
||||||
#include "qgsfieldmodel.h"
|
#include "qgsfieldproxymodel.h"
|
||||||
#include "qgsdistancearea.h"
|
#include "qgsdistancearea.h"
|
||||||
|
|
||||||
QgsFieldExpressionWidget::QgsFieldExpressionWidget( QWidget *parent )
|
QgsFieldExpressionWidget::QgsFieldExpressionWidget( QWidget *parent )
|
||||||
@ -32,9 +32,9 @@ QgsFieldExpressionWidget::QgsFieldExpressionWidget( QWidget *parent )
|
|||||||
mCombo = new QComboBox( this );
|
mCombo = new QComboBox( this );
|
||||||
mCombo->setEditable( true );
|
mCombo->setEditable( true );
|
||||||
mCombo->setSizePolicy( QSizePolicy::MinimumExpanding, QSizePolicy::Minimum );
|
mCombo->setSizePolicy( QSizePolicy::MinimumExpanding, QSizePolicy::Minimum );
|
||||||
mFieldModel = new QgsFieldModel( mCombo );
|
mFieldProxyModel = new QgsFieldProxyModel( mCombo );
|
||||||
mFieldModel->setAllowExpression( true );
|
mFieldProxyModel->sourceFieldModel()->setAllowExpression( true );
|
||||||
mCombo->setModel( mFieldModel );
|
mCombo->setModel( mFieldProxyModel );
|
||||||
|
|
||||||
mButton = new QToolButton( this );
|
mButton = new QToolButton( this );
|
||||||
mButton->setSizePolicy( QSizePolicy::Minimum, QSizePolicy::Minimum );
|
mButton->setSizePolicy( QSizePolicy::Minimum, QSizePolicy::Minimum );
|
||||||
@ -59,6 +59,11 @@ void QgsFieldExpressionWidget::setExpressionDialogTitle( QString title )
|
|||||||
mExpressionDialogTitle = title;
|
mExpressionDialogTitle = title;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void QgsFieldExpressionWidget::setFilters( QgsFieldProxyModel::Filters filters )
|
||||||
|
{
|
||||||
|
mFieldProxyModel->setFilters( filters );
|
||||||
|
}
|
||||||
|
|
||||||
void QgsFieldExpressionWidget::setGeomCalculator( const QgsDistanceArea &da )
|
void QgsFieldExpressionWidget::setGeomCalculator( const QgsDistanceArea &da )
|
||||||
{
|
{
|
||||||
mDa = QSharedPointer<const QgsDistanceArea>( new QgsDistanceArea( da ) );
|
mDa = QSharedPointer<const QgsDistanceArea>( new QgsDistanceArea( da ) );
|
||||||
@ -76,27 +81,28 @@ QString QgsFieldExpressionWidget::currentField( bool *isExpression , bool *isVal
|
|||||||
}
|
}
|
||||||
|
|
||||||
int i = mCombo->currentIndex();
|
int i = mCombo->currentIndex();
|
||||||
const QModelIndex index = mFieldModel->index( i, 0 );
|
const QModelIndex proxyIndex = mFieldProxyModel->index( i, 0 );
|
||||||
if ( !index.isValid() )
|
if ( !proxyIndex.isValid() )
|
||||||
{
|
return "";
|
||||||
|
const QModelIndex index = mFieldProxyModel->mapToSource( proxyIndex );
|
||||||
|
if ( !index.isValid() )
|
||||||
return "";
|
return "";
|
||||||
}
|
|
||||||
|
|
||||||
if ( isExpression )
|
if ( isExpression )
|
||||||
{
|
{
|
||||||
*isExpression = mFieldModel->data( index, QgsFieldModel::IsExpressionRole ).toBool();
|
*isExpression = mFieldProxyModel->data( index, QgsFieldModel::IsExpressionRole ).toBool();
|
||||||
}
|
}
|
||||||
if ( isValid )
|
if ( isValid )
|
||||||
{
|
{
|
||||||
*isValid = mFieldModel->data( index, QgsFieldModel::ExpressionValidityRole ).toBool();
|
*isValid = mFieldProxyModel->data( index, QgsFieldModel::ExpressionValidityRole ).toBool();
|
||||||
}
|
}
|
||||||
QString expression = mFieldModel->data( index, QgsFieldModel::ExpressionRole ).toString();
|
QString expression = mFieldProxyModel->data( index, QgsFieldModel::ExpressionRole ).toString();
|
||||||
return expression;
|
return expression;
|
||||||
}
|
}
|
||||||
|
|
||||||
QgsVectorLayer *QgsFieldExpressionWidget::layer()
|
QgsVectorLayer *QgsFieldExpressionWidget::layer()
|
||||||
{
|
{
|
||||||
return mFieldModel->layer();
|
return mFieldProxyModel->sourceFieldModel()->layer();
|
||||||
}
|
}
|
||||||
|
|
||||||
void QgsFieldExpressionWidget::setLayer( QgsMapLayer *layer )
|
void QgsFieldExpressionWidget::setLayer( QgsMapLayer *layer )
|
||||||
@ -110,7 +116,7 @@ void QgsFieldExpressionWidget::setLayer( QgsMapLayer *layer )
|
|||||||
|
|
||||||
void QgsFieldExpressionWidget::setLayer( QgsVectorLayer *layer )
|
void QgsFieldExpressionWidget::setLayer( QgsVectorLayer *layer )
|
||||||
{
|
{
|
||||||
mFieldModel->setLayer( layer );
|
mFieldProxyModel->sourceFieldModel()->setLayer( layer );
|
||||||
}
|
}
|
||||||
|
|
||||||
void QgsFieldExpressionWidget::setField( const QString fieldName )
|
void QgsFieldExpressionWidget::setField( const QString fieldName )
|
||||||
@ -118,13 +124,16 @@ void QgsFieldExpressionWidget::setField( const QString fieldName )
|
|||||||
if ( fieldName.isEmpty() )
|
if ( fieldName.isEmpty() )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
QModelIndex idx = mFieldModel->indexFromName( fieldName );
|
QModelIndex idx = mFieldProxyModel->sourceFieldModel()->indexFromName( fieldName );
|
||||||
if ( !idx.isValid() )
|
if ( !idx.isValid() )
|
||||||
{
|
{
|
||||||
// new expression
|
// new expression
|
||||||
idx = mFieldModel->setExpression( fieldName );
|
idx = mFieldProxyModel->sourceFieldModel()->setExpression( fieldName );
|
||||||
}
|
}
|
||||||
mCombo->setCurrentIndex( idx.row() );
|
|
||||||
|
QModelIndex proxyIndex = mFieldProxyModel->mapFromSource( idx );
|
||||||
|
|
||||||
|
mCombo->setCurrentIndex( proxyIndex.row() );
|
||||||
|
|
||||||
currentFieldChanged();
|
currentFieldChanged();
|
||||||
}
|
}
|
||||||
@ -159,7 +168,7 @@ void QgsFieldExpressionWidget::expressionEdited( const QString expression )
|
|||||||
void QgsFieldExpressionWidget::expressionEditingFinished()
|
void QgsFieldExpressionWidget::expressionEditingFinished()
|
||||||
{
|
{
|
||||||
const QString expression = mCombo->lineEdit()->text();
|
const QString expression = mCombo->lineEdit()->text();
|
||||||
QModelIndex idx = mFieldModel->setExpression( expression );
|
QModelIndex idx = mFieldProxyModel->sourceFieldModel()->setExpression( expression );
|
||||||
mCombo->setCurrentIndex( idx.row() );
|
mCombo->setCurrentIndex( idx.row() );
|
||||||
currentFieldChanged();
|
currentFieldChanged();
|
||||||
}
|
}
|
||||||
|
@ -23,10 +23,10 @@
|
|||||||
#include <QColor>
|
#include <QColor>
|
||||||
|
|
||||||
#include "qgsdistancearea.h"
|
#include "qgsdistancearea.h"
|
||||||
|
#include "qgsfieldproxymodel.h"
|
||||||
|
|
||||||
class QgsMapLayer;
|
class QgsMapLayer;
|
||||||
class QgsVectorLayer;
|
class QgsVectorLayer;
|
||||||
class QgsFieldModel;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -41,6 +41,7 @@ class GUI_EXPORT QgsFieldExpressionWidget : public QWidget
|
|||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
Q_PROPERTY( QString expressionDialogTitle READ expressionDialogTitle WRITE setExpressionDialogTitle )
|
Q_PROPERTY( QString expressionDialogTitle READ expressionDialogTitle WRITE setExpressionDialogTitle )
|
||||||
|
Q_PROPERTY( QgsFieldProxyModel::Filters filters READ filters WRITE setFilters )
|
||||||
|
|
||||||
public:
|
public:
|
||||||
/**
|
/**
|
||||||
@ -54,6 +55,12 @@ class GUI_EXPORT QgsFieldExpressionWidget : public QWidget
|
|||||||
//! return the title used for the expression dialog
|
//! return the title used for the expression dialog
|
||||||
const QString expressionDialogTitle() { return mExpressionDialogTitle; }
|
const QString expressionDialogTitle() { return mExpressionDialogTitle; }
|
||||||
|
|
||||||
|
//! setFilters allows fitering according to the type of field
|
||||||
|
void setFilters( QgsFieldProxyModel::Filters filters );
|
||||||
|
|
||||||
|
//! currently used filter on list of fields
|
||||||
|
QgsFieldProxyModel::Filters filters() { return mFieldProxyModel->filters(); }
|
||||||
|
|
||||||
//! set the geometry calculator used in the expression dialog
|
//! set the geometry calculator used in the expression dialog
|
||||||
void setGeomCalculator( const QgsDistanceArea &da );
|
void setGeomCalculator( const QgsDistanceArea &da );
|
||||||
|
|
||||||
@ -111,7 +118,7 @@ class GUI_EXPORT QgsFieldExpressionWidget : public QWidget
|
|||||||
private:
|
private:
|
||||||
QComboBox* mCombo;
|
QComboBox* mCombo;
|
||||||
QToolButton* mButton;
|
QToolButton* mButton;
|
||||||
QgsFieldModel* mFieldModel;
|
QgsFieldProxyModel* mFieldProxyModel;
|
||||||
QString mExpressionDialogTitle;
|
QString mExpressionDialogTitle;
|
||||||
QSharedPointer<const QgsDistanceArea> mDa;
|
QSharedPointer<const QgsDistanceArea> mDa;
|
||||||
};
|
};
|
||||||
|
@ -212,6 +212,15 @@ QVariant QgsFieldModel::data( const QModelIndex &index, int role ) const
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case FieldTypeRole:
|
||||||
|
{
|
||||||
|
if ( exprIdx < 0 )
|
||||||
|
{
|
||||||
|
QgsField field = mFields[index.internalId()];
|
||||||
|
return ( int )field.type();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
case Qt::DisplayRole:
|
case Qt::DisplayRole:
|
||||||
case Qt::EditRole:
|
case Qt::EditRole:
|
||||||
{
|
{
|
||||||
|
@ -38,7 +38,8 @@ class GUI_EXPORT QgsFieldModel : public QAbstractItemModel
|
|||||||
FieldIndexRole = Qt::UserRole + 2, /* return field index if index corresponds to a field */
|
FieldIndexRole = Qt::UserRole + 2, /* return field index if index corresponds to a field */
|
||||||
ExpressionRole = Qt::UserRole + 3, /* return field name or expression */
|
ExpressionRole = Qt::UserRole + 3, /* return field name or expression */
|
||||||
IsExpressionRole = Qt::UserRole + 4, /* return if index corresponds to an expression */
|
IsExpressionRole = Qt::UserRole + 4, /* return if index corresponds to an expression */
|
||||||
ExpressionValidityRole = Qt::UserRole + 5 /* return if expression is valid or not */
|
ExpressionValidityRole = Qt::UserRole + 5, /* return if expression is valid or not */
|
||||||
|
FieldTypeRole = Qt::UserRole + 6 /* return the field type (if a field, return QVariant if expression) */
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
74
src/gui/qgsfieldproxymodel.cpp
Normal file
74
src/gui/qgsfieldproxymodel.cpp
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
/***************************************************************************
|
||||||
|
qgsfieldproxymodel.cpp
|
||||||
|
--------------------------------------
|
||||||
|
Date : 01.04.2014
|
||||||
|
Copyright : (C) 2014 Denis Rouzaud
|
||||||
|
Email : denis.rouzaud@gmail.com
|
||||||
|
***************************************************************************
|
||||||
|
* *
|
||||||
|
* This program is free software; you can redistribute it and/or modify *
|
||||||
|
* it under the terms of the GNU General Public License as published by *
|
||||||
|
* the Free Software Foundation; either version 2 of the License, or *
|
||||||
|
* (at your option) any later version. *
|
||||||
|
* *
|
||||||
|
***************************************************************************/
|
||||||
|
|
||||||
|
#include "qgsfieldproxymodel.h"
|
||||||
|
#include "qgsfieldmodel.h"
|
||||||
|
#include "qgsvectorlayer.h"
|
||||||
|
|
||||||
|
QgsFieldProxyModel::QgsFieldProxyModel( QObject *parent )
|
||||||
|
: QSortFilterProxyModel( parent )
|
||||||
|
, mFilters( All )
|
||||||
|
, mModel( new QgsFieldModel( this ) )
|
||||||
|
{
|
||||||
|
setSourceModel( mModel );
|
||||||
|
}
|
||||||
|
|
||||||
|
QgsFieldProxyModel *QgsFieldProxyModel::setFilters( Filters filters )
|
||||||
|
{
|
||||||
|
mFilters = filters;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool QgsFieldProxyModel::filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const
|
||||||
|
{
|
||||||
|
if ( mFilters.testFlag( All ) )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
QModelIndex index = sourceModel()->index( source_row, 0, source_parent );
|
||||||
|
QVariant typeVar = sourceModel()->data( index, QgsFieldModel::FieldTypeRole );
|
||||||
|
|
||||||
|
// if expression, consider valid
|
||||||
|
if ( typeVar.isNull() )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
bool ok;
|
||||||
|
QVariant::Type type = ( QVariant::Type )typeVar.toInt( &ok );
|
||||||
|
if ( !ok )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (( mFilters.testFlag( String ) && type == QVariant::String ) ||
|
||||||
|
( mFilters.testFlag( LongLong ) && type == QVariant::LongLong ) ||
|
||||||
|
( mFilters.testFlag( Int ) && type == QVariant::Int ) ||
|
||||||
|
( mFilters.testFlag( Double ) && type == QVariant::Double ) ||
|
||||||
|
( mFilters.testFlag( Date ) && type == QVariant::Date ) )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool QgsFieldProxyModel::lessThan( const QModelIndex &left, const QModelIndex &right ) const
|
||||||
|
{
|
||||||
|
// order is field order, then expressions
|
||||||
|
bool lok, rok;
|
||||||
|
int leftId = sourceModel()->data( left, QgsFieldModel::FieldIndexRole ).toInt( &lok );
|
||||||
|
int rightId = sourceModel()->data( right, QgsFieldModel::FieldIndexRole ).toInt( &rok );
|
||||||
|
|
||||||
|
if ( !lok )
|
||||||
|
return false;
|
||||||
|
if ( !rok )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return leftId < rightId;
|
||||||
|
}
|
72
src/gui/qgsfieldproxymodel.h
Normal file
72
src/gui/qgsfieldproxymodel.h
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
/***************************************************************************
|
||||||
|
qgsfieldproxymodel.h
|
||||||
|
--------------------------------------
|
||||||
|
Date : 01.04.2014
|
||||||
|
Copyright : (C) 2014 Denis Rouzaud
|
||||||
|
Email : denis.rouzaud@gmail.com
|
||||||
|
***************************************************************************
|
||||||
|
* *
|
||||||
|
* This program is free software; you can redistribute it and/or modify *
|
||||||
|
* it under the terms of the GNU General Public License as published by *
|
||||||
|
* the Free Software Foundation; either version 2 of the License, or *
|
||||||
|
* (at your option) any later version. *
|
||||||
|
* *
|
||||||
|
***************************************************************************/
|
||||||
|
|
||||||
|
#ifndef QGSFIELDPROXYMODEL_H
|
||||||
|
#define QGSFIELDPROXYMODEL_H
|
||||||
|
|
||||||
|
#include <QSortFilterProxyModel>
|
||||||
|
|
||||||
|
#include "qgsfieldmodel.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief The QgsFieldProxyModel class provides an easy to use model to display the list of fields of a layer.
|
||||||
|
* @note added in 2.3
|
||||||
|
*/
|
||||||
|
class GUI_EXPORT QgsFieldProxyModel : public QSortFilterProxyModel
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
enum Filter
|
||||||
|
{
|
||||||
|
String = 1,
|
||||||
|
Int = 2,
|
||||||
|
LongLong = 4,
|
||||||
|
Double = 8,
|
||||||
|
Numeric = Int | LongLong | Double,
|
||||||
|
Date = 16,
|
||||||
|
All = Numeric | Date | String
|
||||||
|
};
|
||||||
|
Q_DECLARE_FLAGS( Filters, Filter )
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QgsFieldProxModel creates a proxy model with a QgsFieldModel as source model.
|
||||||
|
* It can be used to filter the fields based on their types.
|
||||||
|
*/
|
||||||
|
explicit QgsFieldProxyModel( QObject *parent = 0 );
|
||||||
|
|
||||||
|
//! sourceFieldModel returns the QgsFieldModel used in this QSortFilterProxyModel
|
||||||
|
QgsFieldModel* sourceFieldModel() { return mModel; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief setFilters set flags that affect how fields are filtered
|
||||||
|
* @param filters are Filter flags
|
||||||
|
* @note added in 2.3
|
||||||
|
*/
|
||||||
|
QgsFieldProxyModel* setFilters( Filters filters );
|
||||||
|
const Filters& filters() const { return mFilters; }
|
||||||
|
|
||||||
|
private:
|
||||||
|
Filters mFilters;
|
||||||
|
QgsFieldModel* mModel;
|
||||||
|
|
||||||
|
// QSortFilterProxyModel interface
|
||||||
|
public:
|
||||||
|
bool filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const;
|
||||||
|
bool lessThan( const QModelIndex &left, const QModelIndex &right ) const;
|
||||||
|
};
|
||||||
|
|
||||||
|
Q_DECLARE_OPERATORS_FOR_FLAGS( QgsFieldProxyModel::Filters )
|
||||||
|
|
||||||
|
#endif // QGSFIELDPROXYMODEL_H
|
@ -358,6 +358,7 @@ QgsGraduatedSymbolRendererV2Widget::QgsGraduatedSymbolRendererV2Widget( QgsVecto
|
|||||||
// setup user interface
|
// setup user interface
|
||||||
setupUi( this );
|
setupUi( this );
|
||||||
|
|
||||||
|
mExpressionWidget->setFilters( QgsFieldProxyModel::Numeric | QgsFieldProxyModel::Date );
|
||||||
mExpressionWidget->setLayer( mLayer );
|
mExpressionWidget->setLayer( mLayer );
|
||||||
|
|
||||||
cboGraduatedColorRamp->populate( mStyle );
|
cboGraduatedColorRamp->populate( mStyle );
|
||||||
|
Loading…
x
Reference in New Issue
Block a user