1

I have a problem on the development of a python plugin, I'm trying to display the OpenStreetMap map behind layers, only the map is not synchronized with the layers, it can't find it or even the location.

The geographical position of the map does not correspond to that of my layers.

#Vlayer is defined above the code / Vlayer est définie au-dessus du code 

urlWithParams = 'type=xyz&url=http://a.tile.openstreetmap.org/%7Bz%7D/%7Bx%7D/%7By%7D.png&zmax=19&zmin=0&crs=EPSG3857'
maplayer = QgsRasterLayer(urlWithParams, 'OpenStreetMap', 'wms')
settings = QgsMapSettings()
settings.setLayers([vlayer,maplayer])
settings.setBackgroundColor(QColor(255, 255, 255))
settings.setOutputSize(QSize(800, 690))

settings.setExtent(vlayer.extent())

render = QgsMapRendererParallelJob(settings)

render.start()
render.waitForFinished()

img = render.renderedImage()
img.save(QgsApplication.qgisSettingsDirPath()+"python/plugins/nro_print/img/render.png", "png")

result:

resulut

  • Welcome to Geographic Information Systems! Welcome to GIS SE! We're a little different from other sites; this isn't a discussion forum but a Q&A site. Your questions should as much as possible describe not just what you want to do, but precisely what you have tried and where you are stuck trying that. Please check out our short tour for more about how the site works. – Ian Turton Sep 17 at 8:04
  • 1
    can you clarify what is wrong with that map? – Ian Turton Sep 17 at 8:04
  • the geographical position of the map does not correspond to that of my layers – mathias mirra Sep 17 at 8:13
  • 1
    OK, where should you data be? – Ian Turton Sep 17 at 8:35
  • 1
    You say your data is in the wrong place, where should it be? – Ian Turton Sep 17 at 8:45
1

You need to set a destination CRS on the renderer settings. The following works for me.

Create a test memory layer

vlayer = QgsVectorLayer('Point?crs=epsg:4647&field=ID:integer(3)&field=value:double','test',"memory")

mypts = [QgsPointXY(32500000,5700000),
  QgsPointXY(32500010,5700010),
  QgsPointXY(32500010,5700060),
  QgsPointXY(32500040,5700090)
]

for p in mypts:
    pt = QgsGeometry.fromPointXY(p)
    f = QgsFeature(vlayer.fields())
    f.setGeometry(pt)
    vlayer.dataProvider().addFeatures([f])

vlayer.updateExtents()

Add OSM layer, note https and tile., not a.tile..

urlWithParams = 'type=xyz&url=https://tile.openstreetmap.org/%7Bz%7D/%7Bx%7D/%7By%7D.png&zmax=19&zmin=0&crs=EPSG3857'
maplayer = QgsRasterLayer(urlWithParams, 'OpenStreetMap', 'wms')

Define the settings, these are yours.

settings = QgsMapSettings()
settings.setLayers([vlayer,maplayer])
settings.setBackgroundColor(QColor(255, 255, 255))
settings.setOutputSize(QSize(800, 690))

This is what I needed to set, otherwise the OSM layer wouldn't render. edit: Apparently, it needs to be the same as the vlayer CRS. This is also mentioned in section 10.2 of the PyQIS cookbook.

settings.setDestinationCrs(vlayer.crs())

settings.setExtent(vlayer.extent().buffered(30))

render = QgsMapRendererParallelJob(settings)

render.start()
render.waitForFinished()

img = render.renderedImage()
img.save("c:/temp/render.png", "png")

Result, which is correctly placed

result

Full code here as a GIST.

| improve this answer | |
  • 1
    Thank you very much I just added settings.setDestinationCrs(vlayer.crs()) and it works perfectly – mathias mirra Sep 21 at 7:08

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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