mirror of
https://github.com/qgis/QGIS.git
synced 2025-04-14 00:07:35 -04:00
Fix graduated classifications for joined fields
git-svn-id: http://svn.osgeo.org/qgis/trunk@15389 c8812cc2-4d05-0410-92ff-de0c093fc19c
This commit is contained in:
parent
caa0cae3b9
commit
3717e57e82
@ -598,6 +598,14 @@ public:
|
||||
@note: this method was added in version 1.7*/
|
||||
void uniqueValues( int index, QList<QVariant>& uniqueValues /Out/, int limit );
|
||||
|
||||
/**Returns minimum value for an attribute column or invalid variant in case of error
|
||||
@note added in 1.7*/
|
||||
QVariant minimumValue( int index );
|
||||
|
||||
/**Returns maximum value for an attribute column or invalid variant in case of error
|
||||
@note added in 1.7*/
|
||||
QVariant maximumValue( int index );
|
||||
|
||||
public slots:
|
||||
|
||||
/** Select feature by its ID, optionally emit signal selectionChanged() */
|
||||
|
@ -265,7 +265,6 @@ void QgsGraduatedSymbolDialog::adjustClassification()
|
||||
{
|
||||
mClassListWidget->clear();
|
||||
QGis::GeometryType m_type = mVectorLayer->geometryType();
|
||||
QgsVectorDataProvider *provider = dynamic_cast<QgsVectorDataProvider *>( mVectorLayer->dataProvider() );
|
||||
double minimum = 0;
|
||||
double maximum = 0;
|
||||
|
||||
@ -288,20 +287,16 @@ void QgsGraduatedSymbolDialog::adjustClassification()
|
||||
std::map < QString, int >::iterator iter = mFieldMap.find( fieldstring );
|
||||
int field = iter->second;
|
||||
|
||||
|
||||
if ( provider )
|
||||
if ( modeComboBox->currentText() == tr( "Equal Interval" ) ||
|
||||
modeComboBox->currentText() == tr( "Quantiles" ) )
|
||||
{
|
||||
if ( modeComboBox->currentText() == tr( "Equal Interval" ) ||
|
||||
modeComboBox->currentText() == tr( "Quantiles" ) )
|
||||
{
|
||||
minimum = provider->minimumValue( field ).toDouble();
|
||||
maximum = provider->maximumValue( field ).toDouble();
|
||||
}
|
||||
else //don't waste performance if mMode is QgsGraduatedSymbolDialog::EMPTY
|
||||
{
|
||||
minimum = 0;
|
||||
maximum = 0;
|
||||
}
|
||||
minimum = mVectorLayer->minimumValue( field ).toDouble();
|
||||
maximum = mVectorLayer->maximumValue( field ).toDouble();
|
||||
}
|
||||
else //don't waste performance if mMode is QgsGraduatedSymbolDialog::EMPTY
|
||||
{
|
||||
minimum = 0;
|
||||
maximum = 0;
|
||||
}
|
||||
|
||||
//todo: setup a data structure which holds the symbols
|
||||
@ -500,30 +495,25 @@ int QgsGraduatedSymbolDialog::quantilesFromVectorLayer( std::list<double>& resul
|
||||
{
|
||||
if ( mVectorLayer )
|
||||
{
|
||||
QgsVectorDataProvider* provider = mVectorLayer->dataProvider();
|
||||
std::vector<double> attributeValues( mVectorLayer->featureCount() );
|
||||
QgsAttributeList attList;
|
||||
attList.push_back( attributeIndex );
|
||||
QgsFeature currentFeature;
|
||||
QgsAttributeMap currentAttributeMap;
|
||||
double currentValue;
|
||||
int index = 0;
|
||||
|
||||
if ( provider )
|
||||
mVectorLayer->select( attList, QgsRectangle(), false );
|
||||
while ( mVectorLayer->nextFeature( currentFeature ) )
|
||||
{
|
||||
std::vector<double> attributeValues( provider->featureCount() );
|
||||
QgsAttributeList attList;
|
||||
attList.push_back( attributeIndex );
|
||||
QgsFeature currentFeature;
|
||||
QgsAttributeMap currentAttributeMap;
|
||||
double currentValue;
|
||||
int index = 0;
|
||||
|
||||
provider->select( attList, QgsRectangle(), false );
|
||||
while ( provider->nextFeature( currentFeature ) )
|
||||
{
|
||||
currentAttributeMap = currentFeature.attributeMap();
|
||||
currentValue = currentAttributeMap[attributeIndex].toDouble();
|
||||
attributeValues[index] = currentValue;
|
||||
++index;
|
||||
}
|
||||
|
||||
sort( attributeValues.begin(), attributeValues.end() );
|
||||
return calculateQuantiles( result, attributeValues, numQuantiles );
|
||||
currentAttributeMap = currentFeature.attributeMap();
|
||||
currentValue = currentAttributeMap[attributeIndex].toDouble();
|
||||
attributeValues[index] = currentValue;
|
||||
++index;
|
||||
}
|
||||
|
||||
sort( attributeValues.begin(), attributeValues.end() );
|
||||
return calculateQuantiles( result, attributeValues, numQuantiles );
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
@ -5003,6 +5003,114 @@ void QgsVectorLayer::uniqueValues( int index, QList<QVariant> &uniqueValues, int
|
||||
uniqueValues = val.values();
|
||||
}
|
||||
|
||||
QVariant QgsVectorLayer::minimumValue( int index )
|
||||
{
|
||||
if ( !mDataProvider )
|
||||
{
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
int maxProviderIndex;
|
||||
QgsVectorLayerJoinBuffer::maximumIndex( mDataProvider->fields(), maxProviderIndex );
|
||||
|
||||
if ( index <= maxProviderIndex && !mEditable ) //a provider field
|
||||
{
|
||||
return mDataProvider->minimumValue( index );
|
||||
}
|
||||
else // a joined field?
|
||||
{
|
||||
int indexOffset; //offset between layer index and joined provider index
|
||||
const QgsVectorJoinInfo* join = mJoinBuffer->joinForFieldIndex( index, maxProviderIndex, indexOffset );
|
||||
if ( join )
|
||||
{
|
||||
QgsVectorLayer* vl = dynamic_cast<QgsVectorLayer*>( QgsMapLayerRegistry::instance()->mapLayer( join->joinLayerId ) );
|
||||
if ( vl )
|
||||
{
|
||||
return vl->minimumValue( index );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//the layer is editable, but in certain cases it can still be avoided going through all features
|
||||
if ( mDeletedFeatureIds.size() < 1 && mAddedFeatures.size() < 1 && !mDeletedAttributeIds.contains( index ) && mChangedAttributeValues.size() < 1 )
|
||||
{
|
||||
return mDataProvider->minimumValue( index );
|
||||
}
|
||||
|
||||
//we need to go through each feature
|
||||
QgsAttributeList attList;
|
||||
attList << index;
|
||||
|
||||
select( attList, QgsRectangle(), false, false );
|
||||
|
||||
QgsFeature f;
|
||||
double minimumValue = std::numeric_limits<double>::max();
|
||||
double currentValue = 0;
|
||||
while ( nextFeature( f ) )
|
||||
{
|
||||
currentValue = f.attributeMap()[index].toDouble();
|
||||
if ( currentValue < minimumValue )
|
||||
{
|
||||
minimumValue = currentValue;
|
||||
}
|
||||
}
|
||||
return QVariant( minimumValue );
|
||||
}
|
||||
|
||||
QVariant QgsVectorLayer::maximumValue( int index )
|
||||
{
|
||||
if ( !mDataProvider )
|
||||
{
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
int maxProviderIndex;
|
||||
QgsVectorLayerJoinBuffer::maximumIndex( mDataProvider->fields(), maxProviderIndex );
|
||||
|
||||
if ( index <= maxProviderIndex && !mEditable ) //a provider field
|
||||
{
|
||||
return mDataProvider->maximumValue( index );
|
||||
}
|
||||
else // a joined field?
|
||||
{
|
||||
int indexOffset; //offset between layer index and joined provider index
|
||||
const QgsVectorJoinInfo* join = mJoinBuffer->joinForFieldIndex( index, maxProviderIndex, indexOffset );
|
||||
if ( join )
|
||||
{
|
||||
QgsVectorLayer* vl = dynamic_cast<QgsVectorLayer*>( QgsMapLayerRegistry::instance()->mapLayer( join->joinLayerId ) );
|
||||
if ( vl )
|
||||
{
|
||||
return vl->maximumValue( index );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//the layer is editable, but in certain cases it can still be avoided going through all features
|
||||
if ( mDeletedFeatureIds.size() < 1 && mAddedFeatures.size() < 1 && !mDeletedAttributeIds.contains( index ) && mChangedAttributeValues.size() < 1 )
|
||||
{
|
||||
return mDataProvider->maximumValue( index );
|
||||
}
|
||||
|
||||
//we need to go through each feature
|
||||
QgsAttributeList attList;
|
||||
attList << index;
|
||||
|
||||
select( attList, QgsRectangle(), false, false );
|
||||
|
||||
QgsFeature f;
|
||||
double maximumValue = -std::numeric_limits<double>::max();
|
||||
double currentValue = 0;
|
||||
while ( nextFeature( f ) )
|
||||
{
|
||||
currentValue = f.attributeMap()[index].toDouble();
|
||||
if ( currentValue > maximumValue )
|
||||
{
|
||||
maximumValue = currentValue;
|
||||
}
|
||||
}
|
||||
return QVariant( maximumValue );
|
||||
}
|
||||
|
||||
void QgsVectorLayer::stopRendererV2( QgsRenderContext& rendererContext, QgsSingleSymbolRendererV2* selRenderer )
|
||||
{
|
||||
mRendererV2->stopRender( rendererContext );
|
||||
|
@ -651,6 +651,13 @@ class CORE_EXPORT QgsVectorLayer : public QgsMapLayer
|
||||
@note this method was added in version 1.7*/
|
||||
void uniqueValues( int index, QList<QVariant> &uniqueValues, int limit = -1 );
|
||||
|
||||
/**Returns minimum value for an attribute column or invalid variant in case of error
|
||||
@note added in 1.7*/
|
||||
QVariant minimumValue( int index );
|
||||
|
||||
/**Returns maximum value for an attribute column or invalid variant in case of error
|
||||
@note added in 1.7*/
|
||||
QVariant maximumValue( int index );
|
||||
|
||||
public slots:
|
||||
/** Select feature by its ID, optionally emit signal selectionChanged() */
|
||||
|
@ -684,12 +684,11 @@ QgsGraduatedSymbolRendererV2* QgsGraduatedSymbolRendererV2::createRenderer(
|
||||
QgsSymbolV2* symbol,
|
||||
QgsVectorColorRampV2* ramp )
|
||||
{
|
||||
QgsVectorDataProvider* provider = vlayer->dataProvider();
|
||||
|
||||
int attrNum = vlayer->fieldNameIndex( attrName );
|
||||
|
||||
double minimum = provider->minimumValue( attrNum ).toDouble();
|
||||
double maximum = provider->maximumValue( attrNum ).toDouble();
|
||||
double minimum = vlayer->minimumValue( attrNum ).toDouble();
|
||||
double maximum = vlayer->maximumValue( attrNum ).toDouble();
|
||||
QgsDebugMsg( QString( "min %1 // max %2" ).arg( minimum ).arg( maximum ) );
|
||||
|
||||
QList<double> breaks;
|
||||
@ -709,8 +708,8 @@ QgsGraduatedSymbolRendererV2* QgsGraduatedSymbolRendererV2::createRenderer(
|
||||
QgsFeature f;
|
||||
QgsAttributeList lst;
|
||||
lst.append( attrNum );
|
||||
provider->select( lst, QgsRectangle(), false );
|
||||
while ( provider->nextFeature( f ) )
|
||||
vlayer->select( lst, QgsRectangle(), false );
|
||||
while ( vlayer->nextFeature( f ) )
|
||||
values.append( f.attributeMap()[attrNum].toDouble() );
|
||||
// calculate the breaks
|
||||
if ( mode == Quantile )
|
||||
|
Loading…
x
Reference in New Issue
Block a user