Skip to content

Plot area legend rendered incorrectly when moved out of the plot #13544

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
jldiaz opened this issue Jul 1, 2016 · 6 comments · Fixed by #13680
Closed

Plot area legend rendered incorrectly when moved out of the plot #13544

jldiaz opened this issue Jul 1, 2016 · 6 comments · Fixed by #13680
Labels
Milestone

Comments

@jldiaz
Copy link

jldiaz commented Jul 1, 2016

Code Sample, a copy-pastable example if possible

In area plots, the handles in the legend are made with filled rectangles, as for example in:

df = pd.DataFrame(np.random.rand(20, 5), columns=['A', 'B', 'C', 'D', 'E'])
df.plot(kind='area', linewidth=0.1)

Result

However, if method legend() is used to alter the position of the legend, the handles are rendered as lines, which poses a problem if the line width is small, as in the following example:

df = pd.DataFrame(np.random.rand(20, 5), columns=['A', 'B', 'C', 'D', 'E'])
df.plot(kind='area', linewidth=0.1).legend(loc="center left", bbox_to_anchor=(1.02, 0.5))

Bad result

output of pd.show_versions()

INSTALLED VERSIONS
------------------
commit: None
python: 3.5.1.final.0
python-bits: 64
OS: Linux
OS-release: 3.19.0-37-generic
machine: x86_64
processor: x86_64
byteorder: little
LC_ALL: None
LANG: en_US.UTF-8

pandas: 0.17.1
nose: 1.3.7
pip: 8.0.2
setuptools: 19.6.2
Cython: None
numpy: 1.10.4
scipy: 0.16.1
statsmodels: None
IPython: 4.0.1
sphinx: None
patsy: None
dateutil: 2.4.2
pytz: 2015.7
blosc: None
bottleneck: None
tables: 3.2.2
numexpr: 2.4.6
matplotlib: 1.5.1
openpyxl: None
xlrd: 0.9.4
xlwt: None
xlsxwriter: None
lxml: None
bs4: 4.4.1
html5lib: 0.999
httplib2: None
apiclient: None
sqlalchemy: None
pymysql: None
psycopg2: None
Jinja2: None
@TomAugspurger
Copy link
Contributor

IIRC the area plot legend is a bit of a hack. It's done here

Interested in seeing how much it would be to get this working?

@jldiaz
Copy link
Author

jldiaz commented Jul 2, 2016

Yes, I was already digging pandas' source and arrived at the conclusion that the function you pointed out is the one wihch builds the legend, at least when it is placed at its default location. However, for some reason which I don't understand (since I'm not familiar with pandas nor matplotlib internal architecture), that is not the one used when you use the method legend() to alter its position. For this case, apparently, the one used is the implemented in LinePlot class (which happens to be the base class of AreaPlot, btw)

I tried to study the code of BarPlot, which works fine also when the legend is positioned via legend() method, but I got lost, because BarPlot does not implement _add_legend_handle(), but uses the one in its base class MPLPlot.

Some hints about how to debug this issue?

@jldiaz
Copy link
Author

jldiaz commented Jul 2, 2016

I've found a workaround, just in case anyone has the same problem:

# Generate and plot the areas
df = pd.DataFrame(np.random.rand(20, 5), columns=['A', 'B', 'C', 'D', 'E'])
a = df.plot(kind='area', linewidth=0.1, alpha=0.6)

# Recreate the legend (reversing labels to preserve the stacked order of the areas)
# and put it at the right of the plot
import matplotlib.patches as mpatches
handles, labels = a.get_legend_handles_labels()
a.legend(reversed([mpatches.Rectangle((0, 0), 1, 1, fc=handle.get_color(), alpha=handle.get_alpha()) 
                   for handle in handles]), reversed(labels), 
         loc="center left", bbox_to_anchor=(1.02, 0.5))

Result

@tacaswell
Copy link
Contributor

What is the underlying artists that area uses?

@sinhrks
Copy link
Member

sinhrks commented Jul 4, 2016

@tacaswell it's PolyCollection (fill_between).

It may be a timing to remove the legend hack which @TomAugspurger pointed, showing a warning if mpl < 1.5.0 which supports PolyCollection legend.

@ResidentMario
Copy link
Contributor

ResidentMario commented Mar 4, 2017

This issue should be closed (?) as it was addressed in the aforementioned pull.

@jreback jreback closed this as completed Mar 4, 2017
@jorisvandenbossche jorisvandenbossche added this to the 0.19.0 milestone Mar 4, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

7 participants