Search code examples
pythonmatplotlibcolormap

How to create a custom colormap with three colors?


I want to create a custom colormap with three colors, red-white-blue, using Matplotlib.

I know how to create a custom colormap with two colors. Here from red to blue:

import numpy as np
from matplotlib.colors import ListedColormap
N = 1024
vals = np.zeros((N, 4))
vals[:, 0] = np.linspace(1.0, 0.0, N) # red
vals[:, 2] = np.linspace(0.0, 1.0, N) # blue
vals[:, 3] = 1.0
my_cmap = ListedColormap(vals)

But how do I add the color white between red and blue?


Solution

  • I used this adapted code from the matplotlib documentation

    import numpy as np
    import matplotlib.pyplot as plt
    from matplotlib import cm
    from matplotlib.colors import ListedColormap
    
    def plot_examples(colormaps):
        """
        Helper function to plot data with associated colormap.
        """
        np.random.seed(19680801)
        data = np.random.randn(30, 30)
        n = len(colormaps)
        fig, axs = plt.subplots(1, n, figsize=(n * 2 + 2, 3),
                                constrained_layout=True, squeeze=False)
        for [ax, cmap] in zip(axs.flat, colormaps):
            psm = ax.pcolormesh(data, cmap=cmap, rasterized=True, vmin=-4, vmax=4)
            fig.colorbar(psm, ax=ax)
        plt.show()
    
    # Red, Green, Blue
    N = 256
    vals = np.ones((N, 4))
    # Red stays constant until middle of colormap all other channels increas
    # to result in white
    # from middle of colormap we decrease to 0, 0, 255 which is blue
    vals[:, 0] = np.concatenate((np.linspace(1, 1, N//2), np.linspace(1, 0, N//2)), axis=None)
    vals[:, 1] = np.concatenate((np.linspace(0, 1, N//2), np.linspace(1, 0, N//2)), axis=None)
    vals[:, 2] = np.concatenate((np.linspace(0, 1, N//2), np.linspace(1, 1, N//2)), axis=None)
    newcmp = ListedColormap(vals)
    
    plot_examples([newcmp])
    

    The output of this script looks similar to this custom colormap