[gdal-dev] Clipping multi-polygons shapefiles with
Geometry.Intersection . Any help to fix out my method?
Hajer Ayed
hajer.ayed at inria.fr
Fri May 27 08:22:20 EDT 2011
Hi all,
I'm a newbie in gdal developement, working with python on a method to clip polygon and multi-polygon shapefiles.
To perform this, I first create the Geometry of my clipper, then I set a spatial filter on my layer and loop for the features.
If I have a feature of type polygon, I calculate the intersection using the methode Geometry.Intersection and add the result to the final geometry to return.
If I have a feature of type multi-polygon, I loop into it and add the intersections between my clipper and the polygons within the multi-polygon feature.
The method works but It seems that it does not always return a correct intersection. See the attached file :
Normally, I should not have not filled (blank spaces) areas. I was wondering if it's a problem of the spatial filter, i removed it, but it still returns exactly the same result.
For polygon shapefiles it perfectly returns a correct result. But when it's up to shapefiles containing multi-polygons, it always return that empty areas.
I think the problem is may be due to multi-polygons containing multi-polygons !
Thank you for help. If you have any suggestions , they would be really welcome !! I can't find the solution to my problem ... :'(
Here is my code :
def clipShp(self, infile, outfile):
# Creating the output Shapefile (out datasource, layer and feature)
#--------------------------------------------------------
driver = ogr.GetDriverByName("ESRI Shapefile")
outDS = driver.CreateDataSource(outfile)
if outDS is None:
print("clipShp ERROR : Unable to create output DataSource.")
return False
outLayer = outDS.CreateLayer(outfile, geom_type=ogr.wkbMultiPolygon)
if outLayer is None:
print("clipShp ERROR : Unable to create output Layer")
return False
outFeature = ogr.Feature(outLayer.GetLayerDefn())
if outFeature is None:
print("clipShp ERROR : Unable to create output Feature")
return False
# Reading the filtred geometry
#--------------------------------------------------------
inGeom = self. clipGeometry(infile)
outFeature.SetGeometryDirectly(inGeom)
outLayer.CreateFeature(outFeature)
# Clean up
#--------------------------------------------------------
outFeature.Destroy()
outDS.Destroy()
return True
Here is the code of the method clipGeometry :
def clipGeometry(self,fileDS):
geom = None
# Read the input file, create the datasource and layer
# (This method works only for shapefiles that contains one Layer. )
#--------------------------------------------------------
datasource = ogr.Open(fileDS,False)
layer = datasource.GetLayer(0)
if layer is None:
print("ERROR : Failed to load layer from datasource")
return None
# Create the geometry of the clipper (variable clipGeom) which is of polygon type
# REMARK : We must create rings first and then add them to the polygon geometry
#--------------------------------------------------------
clipRing = ogr.Geometry(ogr.wkbLinearRing)
clipRing.AddPoint_2D( float(self.xmin), float(self.ymin) )
# Create a rectangle here...
clipGeom = ogr.Geometry(ogr.wkbPolygon)
clipGeom.AddGeometry(clipRing)
# Set in the SpatialFilter (rectangular)
# than, loop on this set of features
#--------------------------------------------------------
#layer.SetSpatialFilterRect(self.xmin,self.ymin,self.xmax,self.ymax)
layer.SetSpatialFilter(clipGeom)
feature = layer.GetNextFeature()
if feature is None:
return None
while feature is not None:
srcGeom = feature.GetGeometryRef()
if srcGeom is not None:
geomType = srcGeom.GetGeometryType()
if geom is None:
geom = ogr.Geometry(ogr.wkbMultiPolygon)
geom.AssignSpatialReference(srcGeom.GetSpatialReference())
if geomType == ogr.wkbPolygon:
# Calculate the intersection Geometry
#--------------------------------------------------------
clippedpolygon = srcGeom.Intersection(clipGeom)
geom.AddGeometry( clippedpolygon )
elif geomType == ogr.wkbMultiPolygon:
for iGeom in range( srcGeom.GetGeometryCount()):
# Calculate the intersection Geometry
#--------------------------------------------------------
clippedpolygon = srcGeom.GetGeometryRef(iGeom).Intersection(clipGeom)
geom.AddGeometry(clippedpolygon)
else:
print("ERROR : Geometry not of polygon type." )
datasource.Destroy()
return None
feature = layer.GetNextFeature()
datasource.Destroy()
return geom
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.osgeo.org/pipermail/gdal-dev/attachments/20110527/05efb14d/attachment-0001.html
More information about the gdal-dev
mailing list