Skip to content

Instantly share code, notes, and snippets.

@Joonalai
Last active Jan 16, 2020
Embed
What would you like to do?
Simple script to have load countries in a globe view similar to the globe image in https://www.gispo.fi/en/blog/the-power-of-community-30daymapchallenge/
'''
Open the script in QGIS Python Console editor window, run it and run the command load_globe_view() in the
QGIS Python console.
Inspired by blog posts at http://www.statsmapsnpix.com/2019/09/globe-projections-and-insets-in-qgis.html
and https://www.gispo.fi/en/blog/the-power-of-community-30daymapchallenge/.
'''
NATURAL_EARTH_BASE_URL = "https://raw.githubusercontent.com/nvkelso/natural-earth-vector/master/geojson/"
def load_natural_earth_data():
lyr_data = [
'ne_110m_admin_0_countries.geojson',
# 'ne_110m_land.geojson',
#'ne_10m_graticules_30.geojson',
# 'ne_10m_graticules_1.geojson'
]
for source in lyr_data:
iface.addVectorLayer(NATURAL_EARTH_BASE_URL + source, "", "ogr")
def change_to_globe(lat=42.5333333333, lon=-0.53333333339999):
proj4_string = '+proj=ortho +lat_0={} +lon_0={} +x_0=0 +y_0=0 +a=6370997 +b=6370997 +units=m +no_defs'.format(lat,
lon)
proj4_string = proj4_string.format(lat, lon)
crs = QgsCoordinateReferenceSystem()
crs.createFromProj4(proj4_string)
QgsProject.instance().setCrs(crs)
def change_to_wgs84():
crs = QgsCoordinateReferenceSystem()
crs.createFromId(4326)
QgsProject.instance().setCrs(crs)
def change_background_color(color=QtCore.Qt.black):
from PyQt5.QtGui import QColor
myColor = QColor(color)
# Write it to the project (will still need to be saved!)
QgsProject.instance().writeEntry("Gui", "/CanvasColorRedPart", myColor.red())
QgsProject.instance().writeEntry("Gui", "/CanvasColorGreenPart", myColor.green())
QgsProject.instance().writeEntry("Gui", "/CanvasColorBluePart", myColor.blue())
# And apply for the current session
iface.mapCanvas().setCanvasColor(myColor);
iface.mapCanvas().refresh()
def set_border_styles(layer):
sym = layer.renderer().symbol()
props = {'color': 'blue'}
fill_symbol = QgsFillSymbol.createSimple(props)
# Assign effects
stack = QgsEffectStack()
stack.appendEffect(QgsDrawSourceEffect.create({'enabled': 'False'}))
stack.appendEffect(QgsDropShadowEffect.create({'color': 'white'}))
stack.appendEffect(QgsInnerShadowEffect.create({'color': 'white'}))
fill_symbol.symbolLayers()[0].setPaintEffect(stack)
geom_generator_sl = QgsGeometryGeneratorSymbolLayer.create({
'SymbolType': 'Fill',
'geometryModifier': 'buffer($geometry, 6371000)' # Earth radius
})
geom_generator_sl.setSubSymbol(fill_symbol)
sym.changeSymbolLayer(0, geom_generator_sl)
layer.triggerRepaint()
return layer
def add_borders(lat=42.5333333333, lon=-0.53333333339999):
proj4_string = '+proj=ortho +lat_0={} +lon_0={} +x_0=0 +y_0=0 +a=6370997 +b=6370997 +units=m +no_defs'.format(lat,
lon)
point = QgsPointXY(lat, lon)
# Bloc signals required to prevent the pop up asking about the crs change
iface.mainWindow().blockSignals(True)
layer = QgsVectorLayer("Point?EPSG:4326", "Sea", "memory")
crs = layer.crs()
crs.createFromProj4(proj4_string)
layer.setCrs(crs)
iface.mainWindow().blockSignals(False)
feature = QgsFeature()
feature.setGeometry(QgsGeometry.fromPointXY(point))
provider = layer.dataProvider()
layer.startEditing()
provider.addFeatures([feature])
layer.commitChanges()
# Assign styles and add to toc
set_border_styles(layer)
QgsProject.instance().addMapLayer(layer)
def change_globe_origo(lat, lon):
'''
Change the origo of the globe
'''
change_to_wgs84()
change_to_globe(lat, lon)
def load_globe_view(lat=42.5, lon=-0.53):
'''
Run the methods above to load the globe view
'''
load_natural_earth_data()
change_background_color()
change_to_globe(lat, lon)
add_borders(lat, lon)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment