Skip to content

Commit 08ac6e9

Browse files
authored
Merge pull request #13397 from anntzer/axes_grid1.colorbar
API: Deprecate axes_grid1.colorbar (in favor of matplotlib's own).
2 parents 8fad359 + 9a8ec76 commit 08ac6e9

12 files changed

+110
-37
lines changed
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
Deprecations
2+
````````````
3+
4+
The ``mpl_toolkits.axes_grid1.colorbar`` module and its colorbar implementation
5+
are deprecated in favor of :mod:`matplotlib.colorbar`, as the former is
6+
essentially abandoned and the latter is a more featureful replacement with a
7+
nearly compatible API (for example, the following additional keywords are
8+
supported: ``panchor``, ``extendfrac``, ``extendrect``).
9+
10+
The main differences are:
11+
12+
- Setting the ticks on the colorbar is done by calling ``colorbar.set_ticks``
13+
rather than ``colorbar.cbar_axis.set_xticks`` or
14+
``colorbar.cbar_axis.set_yticks``.
15+
- The colorbar's long axis is accessed with ``colorbar.xaxis`` or
16+
``colorbar.yaxis`` depending on the orientation, rather than
17+
``colorbar.cbar_axis``.
18+
- Overdrawing multiple colorbars on top of one another in a single Axes (e.g.
19+
when using the ``cax`` attribute of `ImageGrid` elements) is not supported;
20+
if you previously relied on the second colorbar being drawn over the first,
21+
you can call ``cax.cla()`` to clear the axes before drawing the second
22+
colorbar.
23+
24+
During the deprecation period, the ``mpl_toolkits.legacy_colorbar``
25+
rcParam can be set to True to use ``mpl_toolkits.axes_grid1.colorbar`` in
26+
:mod:`mpl_toolkits.axes_grid1` code with a deprecation warning (the default),
27+
or to False to use ``matplotlib.colorbar``.

examples/axes_grid1/demo_axes_grid.py

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,14 @@
55
66
Grid of 2x2 images with single or own colorbar.
77
"""
8+
89
import matplotlib.pyplot as plt
910
from mpl_toolkits.axes_grid1 import ImageGrid
1011

1112

13+
plt.rcParams["mpl_toolkits.legacy_colorbar"] = False
14+
15+
1216
def get_demo_image():
1317
import numpy as np
1418
from matplotlib.cbook import get_sample_data
@@ -108,8 +112,8 @@ def demo_grid_with_each_cbar_labelled(fig):
108112
for ax, cax, vlim in zip(grid, grid.cbar_axes, limits):
109113
im = ax.imshow(Z, extent=extent, interpolation="nearest",
110114
vmin=vlim[0], vmax=vlim[1])
111-
cax.colorbar(im)
112-
cax.set_yticks((vlim[0], vlim[1]))
115+
cb = cax.colorbar(im)
116+
cb.set_ticks((vlim[0], vlim[1]))
113117

114118
# This affects all axes because we set share_all = True.
115119
grid.axes_llc.set_xticks([-2, 0, 2])

examples/axes_grid1/demo_axes_grid2.py

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -5,13 +5,17 @@
55
66
Grid of images with shared xaxis and yaxis.
77
"""
8+
89
import numpy as np
910

1011
import matplotlib.pyplot as plt
1112
from mpl_toolkits.axes_grid1 import ImageGrid
1213
import matplotlib.colors
1314

1415

16+
plt.rcParams["mpl_toolkits.legacy_colorbar"] = False
17+
18+
1519
def get_demo_image():
1620
from matplotlib.cbook import get_sample_data
1721
f = get_sample_data("axes_grid/bivariate_normal.npy", asfileobj=False)
@@ -53,10 +57,13 @@ def add_inner_title(ax, title, loc, **kwargs):
5357
cbar_pad="1%",
5458
)
5559

