Skip to content
Permalink
Browse files

Logic tweaks

  • Loading branch information
nyalldawson committed Apr 30, 2020
1 parent 17c47f5 commit fd3969f04614ae981b057d0adf6a2dd97a60302f
Showing with 11 additions and 4 deletions.
  1. +1 −1 src/core/labeling/qgspallabeling.cpp
  2. +10 −3 src/core/pal/feature.cpp
@@ -2517,7 +2517,7 @@ void QgsPalLayerSettings::registerFeature( const QgsFeature &f, QgsRenderContext
|| placement == QgsPalLayerSettings::OverPoint ||
placement == QgsPalLayerSettings::Free ) && polygonPlacementFlags() & QgsLabeling::PolygonPlacementFlag::AllowPlacementOutsideOfPolygon ) )
{
distance = std::max( distance, 1.0 );
distance = std::max( distance, 2.0 );
}

if ( !qgsDoubleNear( distance, 0.0 ) )
@@ -1854,9 +1854,14 @@ std::size_t FeaturePart::createCandidatesOutsidePolygon( std::vector<std::unique
getCentroid( cx, cy, false );

GEOSContextHandle_t ctxt = QgsGeos::getGEOSHandler();
geos::unique_ptr buffer( GEOSBuffer_r( ctxt, geos(), mLF->distLabel(), 1 ) );

// be a bit sneaky and only buffer out 50% here, and then do the remaining 50% when we make the label candidate itself.
// this avoids candidates being created immediately over the buffered ring and always intersecting with it...
geos::unique_ptr buffer( GEOSBuffer_r( ctxt, geos(), distanceToLabel * 0.5, 1 ) );
std::unique_ptr< QgsAbstractGeometry> gg( QgsGeos::fromGeos( buffer.get() ) );

geos::prepared_unique_ptr preparedBuffer( GEOSPrepare_r( ctxt, buffer.get() ) );

const QgsPolygon *poly = qgsgeometry_cast< const QgsPolygon * >( gg.get() );
if ( !poly )
return candidatesCreated;
@@ -1891,12 +1896,14 @@ std::size_t FeaturePart::createCandidatesOutsidePolygon( std::vector<std::unique
LabelPosition::Quadrant quadrant = LabelPosition::QuadrantAboveLeft;

// Satisfy R2: Label should be placed entirely outside at some distance from the area feature.
createCandidateAtOrderedPositionOverPoint( labelX, labelY, quadrant, x, y, labelWidth, labelHeight, position, distanceToLabel, visualMargin, 0, 0 );
createCandidateAtOrderedPositionOverPoint( labelX, labelY, quadrant, x, y, labelWidth, labelHeight, position, distanceToLabel * 0.5, visualMargin, 0, 0 );

std::unique_ptr< LabelPosition > candidate = qgis::make_unique< LabelPosition >( i, labelX, labelY, labelWidth, labelHeight, labelAngle, 0, this, false, quadrant );
if ( candidate->intersects( preparedGeom() ) )
if ( candidate->intersects( preparedBuffer.get() ) )
{
// satisfy R3. Name should not cross the boundary of its area feature.

// actually, we use the buffered geometry here, because a label shouldn't be closer to the polygon then the minimum distance value
return;
}

0 comments on commit fd3969f

Please sign in to comment.
You can’t perform that action at this time.