I am trying to create a figure in which the colorbar will extend beyond the data range (go higher than the max value of data). The ultimate purpose is that I need to plot a series of images (as time progresses) of model output, and each hour is stored in a separate file. I would like the colorbar for all the figures to be the same, so that they can be joined into an animation.
Here is a sample script:
import matplotlib.pyplot as plt
import numpy as np
x = np.arange(0, 360, 1.5)
y = np.arange(-90, 90, 1.5)
lon, lat = np.meshgrid(x, y)
noise = np.random.random(lon.shape) # values in range [0, 1)
fig = plt.figure()
ax = fig.add_subplot(111)
plt.hold(True)
plt.contourf(lon, lat, noise)
plt.colorbar()
This produces the following figure:
I've been trying to set the limits of the colorbar to values outside the data range (for example, from -1. to 2.) using two methods that I've found online:
Setting vmin=-1 and vmax=2 inside the plotting line:
fig = plt.figure()
ax = fig.add_subplot(111)
plt.hold(True)
plt.contourf(lon, lat, noise, vmin=-1., vmax=2.)
plt.colorbar()
This seems to only change the colors displayed, so that the first color in the colormap would correspond to -1 and the last one to 2, but it does not extend the colorbar to show those values (left figure in link below).
The other one was to try and enforce ticks in the colorbar to extend to that range:
fig = plt.figure()
ax = fig.add_subplot(111)
plt.hold(True)
plt.contourf(lon, lat, noise)
plt.colorbar(ticks=np.arange(-1,2.1, .2))
This results in tick position as defined, but only for the range in which there's data, i.e., the colorbar still doesn't extend from -1 to 2 (middle figure in link below).
Does anyone know how I would get it to do what I want? Something like the right figure at this link: http://orca.rsmas.miami.edu/~ajdas1/SOF/n.html
will map the data in Z linearly from -1 to +1, so Z=0 will give a color at the center of the colormap RdBu_r (white in this case). Matplotlib does this mapping in two steps, with a normalization from the input data to [0, 1] occurring first, and then mapping onto the indices in the colormap.
You can change the color of bars in a barplot using color argument. RGB is a way of making colors. You have to to provide an amount of red, green, blue, and the transparency value to the color argument and it returns a color.
For most 2D plotting function (such as imshow
, pcolor
, etc.) setting vmin
and vmax
does the job. However, contourf
(and also contour
) take the levels
at which you ask it to draw the contours into account when mapping the colors:
If you don't specify the levels
argument, then the function automatically generates 10 equally spaced levels from the minimal to maximal value of your data. So to achieve what you want (consistency over varying input data) you have to specify the levels explicitly:
import matplotlib.pyplot as plt
import numpy as np
# generate data
x = np.arange(0, 360, 1.5)
y = np.arange(-90, 90, 1.5)
lon, lat = np.meshgrid(x, y)
noise = np.random.random(lon.shape)
# specify levels from vmim to vmax
levels = np.arange(-1, 2.1, 0.2)
# plot
fig = plt.figure()
ax = fig.add_subplot(111)
plt.contourf(lon, lat, noise, levels=levels)
plt.colorbar(ticks=levels)
plt.show()
Result:
Colorbar limits are not respecting set vmin/vmax in plt.contourf. How can I more explicitly set the colorbar limits? gives a good example to solve this problem.
These can be done if the colorbars of a series of images share a same ScalarMappable instance, but not the corresponding ContourSet instance which is created by each plt.contourf(). More details in https://matplotlib.org/3.2.1/api/_as_gen/matplotlib.figure.Figure.html#matplotlib.figure.Figure.colorbar
We can solve the problem like this:
import matplotlib.pyplot as plt
import matplotlib.cm as cm
fig = plt.figure()
ax = fig.add_subplot(111)
m0=ax.contourf(lon, lat, noise, vmin=-1., vmax=2.)
m = plt.cm.ScalarMappable(cmap=cm.coolwarm)
m.set_clim(-1, 2)
fig.colorbar(m,ax=ax)
Instead of using m0 (QuadContourSet instance created by contourf), we use m (ScalarMappable instance) in fig.colorbar(), because colorbar is used to describe the mappable parameter. https://matplotlib.org/3.2.1/api/_as_gen/matplotlib.figure.Figure.html#matplotlib.figure.Figure.colorbar
clim in m.set_clim
should be matched to vmin/vmax in contourf
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With