Update:
This feature is now part of the proplot matplotlib package that I recently released on pypi. By default, when you make figures, the labels are "shared" between subplots.
Original answer:
I discovered a more robust method:
If you know the bottom
and top
kwargs that went into a GridSpec
initialization, or you otherwise know the edges positions of your axes in Figure
coordinates, you can also specify the ylabel position in Figure
coordinates with some fancy "transform" magic.
For example:
import matplotlib.pyplot as plt
import matplotlib.transforms as mtransforms
bottom, top = 0.1, 0.9
fig, axs = plt.subplots(nrows=2, ncols=1, bottom=bottom, top=top)
avepos = 0.5 * (bottom + top)
transform = mtransforms.blended_transform_factory(mtransforms.IdentityTransform(), fig.transFigure) # specify x, y transform
axs[0].yaxis.label.set_transform(transform) # changed from default blend (IdentityTransform(), axs[0].transAxes)
axs[0].yaxis.label.set_position((0, avepos))
axs[0].set_ylabel('Hello, world!')
...and you should see that the label still appropriately adjusts left-right to keep from overlapping with labels, just like normal, but will also position itself exactly between the desired subplots.
Notably, if you omit the set_position
call, the ylabel will show up exactly halfway up the figure. I'm guessing this is because when the label is finally drawn, matplotlib
uses 0.5 for the y
-coordinate without checking whether the underlying coordinate transform has changed.