Sunday, 22 September 2019

pyqgis - Adding many columns (to many layers) using QGIS?



The label toolbar uses fields in the attribute table of vector layers to fine tune labeling (Data defined labeling). That's the main reason i'm looking for that, but it may have more applications.


I'd like to automatically add some format columns instead of adding them manually every time.


Do you know a plugin or a way to do this manipulation automatically on multiples layers ?


I tried to get the QGIS tool "Add a field to attribute table" into a quick model which works properly, but it creates a new memory layer. And I'd like just new fields.


##Add_ETIKT_Field=name
##myvlayer=vector
##myvlayer=output vector
outputs_QGISADDFIELDTOATTRIBUTESTABLE_2=processing.runalg('qgis:addfieldtoattributestable', myvlayer,'ETIKT_Y',1,15.0,4.0,None)
outputs_QGISADDFIELDTOATTRIBUTESTABLE_1=processing.runalg('qgis:addfieldtoattributestable', outputs_QGISADDFIELDTOATTRIBUTESTABLE_2['OUTPUT_LAYER'],'ETIKT_X',1,15.0,5.0,myvlayer)


What I'm looking to automate is :



  • Open the attribute table

  • Edit button

  • Field Calculator button

  • Add Column + Type + length + Precision


It seems there's some ideas in QGIS manual, but I'd love to avoid coding anything, or at least at minimum go through the modeler.



Adding and Removing Fields



To add fields (attributes), you need to specify a list of field definitions. For deletion of fields just provide a list of field indexes.



if caps & QgsVectorDataProvider.AddAttributes:
res = layer.dataProvider().addAttributes([QgsField("mytext", QVariant.String), QgsField("myint", QVariant.Int)])

if caps & QgsVectorDataProvider.DeleteAttributes:
res = layer.dataProvider().deleteAttributes([0])

Answer



I finally made up the following code that will do the trick on your choice of loaded layers in QGIS interface. The script can be adapted quite easily to fit any other field types. It's quite basic but it fits my needs.


It can be much more improved if need but it's a first for me. You can add some loops to check if the column name doesn't exist, etc. I would also like to have a refreshed attribute table because the display doesn't refresh and I need to reload the layers to see the changes.



How to use it :



  • Create an empty text file in your script folder with a .py extension. On my computer, it's C:\Users[mylogin].qgis2\processing\scripts and paste the following coding

  • In the processing panel, go to "Scripts", then "Tools", then "Add script from file"

  • Choose the script your created



##Perso=group
##Add_Labelling_Fields=name


##layer=multiple vector
##Field_ETIKT_X=string ETIKT_X
##Field_ETIKT_Y=string ETIKT_Y
##Field_ETIKT_ROT=string ETIKT_ROTATE

from osgeo import ogr

layers= layer.split(";")

for i in layers:

driver = ogr.GetDriverByName('ESRI Shapefile')
dataSource = driver.Open(i, 1) #1 is read/write

#define 3 floating point fields :
fldDef_X = ogr.FieldDefn(str(Field_ETIKT_X), ogr.OFTReal)
fldDef_Y = ogr.FieldDefn(str(Field_ETIKT_Y), ogr.OFTReal)
fldDef_ROT = ogr.FieldDefn(str(Field_ETIKT_ROT), ogr.OFTReal)

#get layer and add the 3 fields:
vlayer = dataSource.GetLayer()

vlayer.CreateField(fldDef_X)
vlayer.CreateField(fldDef_Y)
vlayer.CreateField(fldDef_ROT)
progress.setInfo(i+' OK')

No comments:

Post a Comment

arcpy - Changing output name when exporting data driven pages to JPG?

Is there a way to save the output JPG, changing the output file name to the page name, instead of page number? I mean changing the script fo...