Reputation: 952
When mixing labels that have subscripts with labels without them, they do not vertically align properly in the legend. Since matplotlib determines bounding boxes internally based on printing characters, using a vphantom
character does not work to align these legend labels, and I have not had any luck changing the vertical alignment of the labels with set_va
, either.
Below is a MWE that illustrates problem I am trying to solve. I would like the labels to align to the text baseline if at all possible, otherwise to the text top.
import numpy as np
import matplotlib as mpl
mpl.rcParams['text.usetex'] = True
import matplotlib.pyplot as plt
x = np.arange(10)
plt.plot(x, np.random.uniform(size=(10,)), c='red', label=r'test')
plt.scatter(x, np.random.uniform(size=(10,)), c='blue', label=r'test${}_{xy}$')
plt.legend(ncol=2)
plt.show()
Upvotes: 8
Views: 6208
Reputation: 120
Set the text.latex.preview
parameter to True
:
import numpy as np
import matplotlib as mpl
mpl.rcParams['text.usetex'] = True
mpl.rcParams['text.latex.preview'] = True
import matplotlib.pyplot as plt
x = np.arange(10)
plt.plot(x, np.random.uniform(size=(10,)), c='red', label=r'test')
plt.scatter(x, np.random.uniform(size=(10,)), c='blue', label=r'test${}_{xy}$')
plt.legend(ncol=2)
plt.show()
For the effect of the preview
argument, also refer to this example.
Upvotes: 10
Reputation: 3325
You can have a look on Text alignment in a Matplotlib legend.
Or you can just shift down the second legend text,
h_legend = plt.legend(ncol=2)
y_shift = -2.5
h_legend.texts[1].set_position((0, y_shift))
You can peak your shift distance based on the extent of the legend window using something like:
h_legend = plt.legend(ncol=2)
renderer = plt.gcf().canvas.get_renderer()
y_shift = -0.2*h_legend.texts[0].get_window_extent(renderer).height
h_legend.texts[1].set_position((0, y_shift))
this will shift the second text by 20% of the full legend window height.
Upvotes: 2