1

I am a bit of a GIS beginner here.

I've got an image mask in .jpg format that I'm trying to convert to a shapefile .shp format. To do so, I use the GDAL polygonize function.

This is what the input mask looks like:

enter image description here

I then use the following code to polygonize the image

sourceRaster = gdal.Open('./storage/processed/71ee8db7-d2b0-45e6-a232-e218d6977266/result.jpg')
band = sourceRaster.GetRasterBand(1)
bandArray = band.ReadAsArray()
outShapefile = "polygonized"
driver = ogr.GetDriverByName("ESRI Shapefile")
outDatasource = driver.CreateDataSource(outShapefile+ ".shp")
outLayer = outDatasource.CreateLayer("polygonized", srs=None)
newField = ogr.FieldDefn('MYFLD', ogr.OFTInteger)
outLayer.CreateField(newField)
gdal.Polygonize(band, None, outLayer, 0, [], callback=None )
outDatasource.Destroy()
sourceRaster = None

The output of the above code is the following:

enter image description here

As you may notice there are 2 problems that I see with the resulting shapefile:

  1. It seems to be flipped upside down and
  2. The contours of the objects seem to be extremely messy.

Would anyone have pointers on how the above issues could be resolved or improved?

1

Don't know about the flipping, but I wonder if your (lossy) jpeg has artefacts which are visually imperceptible but decode into different values in the source raster, that then generate distinct polygons.

I would

  1. Try to make the source raster a tiff or png or some other nonlossy format (not by converting it back now, since the artefacts, if any, will be kept; rather by saving it in a nonlossy format wherever it came from so the artefacts are not introduced.)

  2. In an interactive tool like QGIS plot a histogram of the input raster to see if there is anything else than 0s and 1s

  3. Examine the features in the output to figure out if the "speckles" are additional polygons with slightly different values of the DN field (which is the value read from the input raster).

1
  • Using a losless format would be ideal for sure, but if that's not possible a simple threshold should filter the JPEG artifacts decently enough. i.e. doing bandArray = bandArray > 127 before polygonizing
    – mikewatt
    Jul 21 '20 at 21:46

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.