@@ -155,25 +155,10 @@ Cell *getCentroidCell( const QgsPolygonV2 *polygon )
155
155
return new Cell ( x / area, y / area, 0.0 , polygon );
156
156
}
157
157
158
- // /@endcond
159
-
160
- QgsGeometry QgsInternalGeometryEngine::poleOfInaccessibility ( double precision, double *distanceFromBoundary ) const
158
+ QgsPoint surfacePoleOfInaccessibility ( const QgsSurface *surface, double precision, double &distanceFromBoundary )
161
159
{
162
- if ( distanceFromBoundary )
163
- *distanceFromBoundary = DBL_MAX;
164
-
165
- if ( !mGeometry || mGeometry ->isEmpty () )
166
- return QgsGeometry ();
167
-
168
- if ( precision <= 0 )
169
- return QgsGeometry ();
170
-
171
- const QgsSurface *surface = dynamic_cast < const QgsSurface * >( mGeometry );
172
- if ( !surface )
173
- return QgsGeometry ();
174
-
175
160
std::unique_ptr< QgsPolygonV2 > segmentizedPoly;
176
- const QgsPolygonV2 *polygon = dynamic_cast < const QgsPolygonV2 * >( mGeometry );
161
+ const QgsPolygonV2 *polygon = dynamic_cast < const QgsPolygonV2 * >( surface );
177
162
if ( !polygon )
178
163
{
179
164
segmentizedPoly.reset ( static_cast < QgsPolygonV2 *>( surface->segmentize () ) );
@@ -187,7 +172,7 @@ QgsGeometry QgsInternalGeometryEngine::poleOfInaccessibility( double precision,
187
172
double cellSize = qMin ( bounds.width (), bounds.height () );
188
173
189
174
if ( qgsDoubleNear ( cellSize, 0.0 ) )
190
- return QgsGeometry ( new QgsPoint ( bounds.xMinimum (), bounds.yMinimum () ) );
175
+ return QgsPoint ( bounds.xMinimum (), bounds.yMinimum () );
191
176
192
177
double h = cellSize / 2.0 ;
193
178
std::priority_queue< Cell *, std::vector<Cell *>, GreaterThanByMax > cellQueue;
@@ -238,15 +223,70 @@ QgsGeometry QgsInternalGeometryEngine::poleOfInaccessibility( double precision,
238
223
cellQueue.push ( new Cell ( currentCell->x + h, currentCell->y + h, h, polygon ) );
239
224
}
240
225
226
+ distanceFromBoundary = bestCell->d ;
227
+
228
+ return QgsPoint ( bestCell->x , bestCell->y );
229
+ }
230
+
231
+ // /@endcond
232
+
233
+ QgsGeometry QgsInternalGeometryEngine::poleOfInaccessibility ( double precision, double *distanceFromBoundary ) const
234
+ {
241
235
if ( distanceFromBoundary )
242
- *distanceFromBoundary = bestCell-> d ;
236
+ *distanceFromBoundary = DBL_MAX ;
243
237
244
- return QgsGeometry ( new QgsPoint ( bestCell->x , bestCell->y ) );
238
+ if ( !mGeometry || mGeometry ->isEmpty () )
239
+ return QgsGeometry ();
240
+
241
+ if ( precision <= 0 )
242
+ return QgsGeometry ();
243
+
244
+ if ( const QgsGeometryCollection *gc = dynamic_cast < const QgsGeometryCollection *>( mGeometry ) )
245
+ {
246
+ int numGeom = gc->numGeometries ();
247
+ double maxDist = 0 ;
248
+ QgsPoint bestPoint;
249
+ bool found = false ;
250
+ for ( int i = 0 ; i < numGeom; ++i )
251
+ {
252
+ const QgsSurface *surface = dynamic_cast < const QgsSurface * >( gc->geometryN ( i ) );
253
+ if ( !surface )
254
+ continue ;
255
+
256
+ found = true ;
257
+ double dist = DBL_MAX;
258
+ QgsPoint p = surfacePoleOfInaccessibility ( surface, precision, dist );
259
+ if ( dist > maxDist )
260
+ {
261
+ maxDist = dist;
262
+ bestPoint = p;
263
+ }
264
+ }
265
+
266
+ if ( !found )
267
+ return QgsGeometry ();
268
+
269
+ if ( distanceFromBoundary )
270
+ *distanceFromBoundary = maxDist;
271
+ return QgsGeometry ( new QgsPoint ( bestPoint ) );
272
+ }
273
+ else
274
+ {
275
+ const QgsSurface *surface = dynamic_cast < const QgsSurface * >( mGeometry );
276
+ if ( !surface )
277
+ return QgsGeometry ();
278
+
279
+ double dist = DBL_MAX;
280
+ QgsPoint p = surfacePoleOfInaccessibility ( surface, precision, dist );
281
+ if ( distanceFromBoundary )
282
+ *distanceFromBoundary = dist;
283
+ return QgsGeometry ( new QgsPoint ( p ) );
284
+ }
245
285
}
246
286
247
287
248
288
// helpers for orthogonalize
249
- // adapted from original code in potlach /id osm editor
289
+ // adapted from original code in potlatch /id osm editor
250
290
251
291
bool dotProductWithinAngleTolerance ( double dotProduct, double lowerThreshold, double upperThreshold )
252
292
{
0 commit comments