double QgsComposerScaleBar::mapWidth() const
{
  if ( !mComposerMap )
  {
    return 0.0;
  }

  QgsRectangle composerMapRect = *( mComposerMap->currentMapExtent() );
  if ( mUnits == MapUnits )
  {
    return composerMapRect.width();
  }
  else
  {
    QgsDistanceArea da;
    da.setEllipsoidalMode( mComposition->mapSettings().hasCrsTransformEnabled() );
    da.setSourceCrs( mComposition->mapSettings().destinationCrs().srsid() );
    da.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", "WGS84" ) );

    double measure = da.measureLine( QgsPoint( composerMapRect.xMinimum(), composerMapRect.yMinimum() ), QgsPoint( composerMapRect.xMaximum(), composerMapRect.yMinimum() ) );
    if ( mUnits == QgsComposerScaleBar::Feet )
    {
      measure /= QGis::fromUnitToUnitFactor( QGis::Feet, QGis::Meters );
    }
    else if ( mUnits == QgsComposerScaleBar::NauticalMiles )
    {
      measure /= QGis::fromUnitToUnitFactor( QGis::NauticalMiles, QGis::Meters );
    }
    return measure;
  }
}
void QgsAttributeActionDialog::insertExpression()
{
  QString selText = actionAction->textCursor().selectedText();

  // edit the selected expression if there's one
  if ( selText.startsWith( "[%" ) && selText.endsWith( "%]" ) )
    selText = selText.mid( 2, selText.size() - 4 );

  // display the expression builder
  QgsExpressionContext context;
  context << QgsExpressionContextUtils::globalScope()
  << QgsExpressionContextUtils::projectScope()
  << QgsExpressionContextUtils::layerScope( mActions->layer() );

  QgsExpressionBuilderDialog dlg( mActions->layer(), selText, this, "generic", context );
  dlg.setWindowTitle( tr( "Insert expression" ) );

  QgsDistanceArea myDa;
  myDa.setSourceCrs( mActions->layer()->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );
  dlg.setGeomCalculator( myDa );

  if ( dlg.exec() == QDialog::Accepted )
  {
    QString expression =  dlg.expressionBuilder()->expressionText();
    //Only add the expression if the user has entered some text.
    if ( !expression.isEmpty() )
    {
      actionAction->insertPlainText( "[%" + expression + "%]" );
    }
  }
}
double QgsComposerScaleBar::mapWidth() const
{
  if ( !mComposerMap )
  {
    return 0.0;
  }

  QgsRectangle composerMapRect = mComposerMap->extent();
  if ( mUnits == MapUnits )
  {
    return composerMapRect.width();
  }
  else
  {
    QgsDistanceArea da;
    da.setEllipsoidalMode( mComposerMap->mapRenderer()->hasCrsTransformEnabled() );
    da.setSourceCrs( mComposerMap->mapRenderer()->destinationCrs().srsid() );
    da.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", "WGS84" ) );

    double measure = da.measureLine( QgsPoint( composerMapRect.xMinimum(), composerMapRect.yMinimum() ), QgsPoint( composerMapRect.xMaximum(), composerMapRect.yMinimum() ) );
    if ( mUnits == Feet )
    {
      measure /= 0.3048;
    }
    return measure;
  }
}
void TestQgsDistanceArea::unit_conversions()
{
    // Do some very simple test of conversion and units
    QgsDistanceArea myDa;
    myDa.setEllipsoidalMode( false );

    double inputValue;
    QGis::UnitType inputUnit;
    QGis::UnitType outputUnit;

    inputValue = 10000.0;
    inputUnit = QGis::Meters;
    outputUnit = QGis::Feet;
    //outputUnit = QGis::Meters;

    // First, convert from sq.meter to sq.feet
    Q_NOWARN_DEPRECATED_PUSH
    myDa.convertMeasurement( inputValue, inputUnit, outputUnit, true );
    Q_NOWARN_DEPRECATED_POP
    QVERIFY( qAbs( inputValue - 107639.1041671 ) <= 0.0000001 );

    // The print a text unit. This is i18n, so we should ignore the unit
    // and use the locale settings for separation of digits.
    QString myTxt = QgsDistanceArea::textUnit( inputValue, 7, inputUnit, true, false );
    QString expectedTxt = QLocale::system().toString( 2.4710538146717, 'g', 1 + 7 );
    QVERIFY( myTxt.startsWith( expectedTxt ) ); // Ignore units for now.
}
QgsAttributeActionPropertiesDialog::QgsAttributeActionPropertiesDialog( QgsVectorLayer* layer, QWidget* parent )
    : QDialog( parent )
    , mLayer( layer )
{
  setupUi( this );

  // display the expression builder
  QgsExpressionContext context;
  context << QgsExpressionContextUtils::globalScope()
  << QgsExpressionContextUtils::projectScope()
  << QgsExpressionContextUtils::layerScope( mLayer );

  QgsDistanceArea myDa;
  myDa.setSourceCrs( mLayer->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->ellipsoid() );

  mFieldExpression->setLayer( mLayer );
  mFieldExpression->setGeomCalculator( myDa );

  connect( mBrowseButton, SIGNAL( clicked( bool ) ), this, SLOT( browse() ) );
  connect( mInsertFieldOrExpression, SIGNAL( clicked( bool ) ), this, SLOT( insertExpressionOrField() ) );
  connect( mActionName, SIGNAL( textChanged( QString ) ), this, SLOT( updateButtons() ) );
  connect( mActionText, SIGNAL( textChanged() ), this, SLOT( updateButtons() ) );

  updateButtons();
}
Exemple #6
0
void GlobePlugin::syncExtent()
{
  osgEarth::Util::EarthManipulator* manip = dynamic_cast<osgEarth::Util::EarthManipulator*>( mOsgViewer->getCameraManipulator() );
  //rotate earth to north and perpendicular to camera
  manip->setRotation( osg::Quat() );

  //get mapCanvas->extent().height() in meters
  QgsRectangle extent = mQGisIface->mapCanvas()->extent();
  QgsDistanceArea dist;
  dist.setEllipsoidalMode( true );
  //dist.setProjectionsEnabled( true );
  QgsPoint ll = QgsPoint( extent.xMinimum(), extent.yMinimum() );
  QgsPoint ul = QgsPoint( extent.xMinimum(), extent.yMaximum() );
  double height = dist.measureLine( ll, ul );

  //camera viewing angle
  double viewAngle = 30;
  //camera distance
  double distance = height / tan( viewAngle * osg::PI / 180 ); //c = b*cotan(B(rad))

  OE_NOTICE << "map extent: " << height << " camera distance: " << distance << std::endl;

  osgEarth::Util::Viewpoint viewpoint( osg::Vec3d( extent.center().x(), extent.center().y(), 0.0 ), 0.0, -90.0, distance );
  manip->setViewpoint( viewpoint, 4.0 );
}
void TestQgsDistanceArea::collections()
{
  //test measuring for collections
  QgsDistanceArea myDa;
  myDa.setSourceAuthId( "EPSG:4030" );
  myDa.setEllipsoidalMode( true );
  myDa.setEllipsoid( "WGS84" );

  //collection of lines, should be sum of line length
  QgsGeometry lines( QgsGeometryFactory::geomFromWkt( "GeometryCollection( LineString(0 36.53, 5.76 -48.16), LineString(0 25.54, 24.20 36.70) )" ) );
  double result = myDa.measureLength( &lines );
  QGSCOMPARENEAR( result, 12006159, 1 );
  result = myDa.measureArea( &lines );
  QVERIFY( qgsDoubleNear( result, 0 ) );

  //collection of polygons
  QgsGeometry polys( QgsGeometryFactory::geomFromWkt( "GeometryCollection( Polygon((0 36.53, 5.76 -48.16, 0 25.54, 0 36.53)), Polygon((10 20, 15 20, 15 10, 10 20)) )" ) );
  result = myDa.measureArea( &polys );
  QGSCOMPARENEAR( result, 670434859475LL, 1 );
  result = myDa.measureLength( &polys );
  QVERIFY( qgsDoubleNear( result, 0 ) );

  //mixed collection
  QgsGeometry mixed( QgsGeometryFactory::geomFromWkt( "GeometryCollection( LineString(0 36.53, 5.76 -48.16), LineString(0 25.54, 24.20 36.70), Polygon((0 36.53, 5.76 -48.16, 0 25.54, 0 36.53)), Polygon((10 20, 15 20, 15 10, 10 20)) )" ) );
  //measure area specifically
  result = myDa.measureArea( &mixed );
  QGSCOMPARENEAR( result, 670434859475LL, 1 );
  //measure length
  result = myDa.measureLength( &mixed );
  QGSCOMPARENEAR( result, 12006159, 1 );
}
void GlobePlugin::syncExtent()
{
  QgsMapCanvas* mapCanvas = mQGisIface->mapCanvas();
  QgsMapRenderer* mapRenderer = mapCanvas->mapRenderer();
  QgsRectangle extent = mapCanvas->extent();

  osgEarth::Util::EarthManipulator* manip = dynamic_cast<osgEarth::Util::EarthManipulator*>( mOsgViewer->getCameraManipulator() );
  //rotate earth to north and perpendicular to camera
  manip->setRotation( osg::Quat() );

  QgsDistanceArea dist;

  dist.setSourceCrs( mapRenderer->destinationCrs().srsid() );
  dist.setEllipsoidalMode( mapRenderer->hasCrsTransformEnabled() );
  dist.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );

  QgsPoint ll = QgsPoint( extent.xMinimum(), extent.yMinimum() );
  QgsPoint ul = QgsPoint( extent.xMinimum(), extent.yMaximum() );
  double height = dist.measureLine( ll, ul );

  //camera viewing angle
  double viewAngle = 30;
  //camera distance
  double distance = height / tan( viewAngle * osg::PI / 180 ); //c = b*cotan(B(rad))

  OE_NOTICE << "map extent: " << height << " camera distance: " << distance << std::endl;

  osgEarth::Util::Viewpoint viewpoint( osg::Vec3d( extent.center().x(), extent.center().y(), 0.0 ), 0.0, -90.0, distance );
  manip->setViewpoint( viewpoint, 4.0 );
}
void TestQgsDistanceArea::emptyPolygon()
{
  QgsDistanceArea da;
  da.setSourceCrs( 3452 );
  da.setEllipsoidalMode( true );
  da.setEllipsoid( "WGS84" );

  //test that measuring an empty polygon doesn't crash
  da.measurePolygon( QList< QgsPoint >() );
}
Exemple #10
0
void TestQgsDistanceArea::regression13601()
{
    //test regression #13601
    QgsDistanceArea calc;
    calc.setEllipsoidalMode( true );
    calc.setEllipsoid( "NONE" );
    calc.setSourceCrs( 1108L );
    QgsGeometry geom( QgsGeometryFactory::geomFromWkt( "Polygon ((252000 1389000, 265000 1389000, 265000 1385000, 252000 1385000, 252000 1389000))" ) );
    QVERIFY( qgsDoubleNear( calc.measureArea( &geom ), 52000000, 0.0001 ) );
}
void TestQgsDistanceArea::regression14675()
{
  //test regression #14675
  QgsDistanceArea calc;
  calc.setEllipsoidalMode( true );
  calc.setEllipsoid( "GRS80" );
  calc.setSourceCrs( 145L );
  QgsGeometry geom( QgsGeometryFactory::geomFromWkt( "Polygon ((917593.5791854317067191 6833700.00807378999888897, 917596.43389983859378844 6833700.67099479306489229, 917599.53056440979707986 6833700.78673478215932846, 917593.5791854317067191 6833700.00807378999888897))" ) );
  //lots of tolerance here - the formulas get quite unstable with small areas due to division by very small floats
  QGSCOMPARENEAR( calc.measureArea( &geom ), 0.83301, 0.02 );
}
QDialog* QgisAppInterface::getFeatureForm( QgsVectorLayer *l, QgsFeature &f )
{
  QgsDistanceArea myDa;

  myDa.setSourceCrs( l->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapRenderer()->hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );

  QgsAttributeDialog *dialog = new QgsAttributeDialog( l, &f, false, myDa );
  return dialog->dialog();
}
Exemple #13
0
double Heatmap::mapUnitsOf( double meters, QgsCoordinateReferenceSystem layerCrs )
{
  // Worker to transform metres input to mapunits
  QgsDistanceArea da;
  da.setSourceCrs( layerCrs.srsid() );
  da.setEllipsoid( layerCrs.ellipsoidAcronym() );
  if ( da.geographic() )
  {
    da.setEllipsoidalMode( true );
  }
  return meters / da.measureLine( QgsPoint( 0.0, 0.0 ), QgsPoint( 0.0, 1.0 ) );
}
Exemple #14
0
void TestQgsDistanceArea::measureUnits()
{
    //test regression #13610
    QgsDistanceArea calc;
    calc.setEllipsoidalMode( false );
    calc.setEllipsoid( "NONE" );
    calc.setSourceCrs( 254L );
    QGis::UnitType units;
    QgsPoint p1( 1341683.9854275715, 408256.9562717728 );
    QgsPoint p2( 1349321.7807031618, 408256.9562717728 );

    double result = calc.measureLine( p1, p2, units );
    //no OTF, result will be in CRS unit (feet)
    QCOMPARE( units, QGis::Feet );
    QVERIFY( qgsDoubleNear( result, 7637.7952755903825, 0.001 ) );

    calc.setEllipsoidalMode( true );
    calc.setEllipsoid( "WGS84" );
    result = calc.measureLine( p1, p2, units );
    //OTF, result will be in meters
    QCOMPARE( units, QGis::Meters );
    QVERIFY( qgsDoubleNear( result, 2328.0988253106957, 0.001 ) );
}
Exemple #15
0
double HeatmapGui::mapUnitsOf( double dist, const QgsCoordinateReferenceSystem& layerCrs ) const
{
  // converter function to transform layer input to mapunits
  // so that bounding box can be updated
  QgsDistanceArea da;
  da.setSourceCrs( layerCrs.srsid() );
  da.setEllipsoid( layerCrs.ellipsoidAcronym() );
  if ( da.geographic() )
  {
    da.setEllipsoidalMode( true );
  }
  double unitDistance = da.measureLine( QgsPoint( 0.0, 0.0 ), QgsPoint( 0.0, 1.0 ) );
  QgsDebugMsg( QString( "Converted %1 layer to %2 map units" ).arg( dist ).arg( dist / unitDistance ) );
  return  dist / unitDistance;
}
Exemple #16
0
void TestQgsDistanceArea::test_distances()
{
    // Read the file of Geod data
    // Column 0 (first) is latitude point 1
    // Column 1 is longitude point 1
    // Column 3 is latitude point 2
    // Column 4 is longitude point 3
    // Column 6 is the resulting distance in meters on the WGS84 ellipsoid
    // Note: lat is north/south, so the QgsPoint should be ( long, lat )
    // See http://geographiclib.sourceforge.net/html/geodesic.html#testgeod

    // Set up DA
    QgsDistanceArea myDa;
    myDa.setSourceAuthId( "EPSG:4030" );
    myDa.setEllipsoidalMode( true );
    myDa.setEllipsoid( "WGS84" );

    QString myFileName = QString( TEST_DATA_DIR ) + "/GeodTest-nano.dat";

    QFile myFile( myFileName );
    if ( ! myFile.open( QIODevice::ReadOnly | QIODevice::Text ) )
    {
        QFAIL( "Couldn't open file" );
        return;
    }
    QTextStream in( & myFile );
    while ( !in.atEnd() )
    {
        QString line = in.readLine();
        // Some test points (antipodal) does not converge with the chosen algorithm!
        // See calcaulator at http://www.movable-type.co.uk/scripts/latlong-vincenty.html
        // These are commented out.
        if ( line[0] != '#' )
        {
            QStringList myLineList = line.split( ' ' ); // Split fields on space.
            // Create points
            QgsPoint p1( myLineList[1].toDouble(), myLineList[0].toDouble() );
            QgsPoint p2( myLineList[4].toDouble(), myLineList[3].toDouble() );
            double result = myDa.measureLine( p1, p2 );
            // QgsDebugMsg( QString( "Distance from %1 to %2 is %3" ).arg( p1.toString( 15 ) ).arg( p2.toString( 15 ) ).arg( result, 0, 'g', 15 ) );
            // QgsDebugMsg( QString( "Distance should be %1" ).arg( myLineList[6] ) );
            // Check result is less than 0.5mm from expected.
            QVERIFY( qAbs( result -  myLineList[6].toDouble() ) < 0.0005 );
        }
    }

}
QgsAttributeDialog *QgsFeatureAction::newDialog( bool cloneFeature )
{
  QgsFeature *f = cloneFeature ? new QgsFeature( *mFeature ) : mFeature;

  QgsAttributeEditorContext context;

  QgsDistanceArea myDa;

  myDa.setSourceCrs( mLayer->crs() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );

  context.setDistanceArea( myDa );
  context.setVectorLayerTools( QgisApp::instance()->vectorLayerTools() );

  QgsAttributeDialog *dialog = new QgsAttributeDialog( mLayer, f, cloneFeature, NULL, true, context );

  if ( mLayer->actions()->size() > 0 )
  {
    dialog->setContextMenuPolicy( Qt::ActionsContextMenu );

    QAction *a = new QAction( tr( "Run actions" ), dialog );
    a->setEnabled( false );
    dialog->addAction( a );

    for ( int i = 0; i < mLayer->actions()->size(); i++ )
    {
      const QgsAction &action = mLayer->actions()->at( i );

      if ( !action.runable() )
        continue;

      QgsFeature& feat = const_cast<QgsFeature&>( *dialog->feature() );
      QgsFeatureAction *a = new QgsFeatureAction( action.name(), feat, mLayer, i, -1, dialog );
      dialog->addAction( a );
      connect( a, SIGNAL( triggered() ), a, SLOT( execute() ) );

      QAbstractButton *pb = dialog->findChild<QAbstractButton *>( action.name() );
      if ( pb )
        connect( pb, SIGNAL( clicked() ), a, SLOT( execute() ) );
    }
  }

  return dialog;
}
QgsAttributeDialog* QgisAppInterface::getFeatureForm( QgsVectorLayer *l, QgsFeature &feature )
{
  QgsDistanceArea myDa;

  myDa.setSourceCrs( l->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );

  QgsAttributeEditorContext context;
  context.setDistanceArea( myDa );
  context.setVectorLayerTools( qgis->vectorLayerTools() );
  QgsAttributeDialog *dialog = new QgsAttributeDialog( l, &feature, false, qgis, true, context );
  if ( !feature.isValid() )
  {
    dialog->setMode( QgsAttributeForm::AddFeatureMode );
  }
  return dialog;
}
Exemple #19
0
void GlobePlugin::syncExtent()
{
  QgsMapCanvas* mapCanvas = mQGisIface->mapCanvas();
  const QgsMapSettings &mapSettings = mapCanvas->mapSettings();
  QgsRectangle extent = mapCanvas->extent();

  long epsgGlobe = 4326;
  QgsCoordinateReferenceSystem globeCrs;
  globeCrs.createFromOgcWmsCrs( QString( "EPSG:%1" ).arg( epsgGlobe ) );

  // transform extent to WGS84
  if ( mapSettings.destinationCrs().authid().compare( QString( "EPSG:%1" ).arg( epsgGlobe ), Qt::CaseInsensitive ) != 0 )
  {
    QgsCoordinateReferenceSystem srcCRS( mapSettings.destinationCrs() );
    QgsCoordinateTransform* coordTransform = new QgsCoordinateTransform( srcCRS, globeCrs );
    extent = coordTransform->transformBoundingBox( extent );
    delete coordTransform;
  }

  osgEarth::Util::EarthManipulator* manip = dynamic_cast<osgEarth::Util::EarthManipulator*>( mOsgViewer->getCameraManipulator() );
  //rotate earth to north and perpendicular to camera
  manip->setRotation( osg::Quat() );

  QgsDistanceArea dist;

  dist.setSourceCrs( globeCrs );
  dist.setEllipsoidalMode( true );
  dist.setEllipsoid( "WGS84" );

  QgsPoint ll = QgsPoint( extent.xMinimum(), extent.yMinimum() );
  QgsPoint ul = QgsPoint( extent.xMinimum(), extent.yMaximum() );
  double height = dist.measureLine( ll, ul );

  //camera viewing angle
  double viewAngle = 30;
  //camera distance
  double distance = height / tan( viewAngle * osg::PI / 180 ); //c = b*cotan(B(rad))

  OE_NOTICE << "map extent: " << height << " camera distance: " << distance << std::endl;

  osgEarth::Util::Viewpoint viewpoint( osg::Vec3d( extent.center().x(), extent.center().y(), 0.0 ), 0.0, -90.0, distance );
  manip->setViewpoint( viewpoint, 4.0 );
}
Exemple #20
0
double QgsComposerScaleBar::mapWidth() const
{
  if ( !mComposerMap )
  {
    return 0.0;
  }

  QgsRectangle composerMapRect = *( mComposerMap->currentMapExtent() );
  if ( mUnits == MapUnits )
  {
    return composerMapRect.width();
  }
  else
  {
    QgsDistanceArea da;
    da.setEllipsoidalMode( mComposition->mapSettings().hasCrsTransformEnabled() );
    da.setSourceCrs( mComposition->mapSettings().destinationCrs().srsid() );
    da.setEllipsoid( mComposition->project()->ellipsoid() );

    QgsUnitTypes::DistanceUnit units = QgsUnitTypes::DistanceMeters;
    double measure = da.measureLine( QgsPoint( composerMapRect.xMinimum(), composerMapRect.yMinimum() ),
                                     QgsPoint( composerMapRect.xMaximum(), composerMapRect.yMinimum() ),
                                     units );
    switch ( mUnits )
    {
      case QgsComposerScaleBar::Feet:
        measure /= QgsUnitTypes::fromUnitToUnitFactor( QgsUnitTypes::DistanceFeet, units );
        break;
      case QgsComposerScaleBar::NauticalMiles:
        measure /= QgsUnitTypes::fromUnitToUnitFactor( QgsUnitTypes::DistanceNauticalMiles, units );
        break;
      case QgsComposerScaleBar::Meters:
        measure /= QgsUnitTypes::fromUnitToUnitFactor( QgsUnitTypes::DistanceMeters, units );
        break;
      case QgsComposerScaleBar::MapUnits:
        //avoid warning
        break;
    }
    return measure;
  }
}
void QgsBullsEyeWidget::createLayer( QString layerName )
{
  if ( layerName.isEmpty() )
  {
    layerName = QInputDialog::getText( this, tr( "Layer Name" ), tr( "Enter name of new layer:" ) );
  }
  if ( !layerName.isEmpty() )
  {
    QgsDistanceArea da;
    da.setEllipsoid( "WGS84" );
    da.setEllipsoidalMode( true );
    da.setSourceCrs( mCanvas->mapSettings().destinationCrs() );
    QgsRectangle extent = mCanvas->extent();
    double extentHeight = da.measureLine( QgsPoint( extent.center().x(), extent.yMinimum() ), QgsPoint( extent.center().x(), extent.yMaximum() ) );
    double interval = 0.5 * extentHeight * QGis::fromUnitToUnitFactor( QGis::Meters, QGis::NauticalMiles ) / 6; // Half height divided by nr rings+1, in nm
    QgsBullsEyeLayer* bullEyeLayer = new QgsBullsEyeLayer( layerName );
    bullEyeLayer->setup( mCanvas->extent().center(), mCanvas->mapSettings().destinationCrs(), 5, interval, 45 );
    QgsMapLayerRegistry::instance()->addMapLayer( bullEyeLayer );
    mLayerTreeView->setCurrentLayer( bullEyeLayer );
  }
}
Exemple #22
0
void TestQgsDistanceArea::basic()
{
    QgsPoint p1( 1.0, 3.0 ), p2( -2.0, -1.0 );
    QgsDistanceArea daA;
    double resultA, resultB, resultC;

    daA.setEllipsoid( GEO_NONE );
    resultA = daA.measureLine( p1, p2 );
    QCOMPARE( resultA, 5.0 );

    // Now, on an ellipsoid. Always less?
    daA.setSourceCrs( 3006 );
    daA.setEllipsoid( "WGS84" );
    daA.setEllipsoidalMode( true );
    resultA = daA.measureLine( p1, p2 );
    QVERIFY( resultA < 5.0 );

    // Test copy constructor
    QgsDistanceArea daB( daA );
    resultB = daB.measureLine( p1, p2 );
    QCOMPARE( resultA, resultB );

    // Different Ellipsoid
    daB.setEllipsoid( "WGS72" );
    resultB = daB.measureLine( p1, p2 );
    QVERIFY( ! qFuzzyCompare( resultA, resultB ) );

    // Test assignment
    QSharedPointer<QgsDistanceArea> daC( new QgsDistanceArea );
    *daC = daB;
    resultC = daC->measureLine( p1, p2 );
    QCOMPARE( resultB, resultC );

    // Use parameter setting of ellipsoid radii (from WGS72 )
    daA.setEllipsoid( 6378135.0, 6378135.0 - ( 6378135.0 / 298.26 ) );
    resultA = daA.measureLine( p1, p2 );
    QCOMPARE( resultA, resultB );
}
QgsAttributeActionPropertiesDialog::QgsAttributeActionPropertiesDialog( QgsAction::ActionType type, const QString& description, const QString& shortTitle, const QString& iconPath, const QString& actionText, bool capture, bool showInAttributeTable, QgsVectorLayer* layer, QWidget* parent )
    : QDialog( parent )
    , mLayer( layer )
{
  setupUi( this );

  mActionType->setCurrentIndex( type );
  mActionName->setText( description );
  mShortTitle->setText( shortTitle );
  mActionIcon->setText( iconPath );
  mIconPreview->setPixmap( QPixmap( iconPath ) );
  mActionText->setText( actionText );
  mCaptureOutput->setChecked( capture );
  mShowInAttributeTable->setChecked( showInAttributeTable );

  // display the expression builder
  QgsExpressionContext context;
  context << QgsExpressionContextUtils::globalScope()
  << QgsExpressionContextUtils::projectScope()
  << QgsExpressionContextUtils::layerScope( mLayer );

  QgsDistanceArea myDa;
  myDa.setSourceCrs( mLayer->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->ellipsoid() );

  mFieldExpression->setLayer( mLayer );
  mFieldExpression->setGeomCalculator( myDa );

  connect( mBrowseButton, SIGNAL( clicked( bool ) ), this, SLOT( browse() ) );
  connect( mInsertFieldOrExpression, SIGNAL( clicked( bool ) ), this, SLOT( insertExpressionOrField() ) );
  connect( mActionName, SIGNAL( textChanged( QString ) ), this, SLOT( updateButtons() ) );
  connect( mActionText, SIGNAL( textChanged() ), this, SLOT( updateButtons() ) );
  connect( mChooseIconButton, SIGNAL( clicked( bool ) ), this, SLOT( chooseIcon() ) );

  updateButtons();
}
Exemple #24
0
QMap< QString, QString > QgsMapToolIdentify::featureDerivedAttributes( QgsFeature *feature, QgsMapLayer *layer )
{
  // Calculate derived attributes and insert:
  // measure distance or area depending on geometry type
  QMap< QString, QString > derivedAttributes;

  // init distance/area calculator
  QString ellipsoid = QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE );
  QgsDistanceArea calc;
  calc.setEllipsoidalMode( mCanvas->hasCrsTransformEnabled() );
  calc.setEllipsoid( ellipsoid );
  calc.setSourceCrs( layer->crs().srsid() );

  QGis::WkbType wkbType = QGis::WKBNoGeometry;
  QGis::GeometryType geometryType = QGis::NoGeometry;

  if ( feature->geometry() )
  {
    geometryType = feature->geometry()->type();
    wkbType = feature->geometry()->wkbType();
  }

  if ( geometryType == QGis::Line )
  {
    double dist = calc.measure( feature->geometry() );
    QGis::UnitType myDisplayUnits;
    convertMeasurement( calc, dist, myDisplayUnits, false );
    QString str = calc.textUnit( dist, 3, myDisplayUnits, false );  // dist and myDisplayUnits are out params
    derivedAttributes.insert( tr( "Length" ), str );
    if ( wkbType == QGis::WKBLineString || wkbType == QGis::WKBLineString25D )
    {
      // Add the start and end points in as derived attributes
      QgsPoint pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, feature->geometry()->asPolyline().first() );
      str = QLocale::system().toString( pnt.x(), 'g', 10 );
      derivedAttributes.insert( tr( "firstX", "attributes get sorted; translation for lastX should be lexically larger than this one" ), str );
      str = QLocale::system().toString( pnt.y(), 'g', 10 );
      derivedAttributes.insert( tr( "firstY" ), str );
      pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, feature->geometry()->asPolyline().last() );
      str = QLocale::system().toString( pnt.x(), 'g', 10 );
      derivedAttributes.insert( tr( "lastX", "attributes get sorted; translation for firstX should be lexically smaller than this one" ), str );
      str = QLocale::system().toString( pnt.y(), 'g', 10 );
      derivedAttributes.insert( tr( "lastY" ), str );
    }
  }
  else if ( geometryType == QGis::Polygon )
  {
    double area = calc.measure( feature->geometry() );
    double perimeter = calc.measurePerimeter( feature->geometry() );
    QGis::UnitType myDisplayUnits;
    convertMeasurement( calc, area, myDisplayUnits, true );  // area and myDisplayUnits are out params
    QString str = calc.textUnit( area, 3, myDisplayUnits, true );
    derivedAttributes.insert( tr( "Area" ), str );
    convertMeasurement( calc, perimeter, myDisplayUnits, false );  // perimeter and myDisplayUnits are out params
    str = calc.textUnit( perimeter, 3, myDisplayUnits, false );
    derivedAttributes.insert( tr( "Perimeter" ), str );
  }
  else if ( geometryType == QGis::Point &&
            ( wkbType == QGis::WKBPoint || wkbType == QGis::WKBPoint25D ) )
  {
    // Include the x and y coordinates of the point as a derived attribute
    QgsPoint pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, feature->geometry()->asPoint() );
    QString str = QLocale::system().toString( pnt.x(), 'g', 10 );
    derivedAttributes.insert( "X", str );
    str = QLocale::system().toString( pnt.y(), 'g', 10 );
    derivedAttributes.insert( "Y", str );
  }

  return derivedAttributes;
}
QgsAttributeTableDialog::QgsAttributeTableDialog( QgsVectorLayer *theLayer, QWidget *parent, Qt::WindowFlags flags )
    : QDialog( parent, flags )
    , mDock( 0 )
    , mLayer( theLayer )
{
  setupUi( this );

  // Fix selection color on loosing focus (Windows)
  setStyleSheet( QgisApp::instance()->styleSheet() );

  setAttribute( Qt::WA_DeleteOnClose );

  QSettings settings;

  // Initialize the window geometry
  restoreGeometry( settings.value( "/Windows/BetterAttributeTable/geometry" ).toByteArray() );

  QgsAttributeEditorContext context;

  QgsDistanceArea myDa;

  myDa.setSourceCrs( mLayer->crs() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );

  context.setDistanceArea( myDa );
  context.setVectorLayerTools( QgisApp::instance()->vectorLayerTools() );

  // Initialize dual view
  mMainView->init( mLayer, QgisApp::instance()->mapCanvas(), QgsFeatureRequest(), context );

  // Initialize filter gui elements
  mFilterActionMapper = new QSignalMapper( this );
  mFilterColumnsMenu = new QMenu( this );
  mActionFilterColumnsMenu->setMenu( mFilterColumnsMenu );
  mApplyFilterButton->setDefaultAction( mActionApplyFilter );

  // Set filter icon in a couple of places
  QIcon filterIcon = QgsApplication::getThemeIcon( "/mActionFilter.svg" );
  mActionShowAllFilter->setIcon( filterIcon );
  mActionAdvancedFilter->setIcon( filterIcon );
  mActionSelectedFilter->setIcon( filterIcon );
  mActionVisibleFilter->setIcon( filterIcon );
  mActionEditedFilter->setIcon( filterIcon );

  // Connect filter signals
  connect( mActionAdvancedFilter, SIGNAL( triggered() ), SLOT( filterExpressionBuilder() ) );
  connect( mActionShowAllFilter, SIGNAL( triggered() ), SLOT( filterShowAll() ) );
  connect( mActionSelectedFilter, SIGNAL( triggered() ), SLOT( filterSelected() ) );
  connect( mActionVisibleFilter, SIGNAL( triggered() ), SLOT( filterVisible() ) );
  connect( mActionEditedFilter, SIGNAL( triggered() ), SLOT( filterEdited() ) );
  connect( mFilterActionMapper, SIGNAL( mapped( QObject* ) ), SLOT( filterColumnChanged( QObject* ) ) );
  connect( mFilterQuery, SIGNAL( returnPressed() ), SLOT( filterQueryAccepted() ) );
  connect( mActionApplyFilter, SIGNAL( triggered() ), SLOT( filterQueryAccepted() ) );

  // info from layer to table
  connect( mLayer, SIGNAL( editingStarted() ), this, SLOT( editingToggled() ) );
  connect( mLayer, SIGNAL( editingStopped() ), this, SLOT( editingToggled() ) );
  connect( mLayer, SIGNAL( layerDeleted() ), this, SLOT( close() ) );
  connect( mLayer, SIGNAL( selectionChanged() ), this, SLOT( updateTitle() ) );
  connect( mLayer, SIGNAL( attributeAdded( int ) ), this, SLOT( columnBoxInit() ) );
  connect( mLayer, SIGNAL( attributeDeleted( int ) ), this, SLOT( columnBoxInit() ) );

  // connect table info to window
  connect( mMainView, SIGNAL( filterChanged() ), this, SLOT( updateTitle() ) );

  // info from table to application
  connect( this, SIGNAL( saveEdits( QgsMapLayer * ) ), QgisApp::instance(), SLOT( saveEdits( QgsMapLayer * ) ) );

  bool myDockFlag = settings.value( "/qgis/dockAttributeTable", false ).toBool();
  if ( myDockFlag )
  {
    mDock = new QgsAttributeTableDock( tr( "Attribute table - %1 (%n Feature(s))", "feature count", mMainView->featureCount() ).arg( mLayer->name() ), QgisApp::instance() );
    mDock->setAllowedAreas( Qt::BottomDockWidgetArea | Qt::TopDockWidgetArea );
    mDock->setWidget( this );
    connect( this, SIGNAL( destroyed() ), mDock, SLOT( close() ) );
    QgisApp::instance()->addDockWidget( Qt::BottomDockWidgetArea, mDock );
  }

  columnBoxInit();
  updateTitle();

  mRemoveSelectionButton->setIcon( QgsApplication::getThemeIcon( "/mActionUnselectAttributes.png" ) );
  mSelectedToTopButton->setIcon( QgsApplication::getThemeIcon( "/mActionSelectedToTop.png" ) );
  mCopySelectedRowsButton->setIcon( QgsApplication::getThemeIcon( "/mActionCopySelected.png" ) );
  mZoomMapToSelectedRowsButton->setIcon( QgsApplication::getThemeIcon( "/mActionZoomToSelected.svg" ) );
  mPanMapToSelectedRowsButton->setIcon( QgsApplication::getThemeIcon( "/mActionPanToSelected.svg" ) );
  mInvertSelectionButton->setIcon( QgsApplication::getThemeIcon( "/mActionInvertSelection.png" ) );
  mToggleEditingButton->setIcon( QgsApplication::getThemeIcon( "/mActionToggleEditing.svg" ) );
  mSaveEditsButton->setIcon( QgsApplication::getThemeIcon( "/mActionSaveEdits.svg" ) );
  mDeleteSelectedButton->setIcon( QgsApplication::getThemeIcon( "/mActionDeleteSelected.svg" ) );
  mOpenFieldCalculator->setIcon( QgsApplication::getThemeIcon( "/mActionCalculateField.png" ) );
  mAddAttribute->setIcon( QgsApplication::getThemeIcon( "/mActionNewAttribute.png" ) );
  mRemoveAttribute->setIcon( QgsApplication::getThemeIcon( "/mActionDeleteAttribute.png" ) );
  mTableViewButton->setIcon( QgsApplication::getThemeIcon( "/mActionOpenTable.png" ) );
  mAttributeViewButton->setIcon( QgsApplication::getThemeIcon( "/mActionPropertyItem.png" ) );
  mExpressionSelectButton->setIcon( QgsApplication::getThemeIcon( "/mIconExpressionSelect.svg" ) );
  mAddFeature->setIcon( QgsApplication::getThemeIcon( "/mActionNewTableRow.png" ) );

  // toggle editing
  bool canChangeAttributes = mLayer->dataProvider()->capabilities() & QgsVectorDataProvider::ChangeAttributeValues;
  bool canDeleteFeatures = mLayer->dataProvider()->capabilities() & QgsVectorDataProvider::DeleteFeatures;
  bool canAddAttributes = mLayer->dataProvider()->capabilities() & QgsVectorDataProvider::AddAttributes;
  bool canDeleteAttributes = mLayer->dataProvider()->capabilities() & QgsVectorDataProvider::DeleteAttributes;
  bool canAddFeatures = mLayer->dataProvider()->capabilities() & QgsVectorDataProvider::AddFeatures;

  mToggleEditingButton->blockSignals( true );
  mToggleEditingButton->setCheckable( true );
  mToggleEditingButton->setChecked( mLayer->isEditable() );
  mToggleEditingButton->setEnabled( canChangeAttributes && !mLayer->isReadOnly() );
  mToggleEditingButton->blockSignals( false );

  mSaveEditsButton->setEnabled( canChangeAttributes && mLayer->isEditable() );
  mOpenFieldCalculator->setEnabled(( canChangeAttributes || canAddAttributes ) && mLayer->isEditable() );
  mDeleteSelectedButton->setEnabled( canDeleteFeatures && mLayer->isEditable() );
  mAddAttribute->setEnabled( canAddAttributes && mLayer->isEditable() );
  mRemoveAttribute->setEnabled( canDeleteAttributes && mLayer->isEditable() );
  mAddFeature->setEnabled( canAddFeatures && mLayer->isEditable() && mLayer->geometryType() == QGis::NoGeometry );
  mAddFeature->setHidden( !canAddFeatures || mLayer->geometryType() != QGis::NoGeometry );

  mMainViewButtonGroup->setId( mTableViewButton, QgsDualView::AttributeTable );
  mMainViewButtonGroup->setId( mAttributeViewButton, QgsDualView::AttributeEditor );

  // Load default attribute table filter
  QgsAttributeTableFilterModel::FilterMode defaultFilterMode = ( QgsAttributeTableFilterModel::FilterMode ) settings.value( "/qgis/attributeTableBehaviour", QgsAttributeTableFilterModel::ShowAll ).toInt();

  switch ( defaultFilterMode )
  {
    case QgsAttributeTableFilterModel::ShowVisible:
      filterVisible();
      break;

    case QgsAttributeTableFilterModel::ShowSelected:
      filterSelected();
      break;

    case QgsAttributeTableFilterModel::ShowAll:
    default:
      filterShowAll();
      break;
  }
}
Exemple #26
0
QgsFieldCalculator::QgsFieldCalculator( QgsVectorLayer* vl )
    : QDialog()
    , mVectorLayer( vl )
    , mAttributeId( -1 )
{
  setupUi( this );

  if ( !vl )
    return;

  builder->setLayer( vl );
  builder->loadFieldNames();

  populateFields();
  populateOutputFieldTypes();

  connect( builder, SIGNAL( expressionParsed( bool ) ), this, SLOT( setOkButtonState() ) );

  QgsDistanceArea myDa;
  myDa.setSourceCrs( vl->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );
  builder->setGeomCalculator( myDa );

  //default values for field width and precision
  mOutputFieldWidthSpinBox->setValue( 10 );
  mOutputFieldPrecisionSpinBox->setValue( 3 );

  if ( vl->providerType() == "ogr" && vl->storageType() == "ESRI Shapefile" )
  {
    mOutputFieldNameLineEdit->setMaxLength( 10 );
  }

  mUpdateExistingGroupBox->setEnabled( vl->dataProvider()->capabilities() & QgsVectorDataProvider::ChangeAttributeValues );
  mNewFieldGroupBox->setEnabled( vl->dataProvider()->capabilities() & QgsVectorDataProvider::AddAttributes );

  Q_ASSERT( mNewFieldGroupBox->isEnabled() || mUpdateExistingGroupBox->isEnabled() );

  if ( mNewFieldGroupBox->isEnabled() )
  {
    mNewFieldGroupBox->setChecked( true );
  }
  else
  {
    mNewFieldGroupBox->setToolTip( tr( "Not available for layer" ) );
    mUpdateExistingGroupBox->setChecked( true );
    mUpdateExistingGroupBox->setCheckable( false );
  }

  if ( mUpdateExistingGroupBox->isEnabled() )
  {
    mUpdateExistingGroupBox->setChecked( !mNewFieldGroupBox->isEnabled() );
  }
  else
  {
    mUpdateExistingGroupBox->setToolTip( tr( "Not available for layer" ) );
    mNewFieldGroupBox->setChecked( true );
    mNewFieldGroupBox->setCheckable( false );
  }

  mOnlyUpdateSelectedCheckBox->setChecked( vl->selectedFeaturesIds().size() > 0 );
}
Exemple #27
0
QMap< QString, QString > QgsMapToolIdentify::featureDerivedAttributes( QgsFeature *feature, QgsMapLayer *layer, const QgsPoint& layerPoint )
{
  // Calculate derived attributes and insert:
  // measure distance or area depending on geometry type
  QMap< QString, QString > derivedAttributes;

  // init distance/area calculator
  QString ellipsoid = QgsProject::instance()->ellipsoid();
  QgsDistanceArea calc;
  calc.setEllipsoidalMode( mCanvas->hasCrsTransformEnabled() );
  calc.setEllipsoid( ellipsoid );
  calc.setSourceCrs( layer->crs().srsid() );

  QgsWkbTypes::Type wkbType = QgsWkbTypes::NoGeometry;
  QgsWkbTypes::GeometryType geometryType = QgsWkbTypes::NullGeometry;

  QgsVertexId vId;
  QgsPointV2 closestPoint;
  if ( feature->hasGeometry() )
  {
    geometryType = feature->geometry().type();
    wkbType = feature->geometry().geometry()->wkbType();
    //find closest vertex to clicked point
    closestPoint = QgsGeometryUtils::closestVertex( *feature->geometry().geometry(), QgsPointV2( layerPoint.x(), layerPoint.y() ), vId );
  }

  if ( QgsWkbTypes::isMultiType( wkbType ) )
  {
    QString str = QLocale::system().toString( static_cast<const QgsGeometryCollection*>( feature->geometry().geometry() )->numGeometries() );
    derivedAttributes.insert( tr( "Parts" ), str );
    str = QLocale::system().toString( vId.part + 1 );
    derivedAttributes.insert( tr( "Part number" ), str );
  }

  if ( geometryType == QgsWkbTypes::LineGeometry )
  {
    double dist = calc.measureLength( feature->geometry() );
    dist = calc.convertLengthMeasurement( dist, displayDistanceUnits() );
    QString str = formatDistance( dist );
    derivedAttributes.insert( tr( "Length" ), str );

    const QgsCurve* curve = dynamic_cast< const QgsCurve* >( feature->geometry().geometry() );
    if ( curve )
    {
      str = QLocale::system().toString( curve->nCoordinates() );
      derivedAttributes.insert( tr( "Vertices" ), str );

      //add details of closest vertex to identify point
      closestVertexAttributes( *curve, vId, layer, derivedAttributes );

      // Add the start and end points in as derived attributes
      QgsPoint pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, QgsPoint( curve->startPoint().x(), curve->startPoint().y() ) );
      str = formatXCoordinate( pnt );
      derivedAttributes.insert( tr( "firstX", "attributes get sorted; translation for lastX should be lexically larger than this one" ), str );
      str = formatYCoordinate( pnt );
      derivedAttributes.insert( tr( "firstY" ), str );
      pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, QgsPoint( curve->endPoint().x(), curve->endPoint().y() ) );
      str = formatXCoordinate( pnt );
      derivedAttributes.insert( tr( "lastX", "attributes get sorted; translation for firstX should be lexically smaller than this one" ), str );
      str = formatYCoordinate( pnt );
      derivedAttributes.insert( tr( "lastY" ), str );
    }
  }
  else if ( geometryType == QgsWkbTypes::PolygonGeometry )
  {
    double area = calc.measureArea( feature->geometry() );
    area = calc.convertAreaMeasurement( area, displayAreaUnits() );
    QString str = formatArea( area );
    derivedAttributes.insert( tr( "Area" ), str );

    double perimeter = calc.measurePerimeter( feature->geometry() );
    perimeter = calc.convertLengthMeasurement( perimeter, displayDistanceUnits() );
    str = formatDistance( perimeter );
    derivedAttributes.insert( tr( "Perimeter" ), str );

    str = QLocale::system().toString( feature->geometry().geometry()->nCoordinates() );
    derivedAttributes.insert( tr( "Vertices" ), str );

    //add details of closest vertex to identify point
    closestVertexAttributes( *feature->geometry().geometry(), vId, layer, derivedAttributes );
  }
  else if ( geometryType == QgsWkbTypes::PointGeometry &&
            QgsWkbTypes::flatType( wkbType ) == QgsWkbTypes::Point )
  {
    // Include the x and y coordinates of the point as a derived attribute
    QgsPoint pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, feature->geometry().asPoint() );
    QString str = formatXCoordinate( pnt );
    derivedAttributes.insert( "X", str );
    str = formatYCoordinate( pnt );
    derivedAttributes.insert( "Y", str );

    if ( QgsWkbTypes::hasZ( wkbType ) )
    {
      str = QLocale::system().toString( static_cast<const QgsPointV2*>( feature->geometry().geometry() )->z(), 'g', 10 );
      derivedAttributes.insert( "Z", str );
    }
    if ( QgsWkbTypes::hasM( wkbType ) )
    {
      str = QLocale::system().toString( static_cast<const QgsPointV2*>( feature->geometry().geometry() )->m(), 'g', 10 );
      derivedAttributes.insert( "M", str );
    }
  }

  return derivedAttributes;
}
Exemple #28
0
void QgsFieldCalculator::accept()
{

  // Set up QgsDistanceArea each time we (re-)calculate
  QgsDistanceArea myDa;

  myDa.setSourceCrs( mVectorLayer->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );


  QString calcString = builder->expressionText();
  QgsExpression exp( calcString );
  exp.setGeomCalculator( myDa );

  if ( !mVectorLayer || !mVectorLayer->isEditable() )
    return;

  if ( ! exp.prepare( mVectorLayer->pendingFields() ) )
  {
    QMessageBox::critical( 0, tr( "Evaluation error" ), exp.evalErrorString() );
    return;
  }

  QApplication::setOverrideCursor( Qt::WaitCursor );

  mVectorLayer->beginEditCommand( "Field calculator" );

  //update existing field
  if ( mUpdateExistingGroupBox->isChecked() || !mNewFieldGroupBox->isEnabled() )
  {
    QMap<QString, int>::const_iterator fieldIt = mFieldMap.find( mExistingFieldComboBox->currentText() );
    if ( fieldIt != mFieldMap.end() )
    {
      mAttributeId = fieldIt.value();
    }
  }
  else
  {
    //create new field
    QgsField newField( mOutputFieldNameLineEdit->text(),
                       ( QVariant::Type ) mOutputFieldTypeComboBox->itemData( mOutputFieldTypeComboBox->currentIndex(), Qt::UserRole ).toInt(),
                       mOutputFieldTypeComboBox->itemData( mOutputFieldTypeComboBox->currentIndex(), Qt::UserRole + 1 ).toString(),
                       mOutputFieldWidthSpinBox->value(),
                       mOutputFieldPrecisionSpinBox->value() );

    if ( !mVectorLayer->addAttribute( newField ) )
    {
      QMessageBox::critical( 0, tr( "Provider error" ), tr( "Could not add the new field to the provider." ) );
      mVectorLayer->destroyEditCommand();
      return;
    }

    //get index of the new field
    const QgsFields& fields = mVectorLayer->pendingFields();

    for ( int idx = 0; idx < fields.count(); ++idx )
    {
      if ( fields[idx].name() == mOutputFieldNameLineEdit->text() )
      {
        mAttributeId = idx;
        break;
      }
    }

    if ( ! exp.prepare( mVectorLayer->pendingFields() ) )
    {
      QMessageBox::critical( 0, tr( "Evaluation error" ), exp.evalErrorString() );
      return;
    }
  }

  if ( mAttributeId == -1 )
  {
    mVectorLayer->destroyEditCommand();
    QApplication::restoreOverrideCursor();
    return;
  }

  //go through all the features and change the new attribute
  QgsFeature feature;
  bool calculationSuccess = true;
  QString error;

  bool onlySelected = mOnlyUpdateSelectedCheckBox->isChecked();
  QgsFeatureIds selectedIds = mVectorLayer->selectedFeaturesIds();

  bool useGeometry = exp.needsGeometry();
  int rownum = 1;

  bool newField = !mUpdateExistingGroupBox->isChecked();
  QVariant emptyAttribute;
  if ( newField )
    emptyAttribute = QVariant( mVectorLayer->pendingFields()[mAttributeId].type() );

  QgsFeatureIterator fit = mVectorLayer->getFeatures( QgsFeatureRequest().setFlags( useGeometry ? QgsFeatureRequest::NoFlags : QgsFeatureRequest::NoGeometry ) );
  while ( fit.nextFeature( feature ) )
  {
    if ( onlySelected )
    {
      if ( !selectedIds.contains( feature.id() ) )
      {
        continue;
      }
    }

    exp.setCurrentRowNumber( rownum );
    QVariant value = exp.evaluate( &feature );
    if ( exp.hasEvalError() )
    {
      calculationSuccess = false;
      error = exp.evalErrorString();
      break;
    }
    else
    {
      mVectorLayer->changeAttributeValue( feature.id(), mAttributeId, value, newField ? emptyAttribute : feature.attributes().value( mAttributeId ) );
    }

    rownum++;
  }

  QApplication::restoreOverrideCursor();

  if ( !calculationSuccess )
  {
    QMessageBox::critical( 0, tr( "Error" ), tr( "An error occured while evaluating the calculation string:\n%1" ).arg( error ) );
    mVectorLayer->destroyEditCommand();
    return;
  }

  mVectorLayer->endEditCommand();
  QDialog::accept();
}
Exemple #29
0
QMap< QString, QString > QgsMapToolIdentify::featureDerivedAttributes( QgsFeature *feature, QgsMapLayer *layer, const QgsPoint& layerPoint )
{
  // Calculate derived attributes and insert:
  // measure distance or area depending on geometry type
  QMap< QString, QString > derivedAttributes;

  // init distance/area calculator
  QString ellipsoid = QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE );
  QgsDistanceArea calc;
  calc.setEllipsoidalMode( mCanvas->hasCrsTransformEnabled() );
  calc.setEllipsoid( ellipsoid );
  calc.setSourceCrs( layer->crs().srsid() );

  QgsWKBTypes::Type wkbType = QgsWKBTypes::NoGeometry;
  QGis::GeometryType geometryType = QGis::NoGeometry;

  QgsVertexId vId;
  QgsPointV2 closestPoint;
  if ( feature->constGeometry() )
  {
    geometryType = feature->constGeometry()->type();
    wkbType = feature->constGeometry()->geometry()->wkbType();
    //find closest vertex to clicked point
    closestPoint = QgsGeometryUtils::closestVertex( *feature->constGeometry()->geometry(), QgsPointV2( layerPoint.x(), layerPoint.y() ), vId );
  }

  if ( QgsWKBTypes::isMultiType( wkbType ) )
  {
    QString str = QLocale::system().toString( static_cast<QgsGeometryCollectionV2*>( feature->constGeometry()->geometry() )->numGeometries() );
    derivedAttributes.insert( tr( "Parts" ), str );
    str = QLocale::system().toString( vId.part + 1 );
    derivedAttributes.insert( tr( "Part number" ), str );
  }

  if ( geometryType == QGis::Line )
  {
    const QgsPolyline &pline = feature->constGeometry()->asPolyline();
    double dist = calc.measureLength( feature->constGeometry() );
    QGis::UnitType myDisplayUnits;
    convertMeasurement( calc, dist, myDisplayUnits, false );
    QString str = calc.textUnit( dist, 3, myDisplayUnits, false );  // dist and myDisplayUnits are out params
    derivedAttributes.insert( tr( "Length" ), str );
    str = QLocale::system().toString( pline.size() );
    derivedAttributes.insert( tr( "Vertices" ), str );

    //add details of closest vertex to identify point
    closestVertexAttributes( *feature->constGeometry()->geometry(), vId, layer, derivedAttributes );

    if ( QgsWKBTypes::flatType( wkbType ) == QgsWKBTypes::LineString )
    {
      // Add the start and end points in as derived attributes
      QgsPoint pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, pline.first() );
      str = QLocale::system().toString( pnt.x(), 'g', 10 );
      derivedAttributes.insert( tr( "firstX", "attributes get sorted; translation for lastX should be lexically larger than this one" ), str );
      str = QLocale::system().toString( pnt.y(), 'g', 10 );
      derivedAttributes.insert( tr( "firstY" ), str );
      pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, pline.last() );
      str = QLocale::system().toString( pnt.x(), 'g', 10 );
      derivedAttributes.insert( tr( "lastX", "attributes get sorted; translation for firstX should be lexically smaller than this one" ), str );
      str = QLocale::system().toString( pnt.y(), 'g', 10 );
      derivedAttributes.insert( tr( "lastY" ), str );
    }
  }
  else if ( geometryType == QGis::Polygon )
  {
    double area = calc.measureArea( feature->constGeometry() );
    double perimeter = calc.measurePerimeter( feature->constGeometry() );
    QGis::UnitType myDisplayUnits;
    convertMeasurement( calc, area, myDisplayUnits, true );  // area and myDisplayUnits are out params
    QString str = calc.textUnit( area, 3, myDisplayUnits, true );
    derivedAttributes.insert( tr( "Area" ), str );
    convertMeasurement( calc, perimeter, myDisplayUnits, false );  // perimeter and myDisplayUnits are out params
    str = calc.textUnit( perimeter, 3, myDisplayUnits, false );
    derivedAttributes.insert( tr( "Perimeter" ), str );

    str = QLocale::system().toString( feature->constGeometry()->geometry()->nCoordinates() );
    derivedAttributes.insert( tr( "Vertices" ), str );

    //add details of closest vertex to identify point
    closestVertexAttributes( *feature->constGeometry()->geometry(), vId, layer, derivedAttributes );
  }
  else if ( geometryType == QGis::Point &&
            QgsWKBTypes::flatType( wkbType ) == QgsWKBTypes::Point )
  {
    // Include the x and y coordinates of the point as a derived attribute
    QgsPoint pnt = mCanvas->mapSettings().layerToMapCoordinates( layer, feature->constGeometry()->asPoint() );
    QString str = QLocale::system().toString( pnt.x(), 'g', 10 );
    derivedAttributes.insert( "X", str );
    str = QLocale::system().toString( pnt.y(), 'g', 10 );
    derivedAttributes.insert( "Y", str );

    if ( QgsWKBTypes::hasZ( wkbType ) )
    {
      str = QLocale::system().toString( static_cast<QgsPointV2*>( feature->constGeometry()->geometry() )->z(), 'g', 10 );
      derivedAttributes.insert( "Z", str );
    }
    if ( QgsWKBTypes::hasM( wkbType ) )
    {
      str = QLocale::system().toString( static_cast<QgsPointV2*>( feature->constGeometry()->geometry() )->m(), 'g', 10 );
      derivedAttributes.insert( "M", str );
    }
  }

  return derivedAttributes;
}
Exemple #30
0
QgsDiagramProperties::QgsDiagramProperties( QgsVectorLayer* layer, QWidget* parent, QgsMapCanvas *canvas )
    : QWidget( parent )
    , mMapCanvas( canvas )
{
  mLayer = layer;
  if ( !layer )
  {
    return;
  }

  setupUi( this );

  // get rid of annoying outer focus rect on Mac
  mDiagramOptionsListWidget->setAttribute( Qt::WA_MacShowFocusRect, false );

  mDiagramTypeComboBox->blockSignals( true );
  QPixmap pix = QgsApplication::getThemePixmap( "diagramNone" );
  mDiagramTypeComboBox->addItem( pix, tr( "No diagrams" ), "None" );
  pix = QgsApplication::getThemePixmap( "pie-chart" );
  mDiagramTypeComboBox->addItem( pix, tr( "Pie chart" ), DIAGRAM_NAME_PIE );
  pix = QgsApplication::getThemePixmap( "text" );
  mDiagramTypeComboBox->addItem( pix, tr( "Text diagram" ), DIAGRAM_NAME_TEXT );
  pix = QgsApplication::getThemePixmap( "histogram" );
  mDiagramTypeComboBox->addItem( pix, tr( "Histogram" ), DIAGRAM_NAME_HISTOGRAM );
  mDiagramTypeComboBox->blockSignals( false );

  mScaleRangeWidget->setMapCanvas( QgisApp::instance()->mapCanvas() );
  mSizeFieldExpressionWidget->registerExpressionContextGenerator( this );

  mBackgroundColorButton->setColorDialogTitle( tr( "Select background color" ) );
  mBackgroundColorButton->setAllowAlpha( true );
  mBackgroundColorButton->setContext( "symbology" );
  mBackgroundColorButton->setShowNoColor( true );
  mBackgroundColorButton->setNoColorString( tr( "Transparent background" ) );
  mDiagramPenColorButton->setColorDialogTitle( tr( "Select pen color" ) );
  mDiagramPenColorButton->setAllowAlpha( true );
  mDiagramPenColorButton->setContext( "symbology" );
  mDiagramPenColorButton->setShowNoColor( true );
  mDiagramPenColorButton->setNoColorString( tr( "Transparent outline" ) );

  mMaxValueSpinBox->setShowClearButton( false );

  connect( mFixedSizeRadio, SIGNAL( toggled( bool ) ), this, SLOT( scalingTypeChanged() ) );
  connect( mAttributeBasedScalingRadio, SIGNAL( toggled( bool ) ), this, SLOT( scalingTypeChanged() ) );

  mDiagramUnitComboBox->setUnits( QgsUnitTypes::RenderUnitList() << QgsUnitTypes::RenderMillimeters << QgsUnitTypes::RenderMapUnits << QgsUnitTypes::RenderPixels );
  mDiagramLineUnitComboBox->setUnits( QgsUnitTypes::RenderUnitList() << QgsUnitTypes::RenderMillimeters << QgsUnitTypes::RenderMapUnits << QgsUnitTypes::RenderPixels );

  QgsWkbTypes::GeometryType layerType = layer->geometryType();
  if ( layerType == QgsWkbTypes::UnknownGeometry || layerType == QgsWkbTypes::NullGeometry )
  {
    mDiagramTypeComboBox->setEnabled( false );
    mDiagramFrame->setEnabled( false );
  }

  //insert placement options
  mPlacementComboBox->blockSignals( true );
  switch ( layerType )
  {
    case QgsWkbTypes::PointGeometry:
      mPlacementComboBox->addItem( tr( "Around Point" ), QgsDiagramLayerSettings::AroundPoint );
      mPlacementComboBox->addItem( tr( "Over Point" ), QgsDiagramLayerSettings::OverPoint );
      mLinePlacementFrame->setVisible( false );
      break;
    case QgsWkbTypes::LineGeometry:
      mPlacementComboBox->addItem( tr( "Around Line" ), QgsDiagramLayerSettings::Line );
      mPlacementComboBox->addItem( tr( "Over Line" ), QgsDiagramLayerSettings::Horizontal );
      mLinePlacementFrame->setVisible( true );
      break;
    case QgsWkbTypes::PolygonGeometry:
      mPlacementComboBox->addItem( tr( "Around Centroid" ), QgsDiagramLayerSettings::AroundPoint );
      mPlacementComboBox->addItem( tr( "Over Centroid" ), QgsDiagramLayerSettings::OverPoint );
      mPlacementComboBox->addItem( tr( "Perimeter" ), QgsDiagramLayerSettings::Line );
      mPlacementComboBox->addItem( tr( "Inside Polygon" ), QgsDiagramLayerSettings::Horizontal );
      mLinePlacementFrame->setVisible( false );
      break;
    default:
      break;
  }
  mPlacementComboBox->blockSignals( false );

  mLabelPlacementComboBox->addItem( tr( "Height" ), QgsDiagramSettings::Height );
  mLabelPlacementComboBox->addItem( tr( "x-height" ), QgsDiagramSettings::XHeight );

  mScaleDependencyComboBox->addItem( tr( "Area" ), true );
  mScaleDependencyComboBox->addItem( tr( "Diameter" ), false );

  mDataDefinedXComboBox->addItem( tr( "None" ), -1 );
  mDataDefinedYComboBox->addItem( tr( "None" ), -1 );

  mAngleOffsetComboBox->addItem( tr( "Top" ), 90 * 16 );
  mAngleOffsetComboBox->addItem( tr( "Right" ), 0 );
  mAngleOffsetComboBox->addItem( tr( "Bottom" ), 270 * 16 );
  mAngleOffsetComboBox->addItem( tr( "Left" ), 180 * 16 );

  mDataDefinedVisibilityComboBox->addItem( tr( "None" ), -1 );

  QSettings settings;

  // reset horiz strech of left side of options splitter (set to 1 for previewing in Qt Designer)
  QSizePolicy policy( mDiagramOptionsListFrame->sizePolicy() );
  policy.setHorizontalStretch( 0 );
  mDiagramOptionsListFrame->setSizePolicy( policy );
  if ( !settings.contains( QString( "/Windows/Diagrams/OptionsSplitState" ) ) )
  {
    // set left list widget width on intial showing
    QList<int> splitsizes;
    splitsizes << 115;
    mDiagramOptionsSplitter->setSizes( splitsizes );
  }

  // restore dialog, splitters and current tab
  mDiagramOptionsSplitter->restoreState( settings.value( QString( "/Windows/Diagrams/OptionsSplitState" ) ).toByteArray() );
  mDiagramOptionsListWidget->setCurrentRow( settings.value( QString( "/Windows/Diagrams/Tab" ), 0 ).toInt() );

  // field combo and expression button
  mSizeFieldExpressionWidget->setLayer( mLayer );
  QgsDistanceArea myDa;
  myDa.setSourceCrs( mLayer->crs().srsid() );
  myDa.setEllipsoidalMode( QgisApp::instance()->mapCanvas()->mapSettings().hasCrsTransformEnabled() );
  myDa.setEllipsoid( QgsProject::instance()->readEntry( "Measure", "/Ellipsoid", GEO_NONE ) );
  mSizeFieldExpressionWidget->setGeomCalculator( myDa );

  //insert all attributes into the combo boxes
  const QgsFields& layerFields = layer->fields();
  for ( int idx = 0; idx < layerFields.count(); ++idx )
  {
    QTreeWidgetItem *newItem = new QTreeWidgetItem( mAttributesTreeWidget );
    QString name = QString( "\"%1\"" ).arg( layerFields.at( idx ).name() );
    newItem->setText( 0, name );
    newItem->setData( 0, Qt::UserRole, name );
    newItem->setFlags( newItem->flags() & ~Qt::ItemIsDropEnabled );

    mDataDefinedXComboBox->addItem( layerFields.at( idx ).name(), idx );
    mDataDefinedYComboBox->addItem( layerFields.at( idx ).name(), idx );
    mDataDefinedVisibilityComboBox->addItem( layerFields.at( idx ).name(), idx );
  }

  const QgsDiagramRenderer* dr = layer->diagramRenderer();
  if ( !dr ) //no diagram renderer yet, insert reasonable default
  {
    mDiagramTypeComboBox->blockSignals( true );
    mDiagramTypeComboBox->setCurrentIndex( 0 );
    mDiagramTypeComboBox->blockSignals( false );
    mFixedSizeRadio->setChecked( true );
    mDiagramUnitComboBox->setUnit( QgsUnitTypes::RenderMillimeters );
    mDiagramLineUnitComboBox->setUnit( QgsUnitTypes::RenderMillimeters );
    mLabelPlacementComboBox->setCurrentIndex( mLabelPlacementComboBox->findText( tr( "x-height" ) ) );
    mDiagramSizeSpinBox->setEnabled( true );
    mDiagramSizeSpinBox->setValue( 15 );
    mLinearScaleFrame->setEnabled( false );
    mIncreaseMinimumSizeSpinBox->setEnabled( false );
    mIncreaseMinimumSizeLabel->setEnabled( false );
    mBarWidthSpinBox->setValue( 5 );
    mScaleVisibilityGroupBox->setChecked( layer->hasScaleBasedVisibility() );
    mScaleRangeWidget->setScaleRange( 1.0 / layer->maximumScale(), 1.0 / layer->minimumScale() ); // caution: layer uses scale denoms, widget uses true scales
    mShowAllCheckBox->setChecked( true );
    mDataDefinedVisibilityGroupBox->setChecked( false );
    mCheckBoxAttributeLegend->setChecked( true );
    mCheckBoxSizeLegend->setChecked( false );
    mSizeLegendSymbol.reset( QgsMarkerSymbol::createSimple( QgsStringMap() ) );

    switch ( layerType )
    {
      case QgsWkbTypes::PointGeometry:
        mPlacementComboBox->setCurrentIndex( mPlacementComboBox->findData( QgsDiagramLayerSettings::AroundPoint ) );
        break;
      case QgsWkbTypes::LineGeometry:
        mPlacementComboBox->setCurrentIndex( mPlacementComboBox->findData( QgsDiagramLayerSettings::Line ) );
        chkLineAbove->setChecked( true );
        chkLineBelow->setChecked( false );
        chkLineOn->setChecked( false );
        chkLineOrientationDependent->setChecked( false );
        break;
      case QgsWkbTypes::PolygonGeometry:
        mPlacementComboBox->setCurrentIndex( mPlacementComboBox->findData( QgsDiagramLayerSettings::AroundPoint ) );
        break;
      case QgsWkbTypes::UnknownGeometry:
      case QgsWkbTypes::NullGeometry:
        break;
    }
    mBackgroundColorButton->setColor( QColor( 255, 255, 255, 255 ) );
    //force a refresh of widget status to match diagram type
    on_mDiagramTypeComboBox_currentIndexChanged( mDiagramTypeComboBox->currentIndex() );
  }
  else // already a diagram renderer present
  {
    //single category renderer or interpolated one?
    if ( dr->rendererName() == "SingleCategory" )
    {
      mFixedSizeRadio->setChecked( true );
    }
    else
    {
      mAttributeBasedScalingRadio->setChecked( true );
    }
    mDiagramSizeSpinBox->setEnabled( mFixedSizeRadio->isChecked() );
    mLinearScaleFrame->setEnabled( mAttributeBasedScalingRadio->isChecked() );
    mCheckBoxAttributeLegend->setChecked( dr->attributeLegend() );
    mCheckBoxSizeLegend->setChecked( dr->sizeLegend() );
    mSizeLegendSymbol.reset( dr->sizeLegendSymbol() ? dr->sizeLegendSymbol()->clone() : QgsMarkerSymbol::createSimple( QgsStringMap() ) );
    QIcon icon = QgsSymbolLayerUtils::symbolPreviewIcon( mSizeLegendSymbol.data(), mButtonSizeLegendSymbol->iconSize() );
    mButtonSizeLegendSymbol->setIcon( icon );

    //assume single category or linearly interpolated diagram renderer for now
    QList<QgsDiagramSettings> settingList = dr->diagramSettings();
    if ( !settingList.isEmpty() )
    {
      mDiagramFrame->setEnabled( settingList.at( 0 ).enabled );
      mDiagramFont = settingList.at( 0 ).font;
      QSizeF size = settingList.at( 0 ).size;
      mBackgroundColorButton->setColor( settingList.at( 0 ).backgroundColor );
      mTransparencySpinBox->setValue( settingList.at( 0 ).transparency * 100.0 / 255.0 );
      mTransparencySlider->setValue( mTransparencySpinBox->value() );
      mDiagramPenColorButton->setColor( settingList.at( 0 ).penColor );
      mPenWidthSpinBox->setValue( settingList.at( 0 ).penWidth );
      mDiagramSizeSpinBox->setValue(( size.width() + size.height() ) / 2.0 );
      // caution: layer uses scale denoms, widget uses true scales
      mScaleRangeWidget->setScaleRange( 1.0 / ( settingList.at( 0 ).maxScaleDenominator > 0 ? settingList.at( 0 ).maxScaleDenominator : layer->maximumScale() ),
                                        1.0 / ( settingList.at( 0 ).minScaleDenominator > 0 ? settingList.at( 0 ).minScaleDenominator : layer->minimumScale() ) );
      mScaleVisibilityGroupBox->setChecked( settingList.at( 0 ).scaleBasedVisibility );
      mDiagramUnitComboBox->setUnit( settingList.at( 0 ).sizeType );
      mDiagramUnitComboBox->setMapUnitScale( settingList.at( 0 ).sizeScale );
      mDiagramLineUnitComboBox->setUnit( settingList.at( 0 ).lineSizeUnit );
      mDiagramLineUnitComboBox->setMapUnitScale( settingList.at( 0 ).lineSizeScale );

      if ( settingList.at( 0 ).labelPlacementMethod == QgsDiagramSettings::Height )
      {
        mLabelPlacementComboBox->setCurrentIndex( 0 );
      }
      else
      {
        mLabelPlacementComboBox->setCurrentIndex( 1 );
      }

      mAngleOffsetComboBox->setCurrentIndex( mAngleOffsetComboBox->findData( settingList.at( 0 ).angleOffset ) );

      mOrientationLeftButton->setProperty( "direction", QgsDiagramSettings::Left );
      mOrientationRightButton->setProperty( "direction", QgsDiagramSettings::Right );
      mOrientationUpButton->setProperty( "direction", QgsDiagramSettings::Up );
      mOrientationDownButton->setProperty( "direction", QgsDiagramSettings::Down );
      switch ( settingList.at( 0 ).diagramOrientation )
      {
        case QgsDiagramSettings::Left:
          mOrientationLeftButton->setChecked( true );
          break;

        case QgsDiagramSettings::Right:
          mOrientationRightButton->setChecked( true );
          break;

        case QgsDiagramSettings::Up:
          mOrientationUpButton->setChecked( true );
          break;

        case QgsDiagramSettings::Down:
          mOrientationDownButton->setChecked( true );
          break;
      }

      mBarWidthSpinBox->setValue( settingList.at( 0 ).barWidth );

      mIncreaseSmallDiagramsCheck->setChecked( settingList.at( 0 ).minimumSize != 0 );
      mIncreaseMinimumSizeSpinBox->setEnabled( mIncreaseSmallDiagramsCheck->isChecked() );
      mIncreaseMinimumSizeLabel->setEnabled( mIncreaseSmallDiagramsCheck->isChecked() );

      mIncreaseMinimumSizeSpinBox->setValue( settingList.at( 0 ).minimumSize );

      if ( settingList.at( 0 ).scaleByArea )
      {
        mScaleDependencyComboBox->setCurrentIndex( 0 );
      }
      else
      {
        mScaleDependencyComboBox->setCurrentIndex( 1 );
      }

      QList< QColor > categoryColors = settingList.at( 0 ).categoryColors;
      QList< QString > categoryAttributes = settingList.at( 0 ).categoryAttributes;
      QList< QString > categoryLabels = settingList.at( 0 ).categoryLabels;
      QList< QString >::const_iterator catIt = categoryAttributes.constBegin();
      QList< QColor >::const_iterator coIt = categoryColors.constBegin();
      QList< QString >::const_iterator labIt = categoryLabels.constBegin();
      for ( ; catIt != categoryAttributes.constEnd(); ++catIt, ++coIt, ++labIt )
      {
        QTreeWidgetItem *newItem = new QTreeWidgetItem( mDiagramAttributesTreeWidget );
        newItem->setText( 0, *catIt );
        newItem->setData( 0, Qt::UserRole, *catIt );
        newItem->setFlags( newItem->flags() & ~Qt::ItemIsDropEnabled );
        QColor col( *coIt );
        col.setAlpha( 255 );
        newItem->setBackground( 1, QBrush( col ) );
        newItem->setText( 2, *labIt );
        newItem->setFlags( newItem->flags() | Qt::ItemIsEditable );
      }
    }

    if ( dr->rendererName() == "LinearlyInterpolated" )
    {
      const QgsLinearlyInterpolatedDiagramRenderer* lidr = dynamic_cast<const QgsLinearlyInterpolatedDiagramRenderer*>( dr );
      if ( lidr )
      {
        mDiagramSizeSpinBox->setEnabled( false );
        mLinearScaleFrame->setEnabled( true );
        mMaxValueSpinBox->setValue( lidr->upperValue() );
        mSizeSpinBox->setValue(( lidr->upperSize().width() + lidr->upperSize().height() ) / 2 );
        if ( lidr->classificationAttributeIsExpression() )
        {
          mSizeFieldExpressionWidget->setField( lidr->classificationAttributeExpression() );
        }
        else
        {
          mSizeFieldExpressionWidget->setField( mLayer->fields().at( lidr->classificationAttribute() ).name() );
        }
      }
    }

    const QgsDiagramLayerSettings *dls = layer->diagramLayerSettings();
    if ( dls )
    {
      mDiagramDistanceSpinBox->setValue( dls->distance() );
      mPrioritySlider->setValue( dls->getPriority() );
      mZIndexSpinBox->setValue( dls->getZIndex() );
      mDataDefinedXComboBox->setCurrentIndex( mDataDefinedXComboBox->findData( dls->xPosColumn ) );
      mDataDefinedYComboBox->setCurrentIndex( mDataDefinedYComboBox->findData( dls->yPosColumn ) );
      if ( dls->xPosColumn != -1 || dls->yPosColumn != -1 )
      {
        mDataDefinedPositionGroupBox->setChecked( true );
      }
      mPlacementComboBox->setCurrentIndex( mPlacementComboBox->findData( dls->getPlacement() ) );

      chkLineAbove->setChecked( dls->linePlacementFlags() & QgsDiagramLayerSettings::AboveLine );
      chkLineBelow->setChecked( dls->linePlacementFlags() & QgsDiagramLayerSettings::BelowLine );
      chkLineOn->setChecked( dls->linePlacementFlags() & QgsDiagramLayerSettings::OnLine );
      if ( !( dls->linePlacementFlags() & QgsDiagramLayerSettings::MapOrientation ) )
        chkLineOrientationDependent->setChecked( true );

      mShowAllCheckBox->setChecked( dls->showAllDiagrams() );
      mDataDefinedVisibilityComboBox->setCurrentIndex( mDataDefinedVisibilityComboBox->findData( dls->showColumn ) );
      if ( dls->showColumn != -1 )
      {
        mDataDefinedVisibilityGroupBox->setChecked( true );
      }
    }

    if ( dr->diagram() )
    {
      mDiagramType = dr->diagram()->diagramName();

      mDiagramTypeComboBox->blockSignals( true );
      mDiagramTypeComboBox->setCurrentIndex( settingList.at( 0 ).enabled ? mDiagramTypeComboBox->findData( mDiagramType ) : 0 );
      mDiagramTypeComboBox->blockSignals( false );
      //force a refresh of widget status to match diagram type
      on_mDiagramTypeComboBox_currentIndexChanged( mDiagramTypeComboBox->currentIndex() );
      if ( mDiagramTypeComboBox->currentIndex() == -1 )
      {
        QMessageBox::warning( this, tr( "Unknown diagram type." ),
                              tr( "The diagram type '%1' is unknown. A default type is selected for you." ).arg( mDiagramType ), QMessageBox::Ok );
        mDiagramTypeComboBox->setCurrentIndex( mDiagramTypeComboBox->findData( DIAGRAM_NAME_PIE ) );
      }
    }
  } // if ( !dr )

  connect( mAddAttributeExpression, SIGNAL( clicked() ), this, SLOT( showAddAttributeExpressionDialog() ) );
  connect( mTransparencySlider, SIGNAL( valueChanged( int ) ), mTransparencySpinBox, SLOT( setValue( int ) ) );
  connect( mTransparencySpinBox, SIGNAL( valueChanged( int ) ), mTransparencySlider, SLOT( setValue( int ) ) );
}