cartopy set_xlabel set_ylabel (not ticklabels)

By chance I found that running...

import matplotlib.pyplot as plt
import cartopy
ax = plt.axes(projection=cartopy.crs.PlateCarree())
ax.add_feature(cartopy.feature.COASTLINE)
ax.set_xlabel('lon')
ax.set_ylabel('lat')

ax.set_xticks([-180,-120,-60,0,60,120,180])
ax.set_yticks([-90,-60,-30,0,30,60,90])

plt.show()

...it prints the xticks and yticks but also the xlabel and ylabel. In other cases where the xticks and yticks are already defined, they would be restored doing...

ax.set_xticks(ax.get_xticks())
ax.set_yticks(ax.get_yticks())

or in case they are automatically generated out of the map limits

ax.set_xticks(ax.get_xticks()[abs(ax.get_xticks())<=180])
ax.set_yticks(ax.get_yticks()[abs(ax.get_yticks())<=90])

enter image description here

For adding the grid...

plt.grid()

enter image description here


Cartopy's matplotlib gridliner takes over the xlabel and ylabel and uses it to manage grid lines and labels. https://github.com/SciTools/cartopy/blob/master/lib/cartopy/mpl/gridliner.py#L93

import matplotlib.pyplot as plt
import cartopy
ax = plt.axes(projection=cartopy.crs.PlateCarree())
ax.add_feature(cartopy.feature.COASTLINE)
gridlines = ax.gridlines(draw_labels=True)
# this would not function, due to the gridliner
# ax.set_xlabel('lon')
# ax.set_ylabel('lat')
plt.show()

If you want to add labels to the axis instances of a cartopy axes, you ought to place them so they don't overlap with the gridliner. At present you need to do this by hand, such as:

import matplotlib.pyplot as plt
import cartopy
ax = plt.axes(projection=cartopy.crs.PlateCarree())
ax.add_feature(cartopy.feature.COASTLINE)
gridlines = ax.gridlines(draw_labels=True)
ax.text(-0.07, 0.55, 'latitude', va='bottom', ha='center',
        rotation='vertical', rotation_mode='anchor',
        transform=ax.transAxes)
ax.text(0.5, -0.2, 'longitude', va='bottom', ha='center',
        rotation='horizontal', rotation_mode='anchor',
        transform=ax.transAxes)
plt.show()

you need to tune the values for the ax.text placement to get the effect you want in each case, which can be a bit frustrating, but it is functional.

It would be a nice feature to add to cartopy to automate this placement.

labelled gridliner