1

I have a multi-year monthly dataset for water vapour values at a certain altitude. Different timesteps have different min and max values. I'm trying to create an animation using FuncAnimation. So far, I've been able to get the contourf plot right. However, I'm doing something wrong with the colorbar. It's only plotting the colorbar for the starting date.(Probably because I have the plt.colorbar set outside of the animate function loop) However, the colorbar range of the first timestep doesn't contain all the data range for other timesteps. I'm trying to plot a colorbar that contains all the values from the entire dataset and can be used to read all the frames in the animation. Another option could be to create a new colorbar for each timestep, all the while sticking to the same colorbar range (that too, I need help with).

from netCDF4 import Dataset
import xarray as xr
import numpy as np

import matplotlib.pyplot as plt
from matplotlib.animation import FuncAnimation
import cartopy.crs as ccrs
model = <model name>
period = <time period>
for m in model:
    for p in period:
        infile = xr.open_dataset('/path/to/file.nc')
    
    #read in the variables
    hus = infile.hus
    lat = infile.lat
    lon = infile.lon
    date = infile.time
    
    #convert date to list
    date = date.values
    date = list(date)
    
    #reduce it to 3 dimesions
    phus = hus.sel(plev='50000', method='nearest')
    
    #multi-year monthly mean
    climatology = phus.groupby("time.month").mean("time")
    
    #deseasonalize the dataset
    anom = phus.groupby("time.month") - climatology
    
  
    
    fig, ax = plt.subplots(figsize=(15, 10))
    ax = plt.axes(projection=ccrs.PlateCarree())
    ax.coastlines()
    contour_opts = {'cmap':'RdBu'}
    cax = ax.contourf(lon, lat, anom[0], **contour_opts)
    cbar = plt.colorbar(cax)
    cbar.set_label('Water Vapour Anomaly')
    
    

    def animate(i):
        ax.collections = []
        ax.set_title(date[i])
        scat = ax.contourf(lon, lat, anom[i], **contour_opts)
       



    anim = FuncAnimation(fig, animate, timestep, interval=100, repeat=True)
    anim.save('test.gif', writer='pillow')
SxS
  • 41
  • 3
  • I think you need to evaluate the "global" min/max values of your data (i.e. find the range of the *fixed* colorbar) and the manually create it similar to the [answer in this question](https://stackoverflow.com/questions/54979958/) – Asmus Jul 08 '20 at 06:02

1 Answers1

0

You should create an axis for the colobar outside the animate function, then you can plot your data with the seaborn package (I think with sns.kdeplot, documentation here, you can replace the plt.contourf) with which you can specify if you want the colorbar and its min and max values.
Read this answer as a reference.

Zephyr
  • 11,891
  • 53
  • 45
  • 80