[gdal-dev] S57 questions

ogr user mrxonx at hotmail.com
Mon May 31 23:02:04 EDT 2010


This patch does not do anything regarding direction of winding.

What it does is - discover the exterior ring for a polygon, and make it
the first ring in the polygon object. This was in response to your
earlier comment that said "The S-57 driver uses
OGRBuildPolygonFromEdges() to form the set of lines into a polygon.  No
effort is currently made to properly represent exterior vs. interior
rings as is required by the simple features geometry specification."

This is that effort. FWIW, with this patch, polygons read from ENC data
that were assembled "out of order" (i.e. exterior ring was assembled
later than a first one) would be rearranged (in that exterior ring is
found and made the "exterior" ring) so that they could be drawn/handled
correctly using OGR geometry.

--Mike

Frank Warmerdam wrote:
> ogr user wrote:
>
> Mike,
>
> There is no expectation for OGR drivers to return polygons with any
> particular winding direction, so I'm not sure what the point of
> the patch is.  Perhaps I'm missing something?
>
> Generally speaking it is better to file suggested patches in Trac
> so they aren't lost in the gdal-dev email stream.
>
> Best regards,
>
>> ===================================================================
>> --- ogr/ograssemblepolygon.cpp    (revision 17)
>> +++ ogr/ograssemblepolygon.cpp    (working copy)
>> @@ -276,6 +276,40 @@
>>  // perhaps even ordering the direction of rings, though this isn't
>>  // required by the OGC geometry model.
>>
>> +    double maxarea, tarea;
>> +    int maxring = -1, rn, rcount;
>> +    OGREnvelope tenv;
>> +    OGRLinearRing *tring;
>> +
>> +    tring = poPolygon->getExteriorRing();
>> +    if (tring) tring->getEnvelope(&tenv);
>> +    maxarea = (tenv.MaxX - tenv.MinX) * (tenv.MaxY - tenv.MinY);
>> +
>> +    rcount = poPolygon->getNumInteriorRings();
>> +    for (rn = 0; rn < rcount; ++rn) {
>> +      tring = poPolygon->getInteriorRing(rn);
>> +      tring->getEnvelope(&tenv);
>> +      tarea = (tenv.MaxX - tenv.MinX) * (tenv.MaxY - tenv.MinY);
>> +      if (tarea > maxarea) {
>> +         maxarea = tarea;
>> +         maxring = rn;
>> +      }
>> +    }
>> +
>> +    if (maxring != -1) {
>> +       OGRPolygon  *poNewPoly = new OGRPolygon();
>> +
>> +       poNewPoly->addRing(poPolygon->getInteriorRing(maxring));
>> +       poNewPoly->addRing(poPolygon->getExteriorRing());
>> +       for (rn = 0; rn < rcount; ++rn) {
>> +          if (rn == maxring) continue;
>> +          poNewPoly->addRing(poPolygon->getInteriorRing(rn));
>> +       }
>> +
>> +       delete poPolygon;
>> +       poPolygon = poNewPoly;
>> +    }
>> +
>>      if( peErr != NULL )
>>      {
>>          if( bSuccess )
>>
>> Frank Warmerdam wrote:
>>> Mike,
>>>
>>> The S-57 driver uses OGRBuildPolygonFromEdges() to form the set of
>>> lines
>>> into a polygon.  No effort is currently made to properly represent
>>> exterior vs. interior rings as is required by the simple features
>>> geometry
>>> specification.
>>>
>>> So, I believe this is a bug of the S-57 driver and
>>> OGRBuildPolygonFromEdges()
>>> function.  In OGRBuildPolygonFromEdges() I see this comment:
>>>
>>> // Eventually we should at least identify the external ring properly,
>>> // perhaps even ordering the direction of rings, though this isn't
>>> // required by the OGC geometry model.
>>>
>>> You might want to file a ticket on this issue, though I can't say when
>>> the
>>> issue will be fixed.
>>>
>>> Best regards,
>>
>> _______________________________________________
>> gdal-dev mailing list
>> gdal-dev at lists.osgeo.org
>> http://lists.osgeo.org/mailman/listinfo/gdal-dev
>>
>>
>
>



More information about the gdal-dev mailing list