Skip to content

BUG: legend behaves inconsistently when plotting to the same axes #6678

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

Merged
merged 1 commit into from
Apr 22, 2014
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions doc/source/release.rst
Original file line number Diff line number Diff line change
Expand Up @@ -384,6 +384,7 @@ Bug Fixes
group match wasn't renamed to the group name
- Bug in ``DataFrame.to_csv`` where setting `index` to `False` ignored the
`header` kwarg (:issue:`6186`)
- Bug in `DataFrame.plot` and `Series.plot` legend behave inconsistently when plotting to the same axes repeatedly (:issue:`6678`)

pandas 0.13.1
-------------
Expand Down
6 changes: 3 additions & 3 deletions doc/source/visualization.rst
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ for controlling the look of the plot:
.. ipython:: python

@savefig series_plot_basic2.png
plt.figure(); ts.plot(style='k--', label='Series'); plt.legend()
plt.figure(); ts.plot(style='k--', label='Series');

On DataFrame, ``plot`` is a convenience to plot all of the columns with labels:

Expand All @@ -76,7 +76,7 @@ On DataFrame, ``plot`` is a convenience to plot all of the columns with labels:
df = df.cumsum()

@savefig frame_plot_basic.png
plt.figure(); df.plot(); plt.legend(loc='best')
plt.figure(); df.plot();

You may set the ``legend`` argument to ``False`` to hide the legend, which is
shown by default.
Expand All @@ -91,7 +91,7 @@ Some other options are available, like plotting each Series on a different axis:
.. ipython:: python

@savefig frame_plot_subplots.png
df.plot(subplots=True, figsize=(6, 6)); plt.legend(loc='best')
df.plot(subplots=True, figsize=(6, 6));

You may pass ``logy`` to get a log-scale Y axis.

Expand Down
115 changes: 96 additions & 19 deletions pandas/tests/test_graphics.py
Original file line number Diff line number Diff line change
Expand Up @@ -490,29 +490,34 @@ def test_subplots(self):
df = DataFrame(np.random.rand(10, 3),
index=list(string.ascii_letters[:10]))

axes = df.plot(subplots=True, sharex=True, legend=True)
for kind in ['bar', 'barh', 'line']:
axes = df.plot(kind=kind, subplots=True, sharex=True, legend=True)

for ax in axes:
self.assertIsNotNone(ax.get_legend())

axes = df.plot(subplots=True, sharex=True)
for ax in axes[:-2]:
[self.assert_(not label.get_visible())
for label in ax.get_xticklabels()]
[self.assert_(label.get_visible())
for label in ax.get_yticklabels()]
for ax, column in zip(axes, df.columns):
self._check_legend_labels(ax, [column])

[self.assert_(label.get_visible())
for label in axes[-1].get_xticklabels()]
[self.assert_(label.get_visible())
for label in axes[-1].get_yticklabels()]
axes = df.plot(kind=kind, subplots=True, sharex=True)
for ax in axes[:-2]:
[self.assert_(not label.get_visible())
for label in ax.get_xticklabels()]
[self.assert_(label.get_visible())
for label in ax.get_yticklabels()]

axes = df.plot(subplots=True, sharex=False)
for ax in axes:
[self.assert_(label.get_visible())
for label in ax.get_xticklabels()]
for label in axes[-1].get_xticklabels()]
[self.assert_(label.get_visible())
for label in ax.get_yticklabels()]
for label in axes[-1].get_yticklabels()]

axes = df.plot(kind=kind, subplots=True, sharex=False)
for ax in axes:
[self.assert_(label.get_visible())
for label in ax.get_xticklabels()]
[self.assert_(label.get_visible())
for label in ax.get_yticklabels()]

axes = df.plot(kind=kind, subplots=True, legend=False)
for ax in axes:
self.assertTrue(ax.get_legend() is None)

@slow
def test_bar_colors(self):
Expand Down Expand Up @@ -873,7 +878,7 @@ def test_kde(self):
_check_plot_works(df.plot, kind='kde')
_check_plot_works(df.plot, kind='kde', subplots=True)
ax = df.plot(kind='kde')
self.assertIsNotNone(ax.get_legend())
self._check_legend_labels(ax, df.columns)
axes = df.plot(kind='kde', logy=True, subplots=True)
for ax in axes:
self.assertEqual(ax.get_yscale(), 'log')
Expand Down Expand Up @@ -1046,6 +1051,64 @@ def test_plot_int_columns(self):
df = DataFrame(randn(100, 4)).cumsum()
_check_plot_works(df.plot, legend=True)