56-
for ax, z in zip(grid, ZS):
60+
for i, (ax, z) in enumerate(zip(grid, ZS)):
5761
im = ax.imshow(
5862
z, origin="lower", extent=extent, interpolation="nearest")
59-
ax.cax.colorbar(im)
63+
cb = ax.cax.colorbar(im)
64+
# Changing the colorbar ticks
65+
if i in [1, 2]:
66+
cb.set_ticks([-1, 0, 1])
6067

6168
for ax, im_title in zip(grid, ["Image 1", "Image 2", "Image 3"]):
6269
t = add_inner_title(ax, im_title, loc='lower left')
@@ -69,10 +76,6 @@ def add_inner_title(ax, title, loc, **kwargs):
6976
#axis.label.set_size(10)
7077
#axis.major_ticklabels.set_size(6)
7178

72-
# Changing the colorbar ticks
73-
grid[1].cax.set_xticks([-1, 0, 1])
74-
grid[2].cax.set_xticks([-1, 0, 1])
75-
7679
grid[0].set_xticks([-2, 0])
7780
grid[0].set_yticks([-2, 0, 2])
7881

examples/axes_grid1/demo_colorbar_of_inset_axes.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@
77
import matplotlib.pyplot as plt
88

99
from mpl_toolkits.axes_grid1.inset_locator import inset_axes, zoomed_inset_axes
10-
from mpl_toolkits.axes_grid1.colorbar import colorbar
1110

1211

1312
def get_demo_image():
@@ -46,6 +45,6 @@ def get_demo_image():
4645
borderpad=0,
4746
)
4847

49-
colorbar(im, cax=cax)
48+
fig.colorbar(im, cax=cax)
5049

5150
plt.show()

examples/axes_grid1/demo_colorbar_with_axes_divider.py

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313

1414
import matplotlib.pyplot as plt
1515
from mpl_toolkits.axes_grid1.axes_divider import make_axes_locatable
16-
from mpl_toolkits.axes_grid1.colorbar import colorbar
1716

1817
fig, (ax1, ax2) = plt.subplots(1, 2)
1918
fig.subplots_adjust(wspace=0.5)
@@ -22,13 +21,13 @@
2221
ax1_divider = make_axes_locatable(ax1)
2322
# add an axes to the right of the main axes.
2423
cax1 = ax1_divider.append_axes("right", size="7%", pad="2%")
25-
cb1 = colorbar(im1, cax=cax1)
24+
cb1 = fig.colorbar(im1, cax=cax1)
2625

2726
im2 = ax2.imshow([[1, 2], [3, 4]])
2827
ax2_divider = make_axes_locatable(ax2)
2928
# add an axes above the main axes.
3029
cax2 = ax2_divider.append_axes("top", size="7%", pad="2%")
31-
cb2 = colorbar(im2, cax=cax2, orientation="horizontal")
30+
cb2 = fig.colorbar(im2, cax=cax2, orientation="horizontal")
3231
# change tick position to top. Tick position defaults to bottom and overlaps
3332
# the image.
3433
cax2.xaxis.set_ticks_position("top")

examples/axes_grid1/simple_colorbar.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,3 +17,5 @@
1717
cax = divider.append_axes("right", size="5%", pad=0.05)
1818

1919
plt.colorbar(im, cax=cax)
20+
21+
plt.show()

lib/matplotlib/rcsetup.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1426,6 +1426,8 @@ def _validate_linestyle(ls):
14261426
# Additional arguments for convert movie writer (using pipes)
14271427
'animation.convert_args': [[], validate_stringlist],
14281428

1429+
'mpl_toolkits.legacy_colorbar': [True, validate_bool],
1430+
14291431
# Classic (pre 2.0) compatibility mode
14301432
# This is used for things that are hard to make backward compatible
14311433
# with a sane rcParam alone. This does *not* turn on classic mode

lib/mpl_toolkits/axes_grid1/axes_grid.py

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
from numbers import Number
22

