Standalone colorbar (matplotlib)

Question:

I’m rendering some graphics in python with matplotlib, and will include them into a LaTeX paper (using LaTex’s nice tabular alignment instead of fiddling with matplotlib’s ImageGrid, etc.). I would like to create and save a standalone colorbar with savefig, without needing to use imshow.

(the vlim, vmax parameters, as well as the cmap could be provided explicitly)

The only way I could find was quite complicated and (from what I understand) draws a hard-coded rectangle onto the canvas:
http://matplotlib.org/examples/api/colorbar_only.html

Is there an elegant way to create a standalone colorbar with matplotlib?

Asked By: user

||

Answers:

You can create some dummy image and then hide it’s axe. Draw your colorbar in a customize Axes.

import pylab as pl
import numpy as np

a = np.array([[0,1]])
pl.figure(figsize=(9, 1.5))
img = pl.imshow(a, cmap="Blues")
pl.gca().set_visible(False)
cax = pl.axes([0.1, 0.2, 0.8, 0.6])
pl.colorbar(orientation="h", cax=cax)
pl.savefig("colorbar.pdf")

the result:

enter image description here

Answered By: HYRY

Using the same idea as in HYRY’s answer, if you want a “standalone” colorbar in the sense that it is independent of the items on a figure (not directly connected with how they are colored), you can do something like the following:

from matplotlib import pyplot as plt
import numpy as np

# create dummy invisible image
# (use the colormap you want to have on the colorbar)
img = plt.imshow(np.array([[0,1]]), cmap="Oranges")
img.set_visible(False)

plt.colorbar(orientation="vertical")

# add any other things you want to the figure.
plt.plot(np.random.rand(30))
Answered By: Mark

So, based on this answer here, if you’re like me and want to avoid this ugly fake plt.imshow(), you can do this in basically two lines:

import matplotlib as mpl
import matplotlib.pyplot as plt


fig, ax = plt.subplots()
col_map = plt.get_cmap('nipy_spectral')
mpl.colorbar.ColorbarBase(ax, cmap=col_map, orientation = 'vertical')

# As for a more fancy example, you can also give an axes by hand:
c_map_ax = fig.add_axes([0.2, 0.8, 0.6, 0.02])
c_map_ax.axes.get_xaxis().set_visible(False)
c_map_ax.axes.get_yaxis().set_visible(False)

# and create another colorbar with:
mpl.colorbar.ColorbarBase(c_map_ax, cmap=col_map, orientation = 'horizontal')

picture of resulting figure

Answered By: Xario

This solution can be also used to draw the colorbar independenly of the content of ax.
Just set fraction = .05.

Code

import matplotlib as mpl
import matplotlib.pyplot as plt

fig, ax = plt.subplots(1, 1)

fraction = 1  # .05

norm = mpl.colors.Normalize(vmin=-3, vmax=99)
cbar = ax.figure.colorbar(
            mpl.cm.ScalarMappable(norm=norm, cmap='Blues'),
            ax=ax, pad=.05, extend='both', fraction=fraction)

ax.axis('off')
plt.show()

enter image description here

Answered By: Markus Dutschke

That reference to http://matplotlib.org/examples/api/colorbar_only.html solved it for me. That example is a little verbose, so here is an easy way to make a standalone colorbar (for posterity)…

import matplotlib.pyplot as plt
import matplotlib as mpl

fig = plt.figure()
ax = fig.add_axes([0.05, 0.80, 0.9, 0.1])

cb = mpl.colorbar.ColorbarBase(ax, orientation='horizontal', 
                               cmap='RdBu')

plt.savefig('just_colorbar', bbox_inches='tight')

enter image description here

Of course, you can specify many other aspects of the Colorbar

import matplotlib.pyplot as plt
import matplotlib as mpl

fig = plt.figure()
ax = fig.add_axes([0.05, 0.80, 0.9, 0.1])

cb = mpl.colorbar.ColorbarBase(ax, orientation='horizontal', 
                               cmap='gist_ncar',
                               norm=mpl.colors.Normalize(0, 10),  # vmax and vmin
                               extend='both',
                               label='This is a label',
                               ticks=[0, 3, 6, 9])

plt.savefig('just_colorbar', bbox_inches='tight')

enter image description here

Answered By: blaylockbk

To add to @blaylockbk’s answer (which is a great solution, even to add to an already created figure), for me the cmap argument won’t take strings for colormap names, but cmap = plt.cm.viridis works, if anyone run into the same problem as I.

Answered By: CZ0143
Categories: questions Tags: ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.