def _check_legend_labels(self, ax, labels):
import pandas.core.common as com
labels = [com.pprint_thing(l) for l in labels]
self.assertTrue(ax.get_legend() is not None)
legend_labels = [t.get_text() for t in ax.get_legend().get_texts()]
self.assertEqual(labels, legend_labels)

@slow
def test_df_legend_labels(self):
kinds = 'line', 'bar', 'barh', 'kde', 'density'
df = DataFrame(randn(3, 3), columns=['a', 'b', 'c'])
df2 = DataFrame(randn(3, 3), columns=['d', 'e', 'f'])
df3 = DataFrame(randn(3, 3), columns=['g', 'h', 'i'])
df4 = DataFrame(randn(3, 3), columns=['j', 'k', 'l'])

for kind in kinds:
ax = df.plot(kind=kind, legend=True)
self._check_legend_labels(ax, df.columns)

ax = df2.plot(kind=kind, legend=False, ax=ax)
self._check_legend_labels(ax, df.columns)

ax = df3.plot(kind=kind, legend=True, ax=ax)
self._check_legend_labels(ax, df.columns + df3.columns)

ax = df4.plot(kind=kind, legend='reverse', ax=ax)
expected = list(df.columns + df3.columns) + list(reversed(df4.columns))
self._check_legend_labels(ax, expected)

# Secondary Y
ax = df.plot(legend=True, secondary_y='b')
self._check_legend_labels(ax, ['a', 'b (right)', 'c'])
ax = df2.plot(legend=False, ax=ax)
self._check_legend_labels(ax, ['a', 'b (right)', 'c'])
ax = df3.plot(kind='bar', legend=True, secondary_y='h', ax=ax)
self._check_legend_labels(ax, ['a', 'b (right)', 'c', 'g', 'h (right)', 'i'])

# Time Series
ind = date_range('1/1/2014', periods=3)
df = DataFrame(randn(3, 3), columns=['a', 'b', 'c'], index=ind)
df2 = DataFrame(randn(3, 3), columns=['d', 'e', 'f'], index=ind)
df3 = DataFrame(randn(3, 3), columns=['g', 'h', 'i'], index=ind)
ax = df.plot(legend=True, secondary_y='b')
self._check_legend_labels(ax, ['a', 'b (right)', 'c'])
ax = df2.plot(legend=False, ax=ax)
self._check_legend_labels(ax, ['a', 'b (right)', 'c'])
ax = df3.plot(legend=True, ax=ax)
self._check_legend_labels(ax, ['a', 'b (right)', 'c', 'g', 'h', 'i'])

# scatter
ax = df.plot(kind='scatter', x='a', y='b', label='data1')
self._check_legend_labels(ax, ['data1'])
ax = df2.plot(kind='scatter', x='d', y='e', legend=False,
label='data2', ax=ax)
self._check_legend_labels(ax, ['data1'])
ax = df3.plot(kind='scatter', x='g', y='h', label='data3', ax=ax)
self._check_legend_labels(ax, ['data1', 'data3'])

def test_legend_name(self):
multi = DataFrame(randn(4, 4),
columns=[np.array(['a', 'a', 'b', 'b']),
Expand All @@ -1056,6 +1119,20 @@ def test_legend_name(self):
leg_title = ax.legend_.get_title()
self.assertEqual(leg_title.get_text(), 'group,individual')

df = DataFrame(randn(5, 5))
ax = df.plot(legend=True, ax=ax)
leg_title = ax.legend_.get_title()
self.assertEqual(leg_title.get_text(), 'group,individual')

df.columns.name = 'new'
ax = df.plot(legend=False, ax=ax)
leg_title = ax.legend_.get_title()
self.assertEqual(leg_title.get_text(), 'group,individual')

ax = df.plot(legend=True, ax=ax)
leg_title = ax.legend_.get_title()
self.assertEqual(leg_title.get_text(), 'new')

def _check_plot_fails(self, f, *args, **kwargs):
with tm.assertRaises(Exception):
f(*args, **kwargs)
Expand Down
Loading