3+
import matplotlib as mpl
4+
from matplotlib import cbook
35
import matplotlib.axes as maxes
46
import matplotlib.ticker as ticker
57
from matplotlib.gridspec import SubplotSpec
68

79
from .axes_divider import Size, SubplotDivider, Divider
8-
from .colorbar import Colorbar
910
from .mpl_axes import Axes
1011

1112

@@ -47,6 +48,16 @@ def colorbar(self, mappable, *, locator=None, **kwargs):
4748
else:
4849
orientation = "vertical"
4950

51+
if mpl.rcParams["mpl_toolkits.legacy_colorbar"]:
52+
cbook.warn_deprecated(
53+
"3.2", message="Since %(since)s, mpl_toolkits's own colorbar "
54+
"implementation is deprecated; it will be removed "
55+
"%(removal)s. Set the 'mpl_toolkits.legacy_colorbar' rcParam "
56+
"to False to use Matplotlib's default colorbar implementation "
57+
"and suppress this deprecation warning.")
58+
from .colorbar import Colorbar
59+
else:
60+
from matplotlib.colorbar import Colorbar
5061
cb = Colorbar(self, mappable, orientation=orientation, **kwargs)
5162
self._config_axes()
5263

@@ -58,7 +69,10 @@ def on_changed(m):
5869
self.cbid = mappable.callbacksSM.connect('changed', on_changed)
5970
mappable.colorbar = cb
6071

61-
self.locator = cb.cbar_axis.get_major_locator()
72+
if mpl.rcParams["mpl_toolkits.legacy_colorbar"]:
73+
self.locator = cb.cbar_axis.get_major_locator()
74+
else:
75+
self.locator = cb.locator
6276

6377
return cb
6478

lib/mpl_toolkits/axes_grid1/colorbar.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020

2121
import numpy as np
2222
import matplotlib as mpl
23+
from matplotlib import cbook
2324
import matplotlib.colors as colors
2425
import matplotlib.cm as cm
2526
from matplotlib import docstring
@@ -31,6 +32,10 @@
3132
from matplotlib.transforms import Bbox
3233

3334

