Mi solución parte de la creación previa de una cuadrícula (como capa de memoria) que cubre la extensión de su shapefile de entrada: para ello, he adaptado un código tomado de este blog .
Una vez creada la cuadrícula, intersecciono cada característica de la misma con la capa de entrada.
Partiendo de este shapefile de muestra:
y usando este código (lo formateé como una función, aunque no es muy eficiente agrupar todas estas líneas):
from qgis.core import *
from qgis.PyQt.QtCore import QVariant
def cut_polygon_into_windows(p, window_height, window_width):
crs = p.crs().toWkt()
extent = p.extent()
(xmin, xmax, ymin, ymax) = (extent.xMinimum(), extent.xMaximum(), extent.yMinimum(), extent.yMaximum())
# Create the grid layer
vector_grid = QgsVectorLayer('Polygon?crs='+ crs, 'vector_grid' , 'memory')
prov = vector_grid.dataProvider()
# Create the grid layer
output = QgsVectorLayer('Polygon?crs='+ crs, 'output' , 'memory')
outprov = output.dataProvider()
# Add ids and coordinates fields
fields = QgsFields()
fields.append(QgsField('ID', QVariant.Int, '', 10, 0))
outprov.addAttributes(fields)
# Generate the features for the vector grid
id = 0
y = ymax
while y >= ymin:
x = xmin
while x <= xmax:
point1 = QgsPoint(x, y)
point2 = QgsPoint(x + window_width, y)
point3 = QgsPoint(x + window_width, y - window_height)
point4 = QgsPoint(x, y - window_height)
vertices = [point1, point2, point3, point4] # Vertices of the polygon for the current id
inAttr = [id]
feat = QgsFeature()
feat.setGeometry(QgsGeometry().fromPolygon([vertices])) # Set geometry for the current id
feat.setAttributes(inAttr) # Set attributes for the current id
prov.addFeatures([feat])
x = x + window_width
id += 1
y = y - window_height
index = QgsSpatialIndex() # Spatial index
for ft in vector_grid.getFeatures():
index.insertFeature(ft)
for feat in p.getFeatures():
geom = feat.geometry()
idsList = index.intersects(geom.boundingBox())
for gridfeat in vector_grid.getFeatures(QgsFeatureRequest().setFilterFids(idsList)):
tmp_geom = QgsGeometry(gridfeat.geometry())
tmp_attrs = gridfeat.attributes()
if geom.intersects(tmp_geom):
int = QgsGeometry(geom.intersection(tmp_geom))
outfeat = QgsFeature()
outfeat.setGeometry(int)
outfeat.setAttributes(tmp_attrs)
outprov.addFeatures([outfeat])
output.updateFields()
return output
# Load the layer
p = QgsVectorLayer('C:/path_to_your_file/input.shp', 'display name', 'ogr')
# Set width and height as you want
window_width = 300
window_height = 300
# Run the function
output = cut_polygon_into_windows(p, window_height, window_width)
# Add the layer to the Layers panel
QgsMapLayerRegistry.instance().addMapLayers([output])
Obtengo el resultado deseado:
0 votos
¿tiene acceso a las bibliotecas de arcpy? Esto podría hacerse con una red de pesca y una intersección.
0 votos
No - y se dijo que esta solución debería ser escrita usando paquetes de código abierto.
1 votos
Sería mejor que dijera esto en la pregunta
0 votos
Estoy trabajando en una solución con PyQGIS. ¿Es su
p
polígono ya cargado en el lienzo o lo cargas directamente desde una fuente externa?0 votos
Lo estamos cargando desde un archivo fuente (archivo shp).
1 votos
GIS SE no es un servicio de codificación. No sólo hay que publicar lo que se quiere, sino que hay que publicar lo que se ha intentado. Se espera que las preguntas de codificación aquí contengan un esfuerzo de buena fe para resolver el problema. Vea el Tour para las directrices de publicación.