diff --git a/src/app/qgslabelinggui.cpp b/src/app/qgslabelinggui.cpp index 7f288bf3301..2c98984407e 100644 --- a/src/app/qgslabelinggui.cpp +++ b/src/app/qgslabelinggui.cpp @@ -99,6 +99,8 @@ QgsLabelingGui::QgsLabelingGui( QgsPalLabeling* lbl, QgsVectorLayer* layer, QgsM int distUnitIndex = lyr.distInMapUnits ? 1 : 0; mXQuadOffset = lyr.xQuadOffset; mYQuadOffset = lyr.yQuadOffset; + mCentroidRadioWhole->setChecked( lyr.centroidWhole ); + mCentroidFrame->setVisible( false ); switch ( lyr.placement ) { case QgsPalLayerSettings::AroundPoint: @@ -106,6 +108,8 @@ QgsLabelingGui::QgsLabelingGui( QgsPalLabeling* lbl, QgsVectorLayer* layer, QgsM radAroundCentroid->setChecked( true ); spinDistPoint->setValue( lyr.dist ); mPointDistanceUnitComboBox->setCurrentIndex( distUnitIndex ); + mCentroidFrame->setVisible( layer->geometryType() == QGis::Polygon ); + //spinAngle->setValue( lyr.angle ); break; case QgsPalLayerSettings::OverPoint: @@ -126,6 +130,7 @@ QgsLabelingGui::QgsLabelingGui( QgsPalLabeling* lbl, QgsVectorLayer* layer, QgsM mPointOffsetYOffsetSpinBox->setValue( lyr.yOffset ); mPointOffsetUnitsComboBox->setCurrentIndex( lyr.labelOffsetInMapUnits ? 1 : 0 ); mPointOffsetAngleSpinBox->setValue( lyr.angleOffset ); + mCentroidFrame->setVisible( layer->geometryType() == QGis::Polygon ); break; case QgsPalLayerSettings::Line: @@ -290,6 +295,7 @@ QgsPalLayerSettings QgsLabelingGui::layerSettings() lyr.dist = 0; lyr.placementFlags = 0; + lyr.centroidWhole = mCentroidRadioWhole->isChecked(); if (( stackedPlacement->currentWidget() == pagePoint && radAroundPoint->isChecked() ) || ( stackedPlacement->currentWidget() == pagePolygon && radAroundCentroid->isChecked() ) ) { @@ -820,15 +826,20 @@ void QgsLabelingGui::changeBufferColor() void QgsLabelingGui::updateOptions() { + mCentroidFrame->setVisible( false ); if (( stackedPlacement->currentWidget() == pagePoint && radAroundPoint->isChecked() ) || ( stackedPlacement->currentWidget() == pagePolygon && radAroundCentroid->isChecked() ) ) { stackedOptions->setCurrentWidget( pageOptionsPoint ); + mCentroidFrame->setVisible( stackedPlacement->currentWidget() == pagePolygon + && radAroundCentroid->isChecked() ); } else if (( stackedPlacement->currentWidget() == pagePoint && radOverPoint->isChecked() ) || ( stackedPlacement->currentWidget() == pagePolygon && radOverCentroid->isChecked() ) ) { stackedOptions->setCurrentWidget( pageOptionsPointOffset ); + mCentroidFrame->setVisible( stackedPlacement->currentWidget() == pagePolygon + && radOverCentroid->isChecked() ); } else if (( stackedPlacement->currentWidget() == pageLine && radLineParallel->isChecked() ) || ( stackedPlacement->currentWidget() == pagePolygon && radPolygonPerimeter->isChecked() ) diff --git a/src/core/qgspallabeling.cpp b/src/core/qgspallabeling.cpp index ac5bdcc2b8b..4e0935e26f7 100644 --- a/src/core/qgspallabeling.cpp +++ b/src/core/qgspallabeling.cpp @@ -147,6 +147,7 @@ QgsPalLayerSettings::QgsPalLayerSettings() xOffset = 0; yOffset = 0; angleOffset = 0; + centroidWhole = false; //textFont = QFont(); textNamedStyle = QString( "" ); textColor = Qt::black; @@ -193,6 +194,7 @@ QgsPalLayerSettings::QgsPalLayerSettings( const QgsPalLayerSettings& s ) xOffset = s.xOffset; yOffset = s.yOffset; angleOffset = s.angleOffset; + centroidWhole = s.centroidWhole; textFont = s.textFont; textNamedStyle = s.textNamedStyle; textColor = s.textColor; @@ -363,6 +365,7 @@ void QgsPalLayerSettings::readFromLayer( QgsVectorLayer* layer ) xOffset = layer->customProperty( "labeling/xOffset", QVariant( 0.0 ) ).toDouble(); yOffset = layer->customProperty( "labeling/yOffset", QVariant( 0.0 ) ).toDouble(); angleOffset = layer->customProperty( "labeling/angleOffset", QVariant( 0.0 ) ).toDouble(); + centroidWhole = layer->customProperty( "labeling/centroidWhole", QVariant( false ) ).toBool(); QString fontFamily = layer->customProperty( "labeling/fontFamily" ).toString(); double fontSize = layer->customProperty( "labeling/fontSize" ).toDouble(); int fontWeight = layer->customProperty( "labeling/fontWeight" ).toInt(); @@ -421,6 +424,7 @@ void QgsPalLayerSettings::writeToLayer( QgsVectorLayer* layer ) layer->setCustomProperty( "labeling/xOffset", xOffset ); layer->setCustomProperty( "labeling/yOffset", yOffset ); layer->setCustomProperty( "labeling/angleOffset", angleOffset ); + layer->setCustomProperty( "labeling/centroidWhole", centroidWhole ); layer->setCustomProperty( "labeling/fontFamily", textFont.family() ); layer->setCustomProperty( "labeling/namedStyle", textNamedStyle ); @@ -676,10 +680,29 @@ void QgsPalLayerSettings::registerFeature( QgsVectorLayer* layer, QgsFeature& f return; } + // whether we're going to create a centroid for polygon + bool centroidPoly = (( placement == QgsPalLayerSettings::AroundPoint + || placement == QgsPalLayerSettings::OverPoint ) + && geom->type() == QGis::Polygon ); + + // CLIP the geometry if it is bigger than the extent + // don't clip if centroid is requested for whole feature + bool do_clip = false; + if ( !centroidPoly || ( centroidPoly && !centroidWhole ) ) + { + do_clip = !extentGeom->contains( geom ); + if ( do_clip ) + { + geom = geom->intersection( extentGeom ); // creates new geometry + if ( !geom ) + { + return; + } + } + } + // convert centroids to points before processing to use GEOS instead of PAL calculation - if (( placement == QgsPalLayerSettings::AroundPoint - || placement == QgsPalLayerSettings::OverPoint ) - && geom->type() == QGis::Polygon ) + if ( centroidPoly ) { QgsGeometry* centroidpt = geom->centroid(); if ( centroidpt->isGeosValid() && extentGeom->contains( centroidpt ) ) @@ -692,34 +715,17 @@ void QgsPalLayerSettings::registerFeature( QgsVectorLayer* layer, QgsFeature& f } else { - // invalid geom type, skip registering feature with PAL + // invalid geom type or outside extents return; } } - // CLIP the geometry if it is bigger than the extent - QgsGeometry* geomClipped = NULL; - GEOSGeometry* geos_geom; - bool do_clip = !extentGeom->contains( geom ); - if ( do_clip ) - { - geomClipped = geom->intersection( extentGeom ); // creates new geometry - if ( !geomClipped ) - { - return; - } - geos_geom = geomClipped->asGeos(); - } - else - { - geos_geom = geom->asGeos(); - } + GEOSGeometry* geos_geom = geom->asGeos(); if ( geos_geom == NULL ) return; // invalid geometry GEOSGeometry* geos_geom_clone = GEOSGeom_clone( geos_geom ); - if ( do_clip ) - delete geomClipped; + //data defined position / alignment / rotation? bool dataDefinedPosition = false; @@ -921,12 +927,11 @@ void QgsPalLayerSettings::registerFeature( QgsVectorLayer* layer, QgsFeature& f pal::LabelPosition* lp = new LabelPosition( 1, xPos, yPos, labelX, labelY, ( angleOffset * M_PI / 180 ), 0.0, fpart ); + // lp->getWidth or lp->getHeight doesn't account for rotation, get bbox instead double amin[2], amax[2]; lp->getBoundingBox( amin, amax ); QgsRectangle lblrect = QgsRectangle( amin[0], amin[1], amax[0], amax[1] ); -// labelW = lp->getWidth(); -// labelH = lp->getHeight(); labelW = lblrect.width(); labelH = lblrect.height(); delete fpart; diff --git a/src/core/qgspallabeling.h b/src/core/qgspallabeling.h index 063c9721add..654178a0cdb 100644 --- a/src/core/qgspallabeling.h +++ b/src/core/qgspallabeling.h @@ -123,6 +123,7 @@ class CORE_EXPORT QgsPalLayerSettings int xQuadOffset, yQuadOffset; double xOffset, yOffset; // offset from point in mm or map units double angleOffset; // rotation applied to offset labels + bool centroidWhole; // whether centroid calculated from whole or visible polygon QFont textFont; QString textNamedStyle; QColor textColor; diff --git a/src/ui/qgslabelingguibase.ui b/src/ui/qgslabelingguibase.ui index 202c07aaaee..845c4b02b47 100644 --- a/src/ui/qgslabelingguibase.ui +++ b/src/ui/qgslabelingguibase.ui @@ -1470,7 +1470,7 @@ 0 0 686 - 485 + 521 @@ -1659,7 +1659,7 @@ - 2 + 1 @@ -1762,342 +1762,471 @@ - - + + 0 - - - - - - Label distance - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - 4 - - - 999999999.000000000000000 - - - - - - - Rotation - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - false - - - - - - - degrees - - - - - - + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 12 + + + 12 + + + 12 + + + 0 + + + + + + 0 + 0 + + - In mm + Centroid of + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + + 0 + 0 + - - - In map units + visible polygon - - - - - - - - - - - Above line - - - true - - - - - - - On line - - - - - - - Below line - - - - - - - - 0 + + true + + + + + + + + 0 + 0 + - - - - - - Label distance - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - 4 - - - 999999999.000000000000000 - - - - - - - - In mm - - - - - In map units - - - - - - - - - - Line orientation dependent position - - - - - - - - - - - - - - - - 0 - 0 - - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - X - - - - - - 4 - - - -9999999.000000000000000 - - - 9999999.000000000000000 - - - - - - - degrees - - - - - - - - 0 - 0 - - - - mm + whole polygon - - - - map units - - - - - - - - - 0 - 0 - - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - Y - - - - - - 4 - - - -9999999.000000000000000 - - - 9999999.000000000000000 - - - - - - - Rotation - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - 8 - - - - - Right - - - + + + + + + + + + 1 + + + - - - Above Right - + + + + In mm + + + + + In map units + + - - + + - Above Left + degrees - + + + false + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + - Over + Rotation + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter + + + + + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + 4 + + + 999999999.000000000000000 + + + + + + + + 0 + 0 + + + + Label distance + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + + + Above line true - - + + - Above + On line - - + + - Left + Below line - - - - Below Left - - - - - - - Below - - - - - - - Below Right - + + + + + 0 + + + + + + + + 0 + 0 + + + + Label distance + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter + + + + + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + 4 + + + 999999999.000000000000000 + + + + + + + + In mm + + + + + In map units + + + + + + + + + + Line orientation dependent position + + + + - - - - - true - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - -360.000000000000000 - - - 360.000000000000000 - - - - - - + + + + + + + + + 0 + 0 + + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + X + + + + + + 4 + + + -9999999.000000000000000 + + + 9999999.000000000000000 + + + + + + + + 0 + 0 + + + + 1 + + + + mm + + + + + map units + + + + + + + + + 0 + 0 + + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + Y + + + + + + 4 + + + -9999999.000000000000000 + + + 9999999.000000000000000 + + + + + + + 8 + + + + + Right + + + + + + + Above Right + + + + + + + Above Left + + + + + + + Over + + + true + + + + + + + Above + + + + + + + Left + + + + + + + Below Left + + + + + + + Below + + + + + + + Below Right + + + + + + + + + + + + 0 + 0 + + + + Rotation + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + true + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + -360.000000000000000 + + + 360.000000000000000 + + + + + + + + 0 + 0 + + + + degrees + + + + + + + + + + @@ -2653,12 +2782,12 @@ setValue(int) - 341 - 286 + 319 + 408 - 415 - 288 + 393 + 410 @@ -2669,12 +2798,12 @@ setValue(int) - 325 - 499 + 319 + 547 - 397 - 500 + 391 + 549 @@ -2685,12 +2814,12 @@ setValue(int) - 397 - 500 + 391 + 549 - 325 - 499 + 319 + 547 @@ -2701,12 +2830,44 @@ setValue(int) - 415 - 288 + 393 + 410 - 341 - 286 + 319 + 408 + + + + + radOverCentroid + toggled(bool) + mCentroidFrame + setVisible(bool) + + + 105 + 154 + + + 362 + 131 + + + + + radAroundCentroid + toggled(bool) + mCentroidFrame + setVisible(bool) + + + 141 + 187 + + + 404 + 128