35+
cbook.warn_deprecated(
36+
"3.2", name="axes_grid1.colorbar", alternative="matplotlib.colorbar")
37+
38+
3439
make_axes_kw_doc = '''
3540
3641
============= ====================================================
Lines changed: 28 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,22 @@
1+
from contextlib import ExitStack
12

2-
import matplotlib
3-
from matplotlib.testing.decorators import image_comparison
4-
from mpl_toolkits.axes_grid1 import ImageGrid
53
import numpy as np
4+
import pytest
5+
6+
import matplotlib as mpl
7+
from matplotlib.testing.decorators import image_comparison
68
import matplotlib.pyplot as plt
9+
from mpl_toolkits.axes_grid1 import ImageGrid
710

811

9-
@image_comparison(['imagegrid_cbar_mode.png'], remove_text=True, style='mpl20')
10-
def test_imagegrid_cbar_mode_edge():
11-
matplotlib.rcParams['image.interpolation'] = 'nearest'
12+
# The original version of this test relied on mpl_toolkits's slightly different
13+
# colorbar implementation; moving to matplotlib's own colorbar implementation
14+
# caused the small image comparison error.
15+
@pytest.mark.parametrize("legacy_colorbar", [False, True])
16+
@image_comparison(['imagegrid_cbar_mode.png'],
17+
remove_text=True, style='mpl20', tol=0.3)
18+
def test_imagegrid_cbar_mode_edge(legacy_colorbar):
19+
mpl.rcParams["mpl_toolkits.legacy_colorbar"] = legacy_colorbar
1220

1321
X, Y = np.meshgrid(np.linspace(0, 6, 30), np.linspace(0, 6, 30))
1422
arr = np.sin(X) * np.cos(Y) + 1j*(np.sin(3*Y) * np.cos(Y/2.))
@@ -19,9 +27,8 @@ def test_imagegrid_cbar_mode_edge():
1927
directions = ['row']*4 + ['column']*4
2028
cbar_locations = ['left', 'right', 'top', 'bottom']*2
2129

22-
for position, direction, location in zip(positions,
23-
directions,
24-
cbar_locations):
30+
for position, direction, location in zip(
31+
positions, directions, cbar_locations):
2532
grid = ImageGrid(fig, position,
2633
nrows_ncols=(2, 2),
2734
direction=direction,
@@ -30,14 +37,15 @@ def test_imagegrid_cbar_mode_edge():
3037
cbar_mode='edge')
3138
ax1, ax2, ax3, ax4, = grid
3239

33-
im1 = ax1.imshow(arr.real, cmap='nipy_spectral')
34-
im2 = ax2.imshow(arr.imag, cmap='hot')
35-
im3 = ax3.imshow(np.abs(arr), cmap='jet')
36-
im4 = ax4.imshow(np.arctan2(arr.imag, arr.real), cmap='hsv')
37-
38-
# Some of these colorbars will be overridden by later ones,
39-
# depending on the direction and cbar_location
40-
ax1.cax.colorbar(im1)
41-
ax2.cax.colorbar(im2)
42-
ax3.cax.colorbar(im3)
43-
ax4.cax.colorbar(im4)
40+
ax1.imshow(arr.real, cmap='nipy_spectral')
41+
ax2.imshow(arr.imag, cmap='hot')
42+
ax3.imshow(np.abs(arr), cmap='jet')
43+
ax4.imshow(np.arctan2(arr.imag, arr.real), cmap='hsv')
44+
45+
with (pytest.warns(mpl.MatplotlibDeprecationWarning) if legacy_colorbar
46+
else ExitStack()):
47+
# In each row/column, the "first" colorbars must be overwritten by
48+
# the "second" ones. To achieve this, clear out the axes first.
49+
for ax in grid:
50+
ax.cax.cla()
51+
ax.cax.colorbar(ax.images[0])

lib/mpl_toolkits/tests/test_axes_grid1.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import matplotlib
22
import matplotlib.pyplot as plt
3+
from matplotlib.cbook import MatplotlibDeprecationWarning
34
from matplotlib.testing.decorators import (
45
image_comparison, remove_ticks_and_titles)
56

@@ -100,7 +101,10 @@ def test_twin_axes_empty_and_removed():
100101
plt.subplots_adjust(wspace=0.5, hspace=1)
101102

102103

103-
def test_axesgrid_colorbar_log_smoketest():
104+
@pytest.mark.parametrize("legacy_colorbar", [False, True])
105+
def test_axesgrid_colorbar_log_smoketest(legacy_colorbar):
106+
matplotlib.rcParams["mpl_toolkits.legacy_colorbar"] = legacy_colorbar
107+
104108
fig = plt.figure()
105109
grid = AxesGrid(fig, 111, # modified to be only subplot
106110
nrows_ncols=(1, 1),
@@ -112,7 +116,11 @@ def test_axesgrid_colorbar_log_smoketest():
112116
Z = 10000 * np.random.rand(10, 10)
113117
im = grid[0].imshow(Z, interpolation="nearest", norm=LogNorm())
114118

115-
grid.cbar_axes[0].colorbar(im)
119+
if legacy_colorbar:
120+
with pytest.warns(MatplotlibDeprecationWarning):
121+
grid.cbar_axes[0].colorbar(im)
122+
else:
123+
grid.cbar_axes[0].colorbar(im)
116124

117125

118126
@image_comparison(['inset_locator.png'], style='default', remove_text=True)

matplotlibrc.template

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -743,3 +743,5 @@
743743
#animation.convert_args : ## Additional arguments to pass to convert
744744
#animation.embed_limit : 20.0 ## Limit, in MB, of size of base64 encoded
745745
## animation in HTML (i.e. IPython notebook)
746+
747+
#mpl_toolkits.legacy_colorbar: True

0 commit comments

Comments
 (0)