45 : mProvider( provider )
50 , mLabelLayer( toLabel )
51 , mDisplayAll( displayAll )
52 , mCentroidInside( false )
53 , mArrangement( arrangement )
54 , mArrangementFlags( nullptr )
55 , mMode( LabelPerFeature )
56 , mMergeLines( false )
57 , mUpsidedownLabels( Upright )
59 mFeatureIndex =
new RTree<FeaturePart *, double, 2, double>();
62 if ( defaultPriority < 0.0001 )
64 else if ( defaultPriority > 1.0 )
88 if ( priority >= 1.0 )
90 else if ( priority <= 0.0001 )
98 if ( lf->
size().width() < 0 || lf->
size().height() < 0 )
116 bool addedFeature =
false;
118 double geom_size = -1, biggest_size = -1;
123 if ( !simpleGeometries )
133 while ( !simpleGeometries->isEmpty() )
135 const GEOSGeometry *geom = simpleGeometries->takeFirst();
138 if ( GEOSisValid_r( geosctxt, geom ) != 1 )
143 int type = GEOSGeomTypeId_r( geosctxt, geom );
145 if ( type != GEOS_POINT && type != GEOS_LINESTRING && type != GEOS_POLYGON )
154 if ( ( type == GEOS_LINESTRING && fpart->
nbPoints < 2 ) ||
155 ( type == GEOS_POLYGON && fpart->
nbPoints < 3 ) )
169 bool labelWellDefined = ( lf->
size().width() > 0.0000001 && lf->
size().height() > 0.0000001 );
171 if ( lf->
isObstacle() && featureGeomIsObstacleGeom )
196 if ( type == GEOS_LINESTRING )
197 GEOSLength_r( geosctxt, geom, &geom_size );
198 else if ( type == GEOS_POLYGON )
199 GEOSArea_r( geosctxt, geom, &geom_size );
201 if ( geom_size > biggest_size )
203 biggest_size = geom_size;
205 biggest_part = fpart;
218 delete simpleGeometries;
220 if ( !featureGeomIsObstacleGeom )
224 if ( !simpleGeometries )
230 while ( !simpleGeometries->isEmpty() )
232 const GEOSGeometry *geom = simpleGeometries->takeFirst();
235 if ( GEOSisValid_r( geosctxt, geom ) != 1 )
240 int type = GEOSGeomTypeId_r( geosctxt, geom );
242 if ( type != GEOS_POINT && type != GEOS_LINESTRING && type != GEOS_POLYGON )
251 if ( ( type == GEOS_LINESTRING && fpart->
nbPoints < 2 ) ||
252 ( type == GEOS_POLYGON && fpart->
nbPoints < 3 ) )
268 delete simpleGeometries;
305 QLinkedList< FeaturePart *> *lst;
309 lst =
new QLinkedList<FeaturePart *>;
317 lst->append( fpart );
337 QLinkedList<FeaturePart *>::const_iterator p = otherParts->constBegin();
338 while ( p != otherParts->constEnd() )
354 int connectedFeaturesId = 0;
360 connectedFeaturesId++;
365 while ( !parts->isEmpty() && parts->count() > 1 )
370 FeaturePart *otherPart = _findConnectedPart( partCheck, parts );
374 double checkpartBMin[2], checkpartBMax[2];
377 double otherPartBMin[2], otherPartBMax[2];
384 mFeatureIndex->Remove( checkpartBMin, checkpartBMax, partCheck );
385 mFeatureIndex->Remove( otherPartBMin, otherPartBMax, otherPart );
389 mFeatureIndex->Insert( otherPartBMin, otherPartBMax, otherPart );
422 QLinkedList<FeaturePart *> newFeatureParts;
426 const GEOSGeometry *geom = fpart->
geos();
428 if ( chopInterval != 0. && GEOSGeomTypeId_r( geosctxt, geom ) == GEOS_LINESTRING )
432 double bmin[2], bmax[2];
436 const GEOSCoordSequence *cs = GEOSGeom_getCoordSeq_r( geosctxt, geom );
440 GEOSCoordSeq_getSize_r( geosctxt, cs, &n );
443 std::vector<Point> points( n );
444 for (
unsigned int i = 0; i < n; ++i )
446 GEOSCoordSeq_getX_r( geosctxt, cs, i, &points[i].x );
447 GEOSCoordSeq_getY_r( geosctxt, cs, i, &points[i].y );
451 std::vector<double> len( n, 0 );
452 for (
unsigned int i = 1; i < n; ++i )
454 double dx = points[i].x - points[i - 1].x;
455 double dy = points[i].y - points[i - 1].y;
456 len[i] = len[i - 1] + std::sqrt( dx * dx + dy * dy );
460 unsigned int cur = 0;
465 lambda += chopInterval;
466 for ( ; cur < n && lambda > len[cur]; ++cur )
468 part.push_back( points[cur] );
474 double c = ( lambda - len[cur - 1] ) / ( len[cur] - len[cur - 1] );
476 p.
x = points[cur - 1].x + c * ( points[cur].x - points[cur - 1].x );
477 p.
y = points[cur - 1].y + c * ( points[cur].y - points[cur - 1].y );
479 GEOSCoordSequence *cooSeq = GEOSCoordSeq_create_r( geosctxt, part.size(), 2 );
480 for (
int i = 0; i < part.size(); ++i )
482 GEOSCoordSeq_setX_r( geosctxt, cooSeq, i, part[i].x );
483 GEOSCoordSeq_setY_r( geosctxt, cooSeq, i, part[i].y );
486 GEOSGeometry *newgeom = GEOSGeom_createLineString_r( geosctxt, cooSeq );
488 newFeatureParts.append( newfpart );
495 part.push_back( points[n - 1] );
496 GEOSCoordSequence *cooSeq = GEOSCoordSeq_create_r( geosctxt, part.size(), 2 );
497 for (
int i = 0; i < part.size(); ++i )
499 GEOSCoordSeq_setX_r( geosctxt, cooSeq, i, part[i].x );
500 GEOSCoordSeq_setY_r( geosctxt, cooSeq, i, part[i].y );
503 GEOSGeometry *newgeom = GEOSGeom_createLineString_r( geosctxt, cooSeq );
505 newFeatureParts.append( newfpart );
512 newFeatureParts.append( fpart );
QList< FeaturePart * > mObstacleParts
List of obstacle parts.
QHash< QgsFeatureId, int > mConnectedFeaturesIds
QString labelText() const
Text of the label.
QgsFeatureId featureId() const
Returns the unique ID of the feature.
QgsFeatureId id() const
Identifier of the label (unique within the parent label provider)
QgsLabelFeature * feature()
Returns the parent feature.
QStringList mConnectedTexts
QHash< QgsFeatureId, QgsLabelFeature * > mHashtable
Lookup table of label features (owned by the label feature provider that created them) ...
static QLinkedList< const GEOSGeometry * > * unmulti(const GEOSGeometry *the_geom)
void setPriority(double priority)
Sets the layer's priority.
void chopFeaturesAtRepeatDistance()
Chop layer features at the repeat distance *.
GEOSGeometry * geometry() const
Get access to the associated geometry.
bool mergeWithFeaturePart(FeaturePart *other)
Merge other (connected) part with this one and save the result in this part (other is unchanged)...
bool isObstacle() const
Returns whether the feature will act as an obstacle for labels.
bool isConnected(FeaturePart *p2)
Check whether this part is connected with some other part.
double repeatDistance() const
Returns the distance between repeating labels for this feature.
QHash< QString, QLinkedList< FeaturePart * > *> mConnectedHashtable
double priority() const
Returns the layer's priority, between 0 and 1.
RTree< FeaturePart *, double, 2, double, 8, 4 > * mFeatureIndex
void joinConnectedFeatures()
Join connected features with the same label text.
void getBoundingBox(double min[2], double max[2]) const
void addObstaclePart(FeaturePart *fpart)
Add newly created obstacle part into r tree and to the list.
void setLayer(pal::Layer *layer)
Assign PAL layer to the label feature. Should be only used internally in PAL.
Layer(QgsAbstractLabelProvider *provider, const QString &name, QgsPalLayerSettings::Placement arrangement, double defaultPriority, bool active, bool toLabel, Pal *pal, bool displayAll=false)
Create a new layer.
GEOSContextHandle_t geosContext()
Get GEOS context handle to be used in all GEOS library calls with reentrant API.
Main class to handle feature.
The QgsAbstractLabelProvider class is an interface class.
Thrown when a geometry type is not like expected.
QSizeF size() const
Size of the label (in map units)
bool registerFeature(QgsLabelFeature *label)
Register a feature in the layer.
Placement
Placement modes which determine how label candidates are generated for a feature. ...
bool hasFixedPosition() const
Whether the label should use a fixed position instead of being automatically placed.
The QgsLabelFeature class describes a feature that should be used within the labeling engine...
GEOSGeometry * obstacleGeometry() const
Returns the label's obstacle geometry, if different to the feature geometry.
QLinkedList< FeaturePart * > mFeatureParts
List of feature parts.
RTree< FeaturePart *, double, 2, double, 8, 4 > * mObstacleIndex
double getLabelWidth() const
static int reorderPolygon(int nbPoints, double *x, double *y)
Reorder points to have cross prod ((x,y)[i], (x,y)[i+1), point) > 0 when point is outside...
const GEOSGeometry * geos() const
Returns the point set's GEOS geometry.
void addFeaturePart(FeaturePart *fpart, const QString &labelText=QString())
Add newly created feature part into r tree and to the list.
int connectedFeatureId(QgsFeatureId featureId) const
Returns the connected feature ID for a label feature ID, which is unique for all features which have ...