4

I want to create a grid with a python script in PyQgis. I have the layer from which I want to take the extent.

it seems that there is different formula : The one from QGIS doc : https://docs.qgis.org/2.6/en/docs/user_manual/processing_algs/qgis/vector_creation_tools/creategrid.html

processing.runalg('qgis:creategrid', type, width, height, hspacing, vspacing, centerx, centery, crs, output)

The one I found on different forums with a string for extent : processing.runalg('qgis:creategrid', type, extent, hspacing, vspacing, crs, output)

I tried both and I always got :problem answer

I tried it from my script and from the console.

Here is my code if it can help :

#!/usr/bin/env Python
from glob import glob
from os import path
import numpy as np
from PyQt4.QtGui import *
from PyQt4.QtCore import *
from qgis.core import *
from qgis.utils import iface
import processing
class Grid:
def __init__(self, iface,crs):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
 self.crs=crs
def new_grid(self,cellsizex,cellsizey,extent,centerx,centery,grid_out):
 processing.runalg('qgis:creategrid', type=1, extent=extent, hspacing=cellsizex, vspacing=cellsizey, crs=self.crs, output=grid_out)
class Extent:
def __init__(self, iface):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
def main(self):
 pabs= "K:\Histo_Europe_All" #path absolu
 path=pabs+"0円_Quadrillage\extent_eu.shp"
 name_l="extent_eu"
 layer=QgsVectorLayer(path,name_l, "ogr")
 extent = QgsVectorLayer( path, '', 'ogr' ).extent()
 cellsize = 1000
 centerx = (extent.xMinimum() + extent.xMaximum()) / 2
 centery = (extent.yMinimum() + extent.yMaximum()) / 20
 #first method
 width = (extent.xMaximum() - extent.xMinimum())
 height = (extent.yMaximum() - extent.yMinimum())/10
 #second method
 extent2 = str(extent.xMinimum())+ ',' + str(extent.xMaximum())+ ',' +str(ymin)+ ',' +str(extent.yMaximum()) 
 cellsizex = 0,002775
 cellsizey = 0,002775
 ymin=extent.yMinimum()+ 0,8 * (extent.yMaximum() - extent.yMinimum())
 grid=pabs+"1円_Grids\Grid0.shp"
 g=Grid(self.iface,layer.crs().authid())
 g.new_grid(cellsizex,cellsizey,extent2,centerx,centery,grid)

Don't mind the missing spaces at the beginning of the classes, they do exist in my code.

I edit my question based on comments. I also gave up the extent as QGIS advise width and height. My code is now the following :

class Grid:
def __init__(self, iface,crs):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
 self.crs=crs
def new_grid(self,cellsizex,cellsizey,width,height,centerx,centery,grid_out):
 #processing.runalg("qgis:creategrid", cellsizex, cellsizey, width, height, centerx, centery, 1, layer.crs().authid(), grid_out)
 #processing.runalg('qgis:creategrid', width, height, cellsizex, cellsizey, centerx, centery,"EPSG:4326", grid_out)
 #processing.runalg('qgis:creategrid', type=1, extent=extent, hspacing=cellsizex, vspacing=cellsizey, crs=self.crs, output=grid_out)
 processing.runalg('qgis:creategrid', 1, width,height, cellsizex, cellsizey, self.crs, output=grid_out)
class Extent:
def __init__(self, iface):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
def main(self):
 pabs= "K:/Histo_Europe_All" #path absolu
 path=pabs+"/0_Quadrillage/extent_eu.shp"
 name_l="extent_eu"
 layer=QgsVectorLayer(path,name_l, "ogr")
 extent = QgsVectorLayer( path, '', 'ogr' ).extent()
 cellsize = 1000
 centerx = (extent.xMinimum() + extent.xMaximum()) / 2
 centery = (extent.yMinimum() + extent.yMaximum()) / 20
 width = (extent.xMaximum() - extent.xMinimum())
 height = (extent.yMaximum() - extent.yMinimum())/10
 print(width)
 print(height)
 cellsizex = 0.002775
 cellsizey = 0.002775
 ymin=extent.yMinimum()+ 0.8 * (extent.yMaximum() - extent.yMinimum())
 extent2 = str(extent.xMinimum())+ ',' + str(extent.xMaximum())+ ',' +str(ymin)+ ',' +str(extent.yMaximum()) 
 grid=pabs+"/1_Grids/Grid0.shp"
 g=Grid(self.iface,layer.crs().authid())
 g.new_grid(cellsizex,cellsizey,width,height,centerx,centery,grid)

