/
qgsgeometrygapcheck.h
96 lines (79 loc) · 3.51 KB
/
qgsgeometrygapcheck.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
/***************************************************************************
* qgsgeometrygapcheck.h *
* ------------------- *
* copyright : (C) 2014 by Sandro Mani / Sourcepole AG *
* email : smani@sourcepole.ch *
***************************************************************************/
#ifndef QGS_GEOMETRY_GAP_CHECK_H
#define QGS_GEOMETRY_GAP_CHECK_H
#include "qgsgeometrycheck.h"
class QgsGeometryGapCheckError : public QgsGeometryCheckError
{
public:
QgsGeometryGapCheckError( const QgsGeometryCheck* check,
QgsAbstractGeometryV2* geometry,
const QgsFeatureIds& neighbors,
double area,
const QgsRectangle& gapAreaBBox )
: QgsGeometryCheckError( check, FEATUREID_NULL, geometry->centroid(), QgsVertexId(), area, ValueArea )
, mNeighbors( neighbors )
, mGapAreaBBox( gapAreaBBox )
{
mGeometry = geometry;
}
~QgsGeometryGapCheckError()
{
delete mGeometry;
}
QgsAbstractGeometryV2* geometry() { return mGeometry->clone(); }
const QgsFeatureIds& neighbors() const { return mNeighbors; }
bool isEqual( QgsGeometryCheckError* other ) const
{
QgsGeometryGapCheckError* err = dynamic_cast<QgsGeometryGapCheckError*>( other );
return err && QgsGeomUtils::pointsFuzzyEqual( err->location(), location(), QgsGeometryCheckPrecision::reducedTolerance() ) && err->neighbors() == neighbors();
}
bool closeMatch( QgsGeometryCheckError *other ) const
{
QgsGeometryGapCheckError* err = dynamic_cast<QgsGeometryGapCheckError*>( other );
return err && err->neighbors() == neighbors();
}
void update( const QgsGeometryCheckError* other )
{
QgsGeometryCheckError::update( other );
// Static cast since this should only get called if isEqual == true
const QgsGeometryGapCheckError* err = static_cast<const QgsGeometryGapCheckError*>( other );
delete mGeometry;
mGeometry = err->mGeometry->clone();
mNeighbors = err->mNeighbors;
mGapAreaBBox = err->mGapAreaBBox;
}
bool handleChanges( const QgsGeometryCheck::Changes& /*changes*/ )
{
return true;
}
QgsRectangle affectedAreaBBox() const
{
return mGapAreaBBox;
}
private:
QgsFeatureIds mNeighbors;
QgsRectangle mGapAreaBBox;
QgsAbstractGeometryV2* mGeometry;
};
class QgsGeometryGapCheck : public QgsGeometryCheck
{
Q_OBJECT
public:
QgsGeometryGapCheck( QgsFeaturePool* featurePool, double threshold )
: QgsGeometryCheck( LayerCheck, featurePool ), mThreshold( threshold ) {}
void collectErrors( QList<QgsGeometryCheckError*>& errors, QStringList &messages, QAtomicInt* progressCounter = 0, const QgsFeatureIds& ids = QgsFeatureIds() ) const override;
void fixError( QgsGeometryCheckError* error, int method, int mergeAttributeIndex, Changes& changes ) const override;
const QStringList& getResolutionMethods() const override;
QString errorDescription() const override { return tr( "Gap" ); }
QString errorName() const override { return "QgsGeometryGapCheck"; }
private:
enum ResolutionMethod { MergeLongestEdge, NoChange };
double mThreshold;
bool mergeWithNeighbor( QgsGeometryGapCheckError *err, Changes &changes , QString &errMsg ) const;
};
#endif // QGS_GEOMETRY_GAP_CHECK_H