3

I got the QGIS Python Programming Cookbook Second Edition, in hopes of improving my abilities around QGIS as well as making me confident in using Python. Keep in mind that my programming abilities are virtually nil, but I figured if I followed the directions in the book I could at least begin to grasp the basics.

Well, the first real exercise has me landing straight on my face! In it, you are supposed to create a vector layer in memory to display a point. The following is the code provided:

layer =  QgsVectorLayer('Point?crs=epsg:4326', 'MyPoint' , "memory")
pr = layer.dataProvider()
pt = QgsFeature()
point1 = QgsPoint(20,20)
pt.setGeometry(QgsGeometry.fromPoint(point1))
pr.addFeatures([pt])
layer.updateExtents()
QgsMapLayerRegistry.instance().addMapLayers([layer])

So when I enter it one line at a time, when I get to the pt.setGeometry(QgsGeometry.fromPoint(point1)) line I get the following error:

Traceback (most recent call last): File "C:\OSGEO4~1\apps\Python37\lib\code.py", line 90, in runcode exec(code, self.locals) File "", line 1, in AttributeError: type object 'QgsGeometry' has no attribute 'fromPoint'

If I continue on, after inputting the last line I get the following error:

Traceback (most recent call last): File "C:\OSGEO4~1\apps\Python37\lib\code.py", line 90, in runcode exec(code, self.locals) File "", line 1, in NameError: name 'QgsMapLayerRegistry' is not defined

If I run it altogether through the script editor, the first error appears. I also considered that they meant fromPointXY, but I get the following error:

Traceback (most recent call last): File "C:\OSGEO4~1\apps\Python37\lib\code.py", line 90, in runcode exec(code, self.locals) File "", line 1, in TypeError: QgsGeometry.fromPointXY(): argument 1 has unexpected type 'QgsPoint'

I am out of ideas here. Since this is a book to learn PyQGIS, I that I should not be in this predicament in the first place! Either there is a major error on the FIRST exercise, or I am doing something incredibly stupid. The only other thing I can think of is that I am not using QGIS 2.18 as the book was written for, but 3.0.3 and 3.4.3 (I also tried upgrading to see if that would help, it didn't). I really don't want to downgrade just to learn PyQGIS, but if you think it would work I may just do so.

Here is a link to the page in question via Google Books


I will be downgrading to 2.18 in order to complete the book. I hope that learning on an older version will still be worthwhile.

closed as off-topic by PolyGeo Jan 15 at 4:44

This question appears to be off-topic. The users who voted to close gave this specific reason:

  • "This problem cannot or can no longer be reproduced. Changes to the system or to the asker's circumstances may have rendered the question obsolete, or the question does not include a procedure to enable potential answerers to reproduce the same symptoms. Such questions are off-topic as they are unlikely to help future readers, but editing them to include more details can lead to re-opening." – PolyGeo
If this question can be reworded to fit the rules in the help center, please edit the question.

7

If you are using QGIS 3 that book is outdated in hopes of improving your abilities around PyQGIS 3. Following code has 3 necessary corrections to run as expected:

layer =  QgsVectorLayer('Point?crs=epsg:4326', 'MyPoint' , "memory")
pr = layer.dataProvider()
pt = QgsFeature()
point1 = QgsPointXY(20,20)  #1 correction
pt.setGeometry(QgsGeometry.fromPointXY(point1)) #2 correction
pr.addFeatures([pt])
layer.updateExtents()
QgsProject.instance().addMapLayers([layer])  #3 correction

After running it at Python Console I got expected point layer:

enter image description here

3

You are faced with some of many incompatibilities between the APIs between QGIS 2 and 3 versions. The first issue you have already found, for the second change the last line as follows:

layer = QgsVectorLayer('Point?crs=epsg:4326', 'MyPoint' , "memory") 
pr = layer.dataProvider()
pt = QgsFeature()
point1 = QgsPoint(20,20)  # or QgsPointXY(20, 20)
pt.setGeometry(point1)  # assign QgsPoint directly to QgsFeature
# or:
# pt.setGeometry(QgsGeometry.fromPointXY(QgsPointXY(20, 20)))
pr.addFeatures([pt])
layer.updateExtents()
QgsProject.instance().addMapLayer(layer)  # API change

For a detailed listing of API changes have a look at https://qgis.org/api/api_break.html

3

You're using QGIS 2.x API in QGIS 3.x. You'll hit plenty of issues like this. You need to either:

  • use QGIS 2.18
  • wait for a third edition of the book, with updated code
  • port the code to 3.x yourself (tricky!)

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