Now it answers : Error: Wrong parameter value: 40.967325 (width)

PolyGeo
65.5k29 gold badges115 silver badges350 bronze badges
asked Jun 27, 2017 at 10:55
14
  • I think self.crs=self.layer.crs.authid() should instead be self.crs=self.layer.crs().authid() Commented Jun 27, 2017 at 12:07
  • Is it ok in my edited post? Commented Jun 27, 2017 at 12:10
  • Any particular reason why you are using two different classes instead of putting those functions into one? Commented Jun 28, 2017 at 9:51
  • 1
    Edited my post with a slightly more concise version. Seems to work fine for me so hopefully for you too :) Commented Jun 28, 2017 at 10:49
  • 1
    Yes it works now !!! Thank you very much for your help. If ever someone else is interested : with this version of QGIS I can't use centerx and centery some I made calcuatation so as to the extent of my grid is different to the one of my layer. For example : ymin=ymin+(ymax-ymin)/2 Commented Jun 28, 2017 at 11:26

1 Answer 1

2

I think there's a couple of things you could try:

  • In your new_grid() function, replace the processing line with the following (if you want to assign variables such as type=1 etc. then you should use a dictionary as described in this post:

    processing.runalg('qgis:creategrid', 1, extent, cellsizex, cellsizey, self.crs, output=grid_out)
    
  • When defining a path for your output, either include the raw string (r) or use a single forward slash to escape:

    grid=pabs+"/1_Grids/Grid0.shp"
    

Edit:

Made some changes to your code which might help (unfortunately, I can't test it at the moment):

class Grid:
def __init__(self, iface):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
def new_grid(self,cellsizex,cellsizey,layer_extent,crs,grid_out):
 processing.runalg('qgis:creategrid', 1, layer_extent, cellsizex, cellsizey, crs, grid_out)
class Extent:
def __init__(self, iface):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
def main(self):
 pabs= "K:/Histo_Europe_All" #path absolu
 path=pabs+"/0_Quadrillage/extent_eu.shp"
 name_l="extent_eu"
 layer=QgsVectorLayer(path,name_l, "ogr")
 crs=layer.crs().authid()
 extent = layer.extent()
 xmin = extent.xMinimum()
 xmax = extent.xMaximum()
 ymin = extent.yMinimum()
 ymax = extent.yMaximum()
 cellsizex = 0.002775
 cellsizey = 0.002775
 grid=pabs+"/1_Grids/Grid0.shp"
 g=Grid(self.iface)
 g.new_grid(cellsizex,cellsizey,"%f,%f,%f,%f"% (xmin,xmax,ymin,ymax),crs,grid)

Edit 2:

Combined both classes into one, did a quick test and works fine for me so hopefully it will for you too.

class Grid:
 def __init__(self, iface):
 """Initialize using the qgis.utils.iface
 object passed from the console.
 """
 self.iface = iface
 def main(self):
 pabs = "K:/Histo_Europe_All" #path absolu
 path = pabs+"/0_Quadrillage/extent_eu.shp"
 grid = pabs+"/1_Grids/Grid0.shp"
 name_l = "extent_eu"
 layer = QgsVectorLayer(path,name_l, "ogr")
 crs = layer.crs().authid()
 extent = layer.extent()
 xmin = extent.xMinimum()
 xmax = extent.xMaximum()
 ymin = extent.yMinimum()
 ymax = extent.yMaximum()
 cellsizex = 0.002775
 cellsizey = 0.002775
 processing.runalg('qgis:creategrid', 1, "%f,%f,%f,%f"% (xmin,xmax,ymin,ymax), cellsizex, cellsizey, crs, grid)

Then use self.main() to call the function.

answered Jun 27, 2017 at 11:30
11
  • I should have said that i also tried this way, sorry. I just tried the dictionary thing because I was wondering if the problem came from the fact that I included center parameters. So I retried with your proposition, I still get the same error. Commented Jun 27, 2017 at 11:36
  • @J.Delannoy - No problem! Did you also use decimal points instead of commas in your cellsizes? (i.e. 0,002775 to 0.002775) Commented Jun 27, 2017 at 11:37
  • Yes I tried it too, it does not change the error message though. Commented Jun 27, 2017 at 11:42
  • As I put exactly the sames parameters it asks in its error message, that must be a problem of type, no ? My parameters are numbers except the extent, the crs and the output which are strings. Commented Jun 27, 2017 at 11:50
  • @J.Delannoy - Try using self.crs=crs.authid() Commented Jun 27, 2017 at 11:53

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.