LCOV - code coverage report
Current view: top level - core/labeling - qgslabelsearchtree.cpp (source / functions) Hit Total Coverage
Test: coverage.info.cleaned Lines: 0 85 0.0 %
Date: 2021-03-26 12:19:53 Functions: 0 0 -
Branches: 0 0 -

           Branch data     Line data    Source code
       1                 :            : /***************************************************************************
       2                 :            :     qgslabelsearchtree.cpp
       3                 :            :     ---------------------
       4                 :            :     begin                : November 2010
       5                 :            :     copyright            : (C) 2010 by Marco Hugentobler
       6                 :            :     email                : marco dot hugentobler at sourcepole dot ch
       7                 :            :  ***************************************************************************
       8                 :            :  *                                                                         *
       9                 :            :  *   This program is free software; you can redistribute it and/or modify  *
      10                 :            :  *   it under the terms of the GNU General Public License as published by  *
      11                 :            :  *   the Free Software Foundation; either version 2 of the License, or     *
      12                 :            :  *   (at your option) any later version.                                   *
      13                 :            :  *                                                                         *
      14                 :            :  ***************************************************************************/
      15                 :            : #include "qgslabelsearchtree.h"
      16                 :            : #include "labelposition.h"
      17                 :            : 
      18                 :          0 : QgsLabelSearchTree::QgsLabelSearchTree() = default;
      19                 :            : 
      20                 :          0 : QgsLabelSearchTree::~QgsLabelSearchTree() = default;
      21                 :            : 
      22                 :          0 : void QgsLabelSearchTree::label( const QgsPointXY &point, QList<QgsLabelPosition *> &posList ) const
      23                 :            : {
      24                 :          0 :   QgsPointXY p( point );
      25                 :            : 
      26                 :          0 :   QList<QgsLabelPosition *> searchResults;
      27                 :          0 :   mSpatialIndex.intersects( QgsRectangle( p.x() - 0.1, p.y() - 0.1, p.x() + 0.1, p.y() + 0.1 ), [&searchResults]( const QgsLabelPosition * pos ) -> bool
      28                 :            :   {
      29                 :          0 :     searchResults.push_back( const_cast< QgsLabelPosition * >( pos ) );
      30                 :          0 :     return true;
      31                 :            :   } );
      32                 :            : 
      33                 :            :   //tolerance +-0.1 could be high in case of degree crs, so check if p is really contained in the results
      34                 :          0 :   posList.clear();
      35                 :          0 :   QList<QgsLabelPosition *>::const_iterator resultIt = searchResults.constBegin();
      36                 :          0 :   for ( ; resultIt != searchResults.constEnd(); ++resultIt )
      37                 :            :   {
      38                 :          0 :     if ( ( *resultIt )->labelGeometry.contains( &p ) )
      39                 :            :     {
      40                 :          0 :       posList.push_back( *resultIt );
      41                 :          0 :     }
      42                 :          0 :   }
      43                 :          0 : }
      44                 :            : 
      45                 :          0 : void QgsLabelSearchTree::labelsInRect( const QgsRectangle &r, QList<QgsLabelPosition *> &posList ) const
      46                 :            : {
      47                 :          0 :   QList<QgsLabelPosition *> searchResults;
      48                 :          0 :   mSpatialIndex.intersects( r, [&searchResults]( const QgsLabelPosition * pos )->bool
      49                 :            :   {
      50                 :          0 :     searchResults.push_back( const_cast< QgsLabelPosition * >( pos ) );
      51                 :          0 :     return true;
      52                 :            :   } );
      53                 :            : 
      54                 :          0 :   posList.clear();
      55                 :          0 :   QList<QgsLabelPosition *>::const_iterator resultIt = searchResults.constBegin();
      56                 :          0 :   for ( ; resultIt != searchResults.constEnd(); ++resultIt )
      57                 :            :   {
      58                 :          0 :     if ( ( *resultIt )->labelGeometry.intersects( r ) )
      59                 :            :     {
      60                 :          0 :       posList.push_back( *resultIt );
      61                 :          0 :     }
      62                 :          0 :   }
      63                 :          0 : }
      64                 :            : 
      65                 :          0 : bool QgsLabelSearchTree::insertLabel( pal::LabelPosition *labelPos, QgsFeatureId featureId, const QString &layerName, const QString &labeltext, const QFont &labelfont, bool diagram, bool pinned, const QString &providerId, bool isUnplaced )
      66                 :            : {
      67                 :          0 :   if ( !labelPos )
      68                 :            :   {
      69                 :          0 :     return false;
      70                 :            :   }
      71                 :            : 
      72                 :          0 :   QVector<QgsPointXY> cornerPoints;
      73                 :          0 :   cornerPoints.reserve( 4 );
      74                 :          0 :   double xMin = std::numeric_limits< double >::max();
      75                 :          0 :   double yMin = std::numeric_limits< double >::max();
      76                 :          0 :   double xMax = std::numeric_limits< double >::lowest();
      77                 :          0 :   double yMax = std::numeric_limits< double >::lowest();
      78                 :          0 :   for ( int i = 0; i < 4; ++i )
      79                 :            :   {
      80                 :            :     // we have to transform the bounding box to convert pre-rotated label positions back to real world locations
      81                 :          0 :     QPointF res = mTransform.map( QPointF( labelPos->getX( i ), labelPos->getY( i ) ) );
      82                 :          0 :     cornerPoints.push_back( QgsPointXY( res ) );
      83                 :          0 :     xMin = std::min( xMin, res.x() );
      84                 :          0 :     xMax = std::max( xMax, res.x() );
      85                 :          0 :     yMin = std::min( yMin, res.y() );
      86                 :          0 :     yMax = std::max( yMax, res.y() );
      87                 :          0 :   }
      88                 :            : 
      89                 :          0 :   const QgsRectangle bounds( xMin, yMin, xMax, yMax );
      90                 :          0 :   QgsGeometry labelGeometry( QgsGeometry::fromPolygonXY( QVector<QgsPolylineXY>() << cornerPoints ) );
      91                 :          0 :   std::unique_ptr< QgsLabelPosition > newEntry = std::make_unique< QgsLabelPosition >( featureId, labelPos->getAlpha() + mMapSettings.rotation(), cornerPoints, bounds,
      92                 :          0 :       labelPos->getWidth(), labelPos->getHeight(), layerName, labeltext, labelfont, labelPos->getUpsideDown(), diagram, pinned, providerId, labelGeometry, isUnplaced );
      93                 :          0 :   mSpatialIndex.insert( newEntry.get(), bounds );
      94                 :          0 :   mOwnedPositions.emplace_back( std::move( newEntry ) );
      95                 :            : 
      96                 :          0 :   if ( pal::LabelPosition *next = labelPos->nextPart() )
      97                 :            :   {
      98                 :          0 :     return insertLabel( next, featureId, layerName, labeltext, labelfont, diagram, pinned, providerId, isUnplaced );
      99                 :            :   }
     100                 :          0 :   return true;
     101                 :          0 : }
     102                 :            : 
     103                 :          0 : bool QgsLabelSearchTree::insertCallout( const QgsCalloutPosition &position )
     104                 :            : {
     105                 :          0 :   const QPointF origin = position.origin();
     106                 :          0 :   const QPointF destination = position.destination();
     107                 :            : 
     108                 :          0 :   std::unique_ptr< QgsCalloutPosition > newEntry = std::make_unique< QgsCalloutPosition >( position );
     109                 :            : 
     110                 :          0 :   mCalloutIndex.insert( newEntry.get(), QgsRectangle( origin.x(), origin.y(), origin.x(), origin.y() ) );
     111                 :          0 :   mCalloutIndex.insert( newEntry.get(), QgsRectangle( destination.x(), destination.y(), destination.x(), destination.y() ) );
     112                 :            : 
     113                 :          0 :   mOwnedCalloutPositions.emplace_back( std::move( newEntry ) );
     114                 :            : 
     115                 :            :   return true;
     116                 :          0 : }
     117                 :            : 
     118                 :          0 : QList<const QgsCalloutPosition *> QgsLabelSearchTree::calloutsInRectangle( const QgsRectangle &rectangle ) const
     119                 :            : {
     120                 :          0 :   QList<const QgsCalloutPosition *> searchResults;
     121                 :          0 :   mCalloutIndex.intersects( rectangle, [&searchResults]( const QgsCalloutPosition * pos )->bool
     122                 :            :   {
     123                 :          0 :     searchResults.push_back( pos );
     124                 :          0 :     return true;
     125                 :            :   } );
     126                 :            : 
     127                 :          0 :   std::sort( searchResults.begin(), searchResults.end() );
     128                 :          0 :   searchResults.erase( std::unique( searchResults.begin(), searchResults.end() ), searchResults.end() );
     129                 :            : 
     130                 :          0 :   return searchResults;
     131                 :          0 : }
     132                 :            : 
     133                 :          0 : void QgsLabelSearchTree::setMapSettings( const QgsMapSettings &settings )
     134                 :            : {
     135                 :          0 :   mMapSettings = settings;
     136                 :            : 
     137                 :          0 :   if ( !qgsDoubleNear( mMapSettings.rotation(), 0.0 ) )
     138                 :            :   {
     139                 :            :     // build a transform to convert points from real world to pre-rotated label positions
     140                 :          0 :     const QgsPointXY center = mMapSettings.visibleExtent().center();
     141                 :          0 :     mTransform = QTransform::fromTranslate( center.x(), center.y() );
     142                 :          0 :     mTransform.rotate( mMapSettings.rotation() );
     143                 :          0 :     mTransform.translate( -center.x(), -center.y() );
     144                 :          0 :   }
     145                 :            :   else
     146                 :            :   {
     147                 :          0 :     mTransform = QTransform();
     148                 :            :   }
     149                 :          0 : }
     150                 :            : 
     151                 :            : 
     152                 :          0 : void QgsLabelSearchTree::clear()
     153                 :            : {
     154                 :            : 
     155                 :          0 : }

Generated by: LCOV version 1.14