Repository: pandas-dev/pandas

Issue:
Matplotlib 3.0 compatibility
I have some local failures with matplotlib 3.x only

```
========================================================================= FAILURES =========================================================================
______________________________________________________ TestTSPlot.test_matplotlib_scatter_datetime64 _______________________________________________________

self = <pandas.tests.plotting.test_datetimelike.TestTSPlot object at 0x118a34cf8>

    def test_matplotlib_scatter_datetime64(self):
        # https://github.com/matplotlib/matplotlib/issues/11391
        df = DataFrame(np.random.RandomState(0).rand(10, 2),
                       columns=["x", "y"])
        df["time"] = date_range("2018-01-01", periods=10, freq="D")
        fig, ax = self.plt.subplots()
        ax.scatter(x="time", y="y", data=df)
        fig.canvas.draw()
        label = ax.get_xticklabels()[0]
>       assert label.get_text() == '2017-12-12'
E       AssertionError: assert '2017-12-08' == '2017-12-12'
E         - 2017-12-08
E         ?         ^^
E         + 2017-12-12
E         ?         ^^

pandas/tests/plotting/test_datetimelike.py:1495: AssertionError
_________________________________________ TestDataFramePlots.test_if_scatterplot_colorbar_affects_xaxis_visibility _________________________________________

self = <pandas.tests.plotting.test_frame.TestDataFramePlots object at 0x11c340160>

    @pytest.mark.slow
    def test_if_scatterplot_colorbar_affects_xaxis_visibility(self):
        # addressing issue #10611, to ensure colobar does not
        # interfere with x-axis label and ticklabels with
        # ipython inline backend.
        random_array = np.random.random((1000, 3))
        df = pd.DataFrame(random_array,
                          columns=['A label', 'B label', 'C label'])

        ax1 = df.plot.scatter(x='A label', y='B label')
        ax2 = df.plot.scatter(x='A label', y='B label', c='C label')

        vis1 = [vis.get_visible() for vis in
                ax1.xaxis.get_minorticklabels()]
        vis2 = [vis.get_visible() for vis in
                ax2.xaxis.get_minorticklabels()]
>       assert vis1 == vis2
E       assert [] == [False, False, False, False, False, False, ...]
E         Right contains more items, first extra item: False
E         Use -v to get the full diff

pandas/tests/plotting/test_frame.py:1106: AssertionError
_________________________________________________ TestDataFramePlots.test_if_hexbin_xaxis_label_is_visible _________________________________________________

self = <pandas.tests.plotting.test_frame.TestDataFramePlots object at 0x11918ba58>

    @pytest.mark.slow
    def test_if_hexbin_xaxis_label_is_visible(self):
        # addressing issue #10678, to ensure colobar does not
        # interfere with x-axis label and ticklabels with
        # ipython inline backend.
        random_array = np.random.random((1000, 3))
        df = pd.DataFrame(random_array,
                          columns=['A label', 'B label', 'C label'])

        ax = df.plot.hexbin('A label', 'B label', gridsize=12)
>       assert all(vis.get_visible() for vis in
                   ax.xaxis.get_minorticklabels())
E       assert False
E        +  where False = all(<generator object TestDataFramePlots.test_if_hexbin_xaxis_label_is_visible.<locals>.<genexpr> at 0x11c69c990>)

pandas/tests/plotting/test_frame.py:1127: AssertionError
```

Our CI will start failing once these hit defaults.


Discussion:
Interestingly, I don't get the first failure from `pytest pandas/tests/plotting/test_datetimelike.py::TestTSPlot::test_ts_plot_with_tz`, but it does reproduce when running all the tests on that class (cc @WillAyd), so something is leaking between tests.
Got lucky and found it quickly:

```
pytest pandas/tests/plotting/test_datetimelike.py::TestTSPlot::test_irregular_datetime64_repr_bug \
 pandas/tests/plotting/test_datetimelike.py::TestTSPlot::test_matplotlib_scatter_datetime64
```

