From 88d3e2aa7f88454d544c8e3a960a30bac33ed21c Mon Sep 17 00:00:00 2001 From: Nyall Dawson Date: Tue, 10 May 2016 10:32:34 +1000 Subject: [PATCH] [FEATURE] Show stats for string and date fields in stats dock --- src/app/qgsstatisticalsummarydockwidget.cpp | 172 ++++++++++++++++---- src/app/qgsstatisticalsummarydockwidget.h | 9 + 2 files changed, 153 insertions(+), 28 deletions(-) diff --git a/src/app/qgsstatisticalsummarydockwidget.cpp b/src/app/qgsstatisticalsummarydockwidget.cpp index b5e93ca75ef..e23811f6e96 100644 --- a/src/app/qgsstatisticalsummarydockwidget.cpp +++ b/src/app/qgsstatisticalsummarydockwidget.cpp @@ -38,6 +38,23 @@ QList< QgsStatisticalSummary::Statistic > QgsStatisticalSummaryDockWidget::mDisp << QgsStatisticalSummary::ThirdQuartile << QgsStatisticalSummary::InterQuartileRange; +QList< QgsStringStatisticalSummary::Statistic > QgsStatisticalSummaryDockWidget::mDisplayStringStats = + QList< QgsStringStatisticalSummary::Statistic > () << QgsStringStatisticalSummary::Count + << QgsStringStatisticalSummary::CountDistinct + << QgsStringStatisticalSummary::CountMissing + << QgsStringStatisticalSummary::Min + << QgsStringStatisticalSummary::Max + << QgsStringStatisticalSummary::MinimumLength + << QgsStringStatisticalSummary::MaximumLength; + +QList< QgsDateTimeStatisticalSummary::Statistic > QgsStatisticalSummaryDockWidget::mDisplayDateTimeStats = + QList< QgsDateTimeStatisticalSummary::Statistic > () << QgsDateTimeStatisticalSummary::Count + << QgsDateTimeStatisticalSummary::CountDistinct + << QgsDateTimeStatisticalSummary::CountMissing + << QgsDateTimeStatisticalSummary::Min + << QgsDateTimeStatisticalSummary::Max + << QgsDateTimeStatisticalSummary::Range; + #define MISSING_VALUES -1 static QgsExpressionContext _getExpressionContext( const void* context ) @@ -65,7 +82,9 @@ QgsStatisticalSummaryDockWidget::QgsStatisticalSummaryDockWidget( QWidget *paren mFieldExpressionWidget->registerGetExpressionContextCallback( &_getExpressionContext, this ); mLayerComboBox->setFilters( QgsMapLayerProxyModel::VectorLayer ); - mFieldExpressionWidget->setFilters( QgsFieldProxyModel::Numeric ); + mFieldExpressionWidget->setFilters( QgsFieldProxyModel::Numeric | + QgsFieldProxyModel::String | + QgsFieldProxyModel::Date ); mLayerComboBox->setLayer( mLayerComboBox->layer( 0 ) ); mFieldExpressionWidget->setLayer( mLayerComboBox->layer( 0 ) ); @@ -113,10 +132,47 @@ void QgsStatisticalSummaryDockWidget::refreshStatistics() return; } + // non numeric field? + bool isNumeric = true; + QVariant::Type fieldType = QVariant::Double; + if ( !mFieldExpressionWidget->isExpression() ) + { + QString field = mFieldExpressionWidget->currentField(); + fieldType = mLayer->fields().field( mLayer->fields().fieldNameIndex( field ) ).type(); + if ( fieldType == QVariant::String || fieldType == QVariant::Date || fieldType == QVariant::DateTime ) + { + isNumeric = false; + } + } + + bool selectedOnly = mSelectedOnlyCheckBox->isChecked(); + + if ( isNumeric ) + { + updateNumericStatistics( selectedOnly ); + } + else + { + switch ( fieldType ) + { + case QVariant::String: + updateStringStatistics( selectedOnly ); + break; + case QVariant::Date: + case QVariant::DateTime: + updateDateTimeStatistics( selectedOnly ); + break; + default: + break; + } + } +} + +void QgsStatisticalSummaryDockWidget::updateNumericStatistics( bool selectedOnly ) +{ QString sourceFieldExp = mFieldExpressionWidget->currentField(); bool ok; - bool selectedOnly = mSelectedOnlyCheckBox->isChecked(); int missingValues = 0; QList< double > values = mLayer->getDoubleValues( sourceFieldExp, ok, selectedOnly, &missingValues ); @@ -150,38 +206,46 @@ void QgsStatisticalSummaryDockWidget::refreshStatistics() int row = 0; Q_FOREACH ( QgsStatisticalSummary::Statistic stat, statsToDisplay ) { - QTableWidgetItem* nameItem = new QTableWidgetItem( QgsStatisticalSummary::displayName( stat ) ); - nameItem->setToolTip( nameItem->text() ); - nameItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled ); - mStatisticsTable->setItem( row, 0, nameItem ); - - QTableWidgetItem* valueItem = new QTableWidgetItem(); - if ( stats.count() != 0 ) - { - valueItem->setText( QString::number( stats.statistic( stat ) ) ); - } - valueItem->setToolTip( valueItem->text() ); - valueItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled ); - mStatisticsTable->setItem( row, 1, valueItem ); - + addRow( row, QgsStatisticalSummary::displayName( stat ), + QString::number( stats.statistic( stat ) ), + stats.count() != 0 ); row++; } if ( mStatsActions.value( MISSING_VALUES )->isChecked() ) { - QTableWidgetItem* nameItem = new QTableWidgetItem( tr( "Missing (null) values" ) ); - nameItem->setToolTip( nameItem->text() ); - nameItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled ); - mStatisticsTable->setItem( row, 0, nameItem ); + addRow( row, tr( "Missing (null) values" ), + QString::number( missingValues ), + stats.count() != 0 || missingValues != 0 ); + row++; + } +} - QTableWidgetItem* valueItem = new QTableWidgetItem(); - if ( stats.count() != 0 || missingValues != 0 ) - { - valueItem->setText( QString::number( missingValues ) ); - } - valueItem->setToolTip( valueItem->text() ); - valueItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled ); - mStatisticsTable->setItem( row, 1, valueItem ); +void QgsStatisticalSummaryDockWidget::updateStringStatistics( bool selectedOnly ) +{ + QString field = mFieldExpressionWidget->currentField(); + + bool ok; + QVariantList values = mLayer->getValues( field, ok, selectedOnly ); + + if ( ! ok ) + { + return; + } + + QgsStringStatisticalSummary stats; + stats.setStatistics( QgsStringStatisticalSummary::All ); + stats.calculateFromVariants( values ); + + mStatisticsTable->setRowCount( mDisplayStringStats.count() ); + mStatisticsTable->setColumnCount( 2 ); + + int row = 0; + Q_FOREACH ( QgsStringStatisticalSummary::Statistic stat, mDisplayStringStats ) + { + addRow( row, QgsStringStatisticalSummary::displayName( stat ), + stats.statistic( stat ).toString(), + stats.count() != 0 ); row++; } } @@ -244,3 +308,55 @@ void QgsStatisticalSummaryDockWidget::layerSelectionChanged() if ( mSelectedOnlyCheckBox->isChecked() ) refreshStatistics(); } + +void QgsStatisticalSummaryDockWidget::updateDateTimeStatistics( bool selectedOnly ) +{ + QString field = mFieldExpressionWidget->currentField(); + + bool ok; + QVariantList values = mLayer->getValues( field, ok, selectedOnly ); + + if ( ! ok ) + { + return; + } + + QgsDateTimeStatisticalSummary stats; + stats.setStatistics( QgsDateTimeStatisticalSummary::All ); + stats.calculate( values ); + + mStatisticsTable->setRowCount( mDisplayDateTimeStats.count() ); + mStatisticsTable->setColumnCount( 2 ); + + int row = 0; + Q_FOREACH ( QgsDateTimeStatisticalSummary::Statistic stat, mDisplayDateTimeStats ) + { + QString value = ( stat == QgsDateTimeStatisticalSummary::Range + ? tr( "%1 seconds" ).arg( stats.range().seconds() ) + : stats.statistic( stat ).toString() ); + + addRow( row, QgsDateTimeStatisticalSummary::displayName( stat ), + value, + stats.count() != 0 ); + row++; + } +} + +void QgsStatisticalSummaryDockWidget::addRow( int row, const QString& name, const QString& value, + bool showValue ) +{ + QTableWidgetItem* nameItem = new QTableWidgetItem( name ); + nameItem->setToolTip( name ); + nameItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled ); + mStatisticsTable->setItem( row, 0, nameItem ); + + QTableWidgetItem* valueItem = new QTableWidgetItem(); + if ( showValue ) + { + valueItem->setText( value ); + } + valueItem->setToolTip( value ); + valueItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled ); + mStatisticsTable->setItem( row, 1, valueItem ); +} + diff --git a/src/app/qgsstatisticalsummarydockwidget.h b/src/app/qgsstatisticalsummarydockwidget.h index 5d1c537aeaa..4d783b2dfd5 100644 --- a/src/app/qgsstatisticalsummarydockwidget.h +++ b/src/app/qgsstatisticalsummarydockwidget.h @@ -20,6 +20,8 @@ #include "ui_qgsstatisticalsummarybase.h" #include "qgsstatisticalsummary.h" +#include "qgsstringstatisticalsummary.h" +#include "qgsdatetimestatisticalsummary.h" class QgsBrowserModel; class QModelIndex; @@ -62,6 +64,13 @@ class APP_EXPORT QgsStatisticalSummaryDockWidget : public QDockWidget, private U QMap< int, QAction* > mStatsActions; static QList< QgsStatisticalSummary::Statistic > mDisplayStats; + static QList< QgsStringStatisticalSummary::Statistic > mDisplayStringStats; + static QList< QgsDateTimeStatisticalSummary::Statistic > mDisplayDateTimeStats; + + void updateNumericStatistics( bool selectedOnly ); + void updateStringStatistics( bool selectedOnly ); + void updateDateTimeStatistics( bool selectedOnly ); + void addRow( int row, const QString& name, const QString& value, bool showValue ); }; #endif // QGSSTATISTICALSUMMARYDOCKWIDGET_H