fails.
The `test_if_scatterplot_colorbar_affects_xaxis_visibility` and hexbin tests are failing because we implemented a hack to workaround an issue in matplotlib. That hack is no longer necessary with mil >= 3 (yay) and is actually breaking stuff, so we just need to not do it anymore.

Resolving patch:
diff --git a/pandas/plotting/_compat.py b/pandas/plotting/_compat.py
--- a/pandas/plotting/_compat.py
+++ b/pandas/plotting/_compat.py
@@ -29,3 +29,4 @@ def inner():
 _mpl_ge_2_0_1 = _mpl_version('2.0.1', operator.ge)
 _mpl_ge_2_1_0 = _mpl_version('2.1.0', operator.ge)
 _mpl_ge_2_2_0 = _mpl_version('2.2.0', operator.ge)
+_mpl_ge_3_0_0 = _mpl_version('3.0.0', operator.ge)
diff --git a/pandas/plotting/_core.py b/pandas/plotting/_core.py
--- a/pandas/plotting/_core.py
+++ b/pandas/plotting/_core.py
@@ -32,7 +32,8 @@
 
 from pandas.plotting._compat import (_mpl_ge_1_3_1,
                                      _mpl_ge_1_5_0,
-                                     _mpl_ge_2_0_0)
+                                     _mpl_ge_2_0_0,
+                                     _mpl_ge_3_0_0)
 from pandas.plotting._style import (plot_params,
                                     _get_standard_colors)
 from pandas.plotting._tools import (_subplots, _flatten, table,
@@ -843,11 +844,16 @@ def _plot_colorbar(self, ax, **kwds):
         # For a more detailed description of the issue
         # see the following link:
         # https://github.com/ipython/ipython/issues/11215
-
         img = ax.collections[0]
         cbar = self.fig.colorbar(img, ax=ax, **kwds)
+
+        if _mpl_ge_3_0_0():
+            # The workaround below is no longer necessary.
+            return
+
         points = ax.get_position().get_points()
         cbar_points = cbar.ax.get_position().get_points()
+
         cbar.ax.set_position([cbar_points[0, 0],
                               points[0, 1],
                               cbar_points[1, 0] - cbar_points[0, 0],


Test patch:
diff --git a/pandas/tests/plotting/common.py b/pandas/tests/plotting/common.py
--- a/pandas/tests/plotting/common.py
+++ b/pandas/tests/plotting/common.py
@@ -57,6 +57,7 @@ def setup_method(self, method):
         self.mpl_ge_2_0_0 = plotting._compat._mpl_ge_2_0_0()
         self.mpl_ge_2_0_1 = plotting._compat._mpl_ge_2_0_1()
         self.mpl_ge_2_2_0 = plotting._compat._mpl_ge_2_2_0()
+        self.mpl_ge_3_0_0 = plotting._compat._mpl_ge_3_0_0()
 
         if self.mpl_ge_1_4_0:
             self.bp_n_objects = 7
diff --git a/pandas/tests/plotting/test_datetimelike.py b/pandas/tests/plotting/test_datetimelike.py
--- a/pandas/tests/plotting/test_datetimelike.py
+++ b/pandas/tests/plotting/test_datetimelike.py
@@ -151,7 +151,7 @@ def test_high_freq(self):
         freaks = ['ms', 'us']
         for freq in freaks:
             _, ax = self.plt.subplots()
-            rng = date_range('1/1/2012', periods=100000, freq=freq)
+            rng = date_range('1/1/2012', periods=100, freq=freq)
             ser = Series(np.random.randn(len(rng)), rng)
             _check_plot_works(ser.plot, ax=ax)
 
@@ -1492,7 +1492,11 @@ def test_matplotlib_scatter_datetime64(self):
         ax.scatter(x="time", y="y", data=df)
         fig.canvas.draw()
         label = ax.get_xticklabels()[0]
-        assert label.get_text() == '2017-12-12'
+        if self.mpl_ge_3_0_0:
+            expected = "2017-12-08"
+        else:
+            expected = "2017-12-12"
+        assert label.get_text() == expected
 
 
 def _check_plot_works(f, freq=None, series=None, *args, **kwargs):