# ax.set_xlabel('Longitude [deg]') # barticks = [valminmax*-1, valminmax*-0.75, valminmax*-0.5, valminmax*-0.25, 0, valminmax*0.25, valminmax*0.5, valminmax*0.75, valminmax] # cbar_ax = fig.add_axes([0.2, 0.25, 0.6, 0.01]) # cbar = fig.colorbar(im, orientation='horizontal', cax=cbar_ax, ticks=barticks) # @UnusedVariable # else: # ax.set_xticklabels(['', '', '', '', '', '', '', '', '']) # figname = figname_st + '_top' # if not use_datline_center: # figname = os.path.dirname(figname) + '/map_' + os.path.basename(figname) # if useClim: # figname = figname + '_anom' # fig.savefig(figname + '.png') fig1 = plt.figure() ax1 = fig1.add_subplot( 1, 1, 1, projection=ccrs.Miller( central_longitude=180.0)) #projection=ccrs.PlateCarree()) ax1.coastlines() ax1.imshow( cma, extent=(np.nanmin(lon), np.nanmax(lon), np.nanmin(lat), np.nanmax(lat) )) #transform=ccrs.Geostationary(satellite_height=35786000)) fig1.show() pdb.set_trace() fig = plt.figure() ax = plt.axes(projection=ccrs.Miller()) ax.coastlines() ax.set_global() # img, crs, extent, origin = geos_image() img_proj = ccrs.Geostationary(satellite_height=35786000)
import matplotlib.pyplot as plt import cartopy.crs as ccrs plt.figure(figsize=(4.091529019548417, 3)) ax = plt.axes(projection=ccrs.Miller()) ax.coastlines(resolution='110m') ax.gridlines()
def test_unsupported_projection(self): source = ogc.WMTSRasterSource(self.URI, self.layer_name) with mock.patch('cartopy.io.ogc_clients._URN_TO_CRS', {}): msg = 'Unable to find tile matrix for projection.' with self.assertRaisesRegexp(ValueError, msg): source.validate_projection(ccrs.Miller())
# from oas_dev.util.plot import plot_settings from sectional_v2.data_info import get_nice_name_case, get_area_specs from sectional_v2.util.slice_average.area_mod import lon180_2lon360 from sectional_v2.util.slice_average.avg_pkg import average_model_var # , get_lat_wgts_matrix, masked_average # import analysis_tools.area_pkg_sara as area_pkg_sara import numpy as np import matplotlib.ticker as mticker from sectional_v2.util.naming_conventions.var_info import get_fancy_var_name import cartopy.crs as ccrs import matplotlib.pyplot as plt import shapely.geometry as sgeom # %% import useful_scit.plot map_projection = ccrs.Miller() default_save_path = 'plots/maps' default_save_path_levlat = 'plots/levlat' # %% # %% def fix_axis4map_plot(ax): ax.set_global() ax.coastlines() gl = ax.gridlines(crs=ccrs.PlateCarree(), draw_labels=False, linewidth=1, color='gray', alpha=0.5,
def plot_part_loc_map(part_pos, release_no, dt, traj, savepath, ls=None, config=None, add_dyn=True, add_fire=None): """""" release_sel = np.array([list(p) for p in part_pos if p[0] == release_no]) meta = traj['releases_meta'][release_no] import matplotlib matplotlib.use('Agg') import cartopy.crs as ccrs import matplotlib.pyplot as plt from fastkml import kml if ls is None: ls = trace_source.land_sfc.land_sfc() if not os.path.isdir(savepath): os.makedirs(savepath) if config['plotmap']['maptype'] == 'northpole': fig = plt.figure(figsize=(11, 10)) if "centerlon" in config['plotmap']: ax = plt.axes(projection=ccrs.NorthPolarStereo( central_longitude=config['plotmap']['centerlon'])) else: ax = plt.axes(projection=ccrs.NorthPolarStereo( central_longitude=45)) if config['plotmap']['maptype'] == 'miller': fig = plt.figure(figsize=(10, 7)) if "centerlon" in config['plotmap']: ax = plt.axes(projection=ccrs.Miller( central_longitude=config['plotmap']['centerlon'])) else: ax = plt.axes(projection=ccrs.Miller(central_longitude=0)) else: print("using standard map") fig = plt.figure(figsize=(10, 7)) ax = plt.axes(projection=ccrs.Miller(central_longitude=0)) #### # make a color map of fixed colors colors = [ 'lightskyblue', 'darkgreen', 'khaki', 'palegreen', 'red', 'white', 'tan' ] # better green for the light map colors = [ 'lightskyblue', 'seagreen', 'khaki', '#6edd6e', 'darkmagenta', 'white', 'tan' ] #colors = ['lightskyblue', 'seagreen', 'khaki', '#a4dd6e', 'red', 'white', 'tan'] colors = [ 'lightskyblue', '#22a361', 'khaki', '#72d472', 'darkmagenta', 'white', 'tan' ] cmap = matplotlib.colors.ListedColormap(colors) cs = [adjust_lightness(c, amount=1.15) for c in colors] print('cs ', cs) cmap = matplotlib.colors.ListedColormap(cs) bounds = [-0.5, 0.5, 1.5, 2.5, 3.5, 4.5, 5.5, 6.5] norm = matplotlib.colors.BoundaryNorm(bounds, cmap.N) #### pcm = ax.pcolormesh(ls.longs, ls.lats, ls.land_sfc_data, cmap=cmap, norm=norm, transform=ccrs.PlateCarree()) # high resolution coastlines #ax.coastlines(resolution='110m') ax.coastlines(resolution='50m') # ax.coastlines(resolution='10m') labels = [ 'Water', 'Forest', 'Savanna/shrubland', 'Grass/cropland', 'Urban', 'Snow/ice', 'Barren' ] handles = [] for c, l in zip(cs, labels): if 'ice' in l: handles.append( matplotlib.patches.Patch(facecolor=c, label=l, edgecolor='grey', linewidth=2)) else: handles.append(matplotlib.patches.Patch(color=c, label=l)) # # # The modis fire map if add_fire: from cartopy.io.shapereader import Reader from cartopy.feature import ShapelyFeature # # fname = '../data/DL_FIRE_M6_78471/fire_nrt_M6_78471.shp' # fname = config_dir['partposit_dir'] + '20191130_DL_FIRE_V1_90092/fire_nrt_V1_90092.shp' fname = f'data/fire_data/DL_FIRE_{add_fire}/fire_nrt_{add_fire}.shp' shp_data = Reader(fname) # print(next(shp_data.records())) frp = np.array([p.attributes['FRP'] for p in shp_data.records()]) # print(frp.shape, np.mean(frp), np.percentile(frp, [10,25,50,75,90])) points = [ p for p in list(shp_data.records()) if p.attributes['FRP'] > 12 ] # # for viirs pixel with their smaller size # points = [p for p in list(shp_data.records()) if p.attributes['FRP'] > 4] # #points = sorted(points, key=lambda x: x.attributes['FRP']) scat = ax.scatter([p.geometry.x for p in points], [p.geometry.y for p in points], transform=ccrs.Geodetic(), s=0.5, c='crimson') # optionally add the dynamics from gfs grib if add_dyn: import xarray as xr if dt.hour % 6 == 0: gribfile = f"data/gfs_083.2/{dt.strftime('%Y%m%d%H')}" print(gribfile) if not os.path.isfile(gribfile): print('try forecast file') gribfile = f"data/gfs_083.2/{dt.strftime('%Y%m%d%H')}_f" ds_isobaric = xr.load_dataset(gribfile, engine='cfgrib', backend_kwargs={ 'filter_by_keys': { 'typeOfLevel': 'isobaricInhPa' }, 'errors': 'ignore' }) ds_mean_sea = xr.load_dataset(gribfile, engine='cfgrib', backend_kwargs={ 'filter_by_keys': { 'typeOfLevel': 'meanSea' }, 'errors': 'ignore' }) prmsl = ds_mean_sea.prmsl gh_500 = ds_isobaric.gh.sel(isobaricInhPa=500) else: gribfile1 = f"data/gfs_083.2/{(dt - datetime.timedelta(hours=3)).strftime('%Y%m%d%H')}" gribfile2 = f"data/gfs_083.2/{(dt + datetime.timedelta(hours=3)).strftime('%Y%m%d%H')}" if not os.path.isfile(gribfile1): print('try forecast file') gribfile1 = f"data/gfs_083.2/{(dt - datetime.timedelta(hours=3)).strftime('%Y%m%d%H')}_f" if not os.path.isfile(gribfile2): print('try forecast file') gribfile2 = f"data/gfs_083.2/{(dt + datetime.timedelta(hours=3)).strftime('%Y%m%d%H')}_f" print(gribfile1, gribfile2) ds_isobaric = xr.load_dataset(gribfile1, engine='cfgrib', backend_kwargs={ 'filter_by_keys': { 'typeOfLevel': 'isobaricInhPa' }, 'errors': 'ignore' }) ds_mean_sea = xr.load_dataset(gribfile1, engine='cfgrib', backend_kwargs={ 'filter_by_keys': { 'typeOfLevel': 'meanSea' }, 'errors': 'ignore' }) ds_isobaric2 = xr.load_dataset(gribfile2, engine='cfgrib', backend_kwargs={ 'filter_by_keys': { 'typeOfLevel': 'isobaricInhPa' }, 'errors': 'ignore' }) ds_mean_sea2 = xr.load_dataset(gribfile2, engine='cfgrib', backend_kwargs={ 'filter_by_keys': { 'typeOfLevel': 'meanSea' }, 'errors': 'ignore' }) prmsl = np.mean(np.dstack((ds_mean_sea.prmsl, ds_mean_sea2.prmsl)), axis=2) gh_500 = np.mean(np.dstack( (ds_isobaric.gh.sel(isobaricInhPa=500), ds_isobaric2.gh.sel(isobaricInhPa=500))), axis=2) levels = np.arange(930, 1050, 4) cont = ax.contour(ds_mean_sea.longitude, ds_mean_sea.latitude, prmsl / 100., linewidths=0.4, colors='lightcoral', transform=ccrs.PlateCarree(), levels=levels) levels = np.arange(0, 900, 8) cont = ax.contour(ds_isobaric.longitude, ds_isobaric.latitude, gh_500 / 10., linewidths=0.4, colors='k', transform=ccrs.PlateCarree(), levels=levels) scat = ax.scatter(release_sel[:, 1], release_sel[:, 2], s=2, c=release_sel[:, 3] / 1000., cmap='plasma', vmin=0.1, vmax=6.0, zorder=5, transform=ccrs.Geodetic()) cbar = fig.colorbar(scat, fraction=0.025, pad=0.01) cbar.ax.set_ylabel('Height [km]', fontweight='semibold', fontsize=12) cbar.ax.tick_params(axis='both', which='major', labelsize=12, width=2, length=4) # add the geometry boundaries... # k = kml.KML() # geo_bounds_file = '../../trace_pub/trace/data/geo_names_arctic.kml' # with open(geo_bounds_file) as f: # k.from_string(bytes(bytearray(f.read(), encoding='utf-8'))) # docu = list(k.features())[0] # polygons = {} # colors = [(0.65098039215686276, 0.84705882352941175, 0.32941176470588235, 1.0), # (1.0, 0.85098039215686272, 0.18431372549019609, 1.0), # (0.89803921568627454, 0.7686274509803922, 0.58039215686274515, 1.0), # (0.40000000000000002, 0.76078431372549016, 0.6470588235294118, 1.0), # (0.9882352941176471, 0.55294117647058827, 0.3843137254901961, 1.0), # (0.55294117647058827, 0.62745098039215685, 0.79607843137254897, 1.0), # (0.70196078431372544, 0.70196078431372544, 0.70196078431372544, 1.0)] # for p in list(docu.features()): # print(p.name) # #print(p.geometry) # polygons[p.name] = p.geometry # for i, (name, poly) in enumerate(list(polygons.items())): # print(i, name) # #ax.add_geometries([poly], ccrs.Geodetic(), alpha=0.5, facecolor=colors[i]) # ax.add_geometries([poly], ccrs.Geodetic(), edgecolor=colors[i], facecolor='none', lw=3) ax.gridlines(linestyle=':') #ax.set_extent([-100, 80, 10, 80], crs=ccrs.PlateCarree()) ##ax.set_extent([-70, 50, 20, 55], crs=ccrs.PlateCarree()) ##ax.set_extent([-50, 40, 20, 55], crs=ccrs.PlateCarree()) ##ax.set_extent([20, 50, 20, 40], crs=ccrs.PlateCarree()) ##ax.set_extent([25, 35, 30, 40], crs=ccrs.PlateCarree()) # North Pole #ax.set_extent([-180, 180, 45, 90], crs=ccrs.PlateCarree()) assert config is not None if config is not None and "bounds" in config['plotmap']: ax.set_extent(config['plotmap']['bounds'], crs=ccrs.PlateCarree()) # if maptype == 'northpole': # ax.set_extent([-179, 179, 45, 90], crs=ccrs.PlateCarree()) # elif maptype == 'southernocean': # ax.set_extent([-179, 179, -75, -10], crs=ccrs.PlateCarree()) if add_fire and 'M6' in add_fire: str1_pos = (.15, 0.080) str2_pos = (.15, 0.040) else: str1_pos = (.2, 0.080) ax.annotate( "MODIS land cover classification [Broxton and Zeng 2014, JAMC]", #xy=(.15, 0.108), xycoords='figure fraction', xy=str1_pos, xycoords='figure fraction', #xy=(.2, 0.085), xycoords='figure fraction', horizontalalignment='left', verticalalignment='bottom', fontsize=11) if add_fire and 'M6' in add_fire: ax.annotate( "MODIS Active Fire Product, FRP > 12 MW/pixel [DOI:10.5067/FIRMS/MODIS/MCD14DL.NRT.006]", #xy=(.15, 0.040), xycoords='figure fraction', xy=str2_pos, xycoords='figure fraction', horizontalalignment='left', verticalalignment='bottom', fontsize=11) #ax.annotate("VIIRS Active Fire Product, FRP > 4 MW/pixel [DOI:10.5067/FIRMS/VIIRS/VNP14IMGT.NRT.001]", # xy=(.2, 0.065), xycoords='figure fraction', # horizontalalignment='left', verticalalignment='bottom', # fontsize=11) fig.legend(handles, labels, ncol=4, fontsize=10, bbox_to_anchor=(0.20, 0.185), loc='upper left') ax.set_title( 'Flexpart particle positions {}UTC\nRelease: [{:.2f} {:.2f} {:.2f} {:.2f}] {:.0f}-{:.0f}m' .format(dt.strftime('%Y-%m-%d %H'), *meta['lat_lon_bounds'], *meta['heights']), fontweight='semibold', fontsize=13) savename = savepath + "/" + "r{:0>2}_{}_{:.0f}_trajectories_map.png".format( release_no, dt.strftime("%Y%m%d_%H"), np.mean(meta['heights'])) print(savename) fig.savefig(savename, dpi=180) plt.close('all')
lon = data["lon"] lat = data["lat"] uwind = data["u-component_of_wind_isobaric"][hour].sel(isobaric5=20000) vwind = data["v-component_of_wind_isobaric"][hour].sel(isobaric5=20000) Geo_250 = data["Geopotential_height_isobaric"][hour].sel(isobaric3=25000) / 10 #assign time variables time1 = datetime.strptime(str(data.time.data[hour].astype('datetime64[ms]')), '%Y-%m-%dT%H:%M:%S.%f') time2 = datetime.strftime(time1, "%Y-%m-%d %H00 UCT") sped_250 = mpcalc.wind_speed(uwind, vwind).to('kt') #Create figure fig = plt.figure(figsize=(14, 9)) ax = fig.add_axes([1, 1, 1, 1], projection=ccrs.Miller()) #List map Coordinates Lat_west = -105 Lat_east = -55 Lon_south = 15 Lon_north = 38 #Plot extent ax.set_extent([Lat_east, Lat_west, Lon_north, Lon_south]) #add landforms ax.add_feature(cfeat.LAKES.with_scale('50m'), facecolor='white') ax.add_feature(cfeat.STATES.with_scale('50m'), linewidth=0.4, zorder=7) ax.add_feature(cfeat.COASTLINE.with_scale('50m'), edgecolor='#4F5457',
def plot_trajectories_ens(traj, savepath, ls=None, config=None): """ plot multiple trajectories into one scene Args: traj (:class:`.trajectory`): trajectory to plot instance to plot savepath (str): path to save ls (:class:`trace_source.land_sfc.land_sfc`, optional): pre loaded land surface information config (dict, optional): the toml derived config dict Returns: None """ import matplotlib matplotlib.use('Agg') import cartopy.crs as ccrs import matplotlib.pyplot as plt if ls is None: ls = trace_source.land_sfc.land_sfc() colors = ['purple', 'darkorange', 'hotpink', 'dimgrey'] c = 'purple' if not os.path.isdir(savepath): os.makedirs(savepath) ### # the map ### fig = plt.figure(figsize=(8, 10)) if config is not None and "centerlon" in config['plotmap']: ax = plt.axes(projection=ccrs.Miller( central_longitude=config['plotmap']['centerlon'])) else: ax = plt.axes(projection=ccrs.Miller(central_longitude=-170.)) ax = plt.axes(projection=ccrs.Miller()) # Projection for the north pole # ax = plt.axes(projection=ccrs.NorthPolarStereo()) raise ValueError('provide plotmap.centerlon in the config file') #### # make a color map of fixed colors cmap = matplotlib.colors.ListedColormap([ 'lightskyblue', 'darkgreen', 'khaki', 'palegreen', 'red', 'white', 'tan' ]) bounds = [-0.5, 0.5, 1.5, 2.5, 3.5, 4.5, 5.5, 6.5] norm = matplotlib.colors.BoundaryNorm(bounds, cmap.N) #### pcm = ax.pcolormesh(ls.longs, ls.lats, ls.land_sfc, cmap=cmap, norm=norm, transform=ccrs.PlateCarree()) ax.coastlines() for k, v in traj.data.items(): ax.plot(v['longitude'], v['latitude'], linewidth=1.5, color=c, transform=ccrs.Geodetic()) ax.plot(v['longitude'][::24], v['latitude'][::24], '.', color=c, transform=ccrs.Geodetic()) ax.gridlines(linestyle=':') if config is not None and "bounds" in config['plotmap']: ax.set_extent(config['plotmap']['bounds'], crs=ccrs.PlateCarree()) else: # bounds for punta arenas ax.set_extent([-180, 180, -75, 0], crs=ccrs.PlateCarree()) # bounds for atlantic #ax.set_extent([-180, 80, -70, 75], crs=ccrs.PlateCarree()) # bounds for the north pole #ax.set_extent([-180, 180, 50, 90], crs=ccrs.PlateCarree()) raise ValueError('provide plotmap.bounds in the config file') ax.set_title('Trajectory {}UTC\n{} {} '.format( traj.info['date'].strftime('%Y-%m-%d %H'), traj.info['lat'], traj.info['lon']), fontweight='semibold', fontsize=13) savename = savepath + "/" + traj.info['date'].strftime("%Y%m%d_%H") \ + '_' + '{:0>5.0f}'.format(traj.info['height']) + "_trajectories_map.png" fig.savefig(savename, dpi=250) plt.close() ### # the profile ### fig, ax = plt.subplots(4, 1, figsize=(6, 7), sharex=True) ax[0].grid(True, axis='y') for k, v in traj.data.items(): ax[0].plot(v['time'], v['height']) ax[1].plot(v['time'], v['AIR_TEMP'][:] - 273.15) ax[2].plot(v['time'], v['RELHUMID'][:]) ax[3].plot(v['time'], v['RAINFALL'][:]) ax[0].set_ylim(0, 10000) ax[0].set_ylabel('Height [m]') ax[0].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[0].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[0].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) # ax[1].set_ylim(0,10000) ax[1].set_ylabel('Temperature [°C]') ax[1].set_ylim(-40, 10) ax[1].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[1].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[1].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) # ax[2].grid(True, axis='y') ax[2].set_ylim(0, 100) ax[2].set_ylabel('rel Humidity [%]') ax[2].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[2].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[2].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) # ax[3].grid(True, axis='y') ax[3].set_ylim(0, 20) ax[3].set_xlabel('Day') ax[3].set_ylabel('Precip [mm]') ax[3].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[3].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[3].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) for axis in ax: axis.tick_params(axis='both', which='both', right=True, top=True, direction='in') ax[0].set_title('Trajectory {}UTC\n{} {} '.format( traj.info['date'].strftime('%Y-%m-%d %H'), traj.info['lat'], traj.info['lon']), fontweight='semibold', fontsize=13) fig.tight_layout() savename = savepath + "/" + traj.info['date'].strftime("%Y%m%d_%H") \ + '_' + '{:0>5.0f}'.format(traj.info['height']) + "_trajectories_prof.png" fig.savefig(savename, dpi=250) plt.close()
x = _x[lim[0]:lim[1]] y = _y[lim[2]:lim[3]] c = _c[lim[2]:lim[3],lim[0]:lim[1]] data = nc.variables['CMI_C13'] satvar = nc.variables.keys() proj_var = nc.variables[data.grid_mapping] globe = ccrs.Globe(ellipse='sphere', semimajor_axis=proj_var.semi_major_axis, semiminor_axis=proj_var.semi_minor_axis) proj = ccrs.Geostationary(central_longitude=-75, sweep_axis='x', satellite_height=sat_height, globe = globe) trans = ccrs.Miller(central_longitude=-75) x, y = np.meshgrid(x, y) fig = plt.figure(figsize=(15, 15)) ax = fig.add_subplot(1, 1, 1, projection=trans) vmin = 198 vmax = 320 lcl = 268 colormap = colortables.get_colortable('ir_rgbv') colormap = pyart.graph.cm.NWSRef_r
#Spread of precip change across all 32 models, ordered from most drying to wetting (Fig S1) files = os.listdir(root + 'bcsd/rcp85/') p_files = sorted([f for f in files if f[0] == 'B' and f[14] == 'p']) order = [ 21, 22, 5, 13, 23, 0, 11, 31, 14, 24, 30, 10, 9, 27, 19, 29, 28, 20, 2, 26, 17, 7, 16, 25, 15, 6, 4, 8, 3, 12, 18, 1 ] #from script 1 fig, axs = plt.subplots( 4, 8, gridspec_kw={'width_ratios': [1, 1, 1, 1, 1, 1, 1, 1.3]}, figsize=(14, 8), subplot_kw={'projection': ccrs.Miller()}) axs = axs.flatten() for i in range(32): model_name = p_files[order[i]].split('_')[4] dp = change.sel(models=i, variables=['p_spring', 'p_fall', 'p_summer', 'p_winter' ]).mean(dim='variables') * 365.25 axs[i].set_extent([235, 246, 33, 45], crs=ccrs.Miller()) contour_plot = axs.flatten()[i].contourf(dp.longitude, dp.latitude, dp, np.arange(-550, 600, 50), cmap='seismic_r', extend='both', transform=ccrs.PlateCarree())
def draw_composite_map(date_obj, t850, u200, v200, u500, v500, mslp, gh500, u850, v850, pwat): """ Draw synoptic composite map. Args: map_subset (int, optional): [description]. Defaults to 1. map_region (list, optional): [description]. Defaults to [70, 140, 20, 60]. """ #Get lat and lon arrays for this dataset: lat = t850.lat.values lon = t850.lon.values #======================================================================================================== # Create a Basemap plotting figure and add geography #======================================================================================================== #Create a Plate Carree projection object proj_ccrs = ccrs.Miller(central_longitude=0.0) #Create figure and axes for main plot and colorbars fig = plt.figure(figsize=(18, 12), dpi=125) gs = gridspec.GridSpec(12, 36, figure=fig) #[ytop:ybot, xleft:xright] ax = plt.subplot(gs[:, :-1], projection=proj_ccrs) #main plot ax.set_xticklabels([]) ax.set_yticklabels([]) ax2 = plt.subplot(gs[:4, -1]) #top plot ax2.set_xticklabels([]) ax2.set_yticklabels([]) ax3 = plt.subplot(gs[4:8, -1]) #bottom plot ax3.set_xticklabels([]) ax3.set_yticklabels([]) ax4 = plt.subplot(gs[8:, -1]) #bottom plot ax4.set_xticklabels([]) ax4.set_yticklabels([]) #Add political boundaries and coastlines ax.add_feature(cfeature.COASTLINE.with_scale('50m'), linewidths=1.2) ax.add_feature(cfeature.BORDERS.with_scale('50m'), linewidths=1.2) ax.add_feature(cfeature.STATES.with_scale('50m'), linewidths=0.5) #Add land/lake/ocean masking land_mask = cfeature.NaturalEarthFeature('physical', 'land', '50m', edgecolor='face', facecolor='#e6e6e6') sea_mask = cfeature.NaturalEarthFeature('physical', 'ocean', '50m', edgecolor='face', facecolor='#ffffff') lake_mask = cfeature.NaturalEarthFeature('physical', 'lakes', '50m', edgecolor='face', facecolor='#ffffff') ax.add_feature(sea_mask, zorder=0) ax.add_feature(land_mask, zorder=0) ax.add_feature(lake_mask, zorder=0) #======================================================================================================== # Fill contours #======================================================================================================== #-------------------------------------------------------------------------------------------------------- # 850-hPa temperature #-------------------------------------------------------------------------------------------------------- #Specify contour settings clevs = np.arange(-40, 40, 1) cmap = plt.cm.jet extend = "both" #Contour fill this variable norm = col.BoundaryNorm(clevs, cmap.N) cs = ax.contourf(lon, lat, t850, clevs, cmap=cmap, norm=norm, extend=extend, transform=proj_ccrs, alpha=0.1) #-------------------------------------------------------------------------------------------------------- # PWAT #-------------------------------------------------------------------------------------------------------- #Specify contour settings clevs = np.arange(20, 71, 0.5) #Define a color gradient for PWAT pwat_colors = gradient([[(255, 255, 255), 0.0], [(255, 255, 255), 20.0]], [[(205, 255, 205), 20.0], [(0, 255, 0), 34.0]], [[(0, 255, 0), 34.0], [(0, 115, 0), 67.0]]) cmap = pwat_colors.get_cmap(clevs) extend = "max" #Contour fill this variable norm = col.BoundaryNorm(clevs, cmap.N) cs = ax.contourf(lon, lat, pwat, clevs, cmap=cmap, norm=norm, extend=extend, transform=proj_ccrs, alpha=0.9) #Add a color bar cbar = plt.colorbar(cs, cax=ax2, shrink=0.75, pad=0.01, ticks=[20, 30, 40, 50, 60, 70]) #-------------------------------------------------------------------------------------------------------- # 250-hPa wind #-------------------------------------------------------------------------------------------------------- #Get the data for this variable wind = calc.wind_speed(u200, v200) #Specify contour settings clevs = [40, 50, 60, 70, 80, 90, 100, 110] cmap = col.ListedColormap([ '#99E3FB', '#47B6FB', '#0F77F7', '#AC97F5', '#A267F4', '#9126F5', '#E118F3', '#E118F3' ]) extend = "max" #Contour fill this variable norm = col.BoundaryNorm(clevs, cmap.N) cs = ax.contourf(lon, lat, wind, clevs, cmap=cmap, norm=norm, extend=extend, transform=proj_ccrs) #Add a color bar cbar = plt.colorbar(cs, cax=ax3, shrink=0.75, pad=0.01, ticks=clevs) #-------------------------------------------------------------------------------------------------------- # 500-hPa smoothed vorticity #-------------------------------------------------------------------------------------------------------- #Get the data for this variable dx, dy = calc.lat_lon_grid_deltas(lon, lat) vort = calc.vorticity(u500, v500, dx, dy) smooth_vort = smooth(vort, 5.0) * 10**5 #Specify contour settings clevs = np.arange(2, 20, 1) cmap = plt.cm.autumn_r extend = "max" #Contour fill this variable norm = col.BoundaryNorm(clevs, cmap.N) cs = ax.contourf(lon, lat, smooth_vort, clevs, cmap=cmap, norm=norm, extend=extend, transform=proj_ccrs, alpha=0.3) #Add a color bar cbar = plt.colorbar(cs, cax=ax4, shrink=0.75, pad=0.01, ticks=clevs[::2]) #======================================================================================================== # Contours #======================================================================================================== #-------------------------------------------------------------------------------------------------------- # MSLP #-------------------------------------------------------------------------------------------------------- #Specify contour settings clevs = np.arange(960, 1040 + 4, 4) style = 'solid' #Plot solid lines color = 'red' #Plot lines as gray width = 0.8 #Width of contours 0.25 #Contour this variable cs = ax.contour(lon, lat, mslp, clevs, colors=color, linewidths=width, linestyles=style, transform=proj_ccrs, alpha=0.9) #Include value labels ax.clabel(cs, inline=1, fontsize=9, fmt='%d') #-------------------------------------------------------------------------------------------------------- # Geopotential heights #-------------------------------------------------------------------------------------------------------- #Get the data for this variable gh500 = gh500 / 10.0 #Specify contour settings clevs = np.arange(480, 612, 4) style = 'solid' #Plot solid lines color = 'black' #Plot lines as gray width = 2.0 #Width of contours #Contour this variable cs = ax.contour(lon, lat, gh500, clevs, colors=color, linewidths=width, linestyles=style, transform=proj_ccrs) #Include value labels ax.clabel(cs, inline=1, fontsize=12, fmt='%d') #-------------------------------------------------------------------------------------------------------- # Surface barbs #-------------------------------------------------------------------------------------------------------- #Plot wind barbs quivers = ax.quiver(lon, lat, u850.values, v850.values, transform=proj_ccrs, regrid_shape=(38, 30), scale=820, alpha=0.5) #-------------------------------------------------------------------------------------------------------- # Label highs & lows #-------------------------------------------------------------------------------------------------------- #Label highs and lows add_mslp_label(ax, proj_ccrs, mslp, lat, lon) #======================================================================================================== # Step 6. Add map boundary, legend, plot title, then save image and close #======================================================================================================== #Add china province boundary add_china_map_2cartopy(ax, name='province') #Add custom legend from matplotlib.lines import Line2D custom_lines = [ Line2D([0], [0], color='#00A123', lw=5), Line2D([0], [0], color='#0F77F7', lw=5), Line2D([0], [0], color='#FFC000', lw=5), Line2D([0], [0], color='k', lw=2), Line2D([0], [0], color='k', lw=0.1, marker=r'$\rightarrow$', ms=20), Line2D([0], [0], color='r', lw=0.8), ] ax.legend(custom_lines, [ 'PWAT (mm)', '200-hPa Wind (m/s)', '500-hPa Vorticity', '500-hPa Height (dam)', '850-hPa Wind (m/s)', 'MSLP (hPa)' ], loc=2, prop={'size': 12}) #Format plot title title = "Synoptic Composite \nValid: " + dt.datetime.strftime( date_obj, '%Y-%m-%d %H%M UTC') st = plt.suptitle(title, fontweight='bold', fontsize=16) st.set_y(0.92) #Return figuration return (fig)
Pred = xr.open_dataset(sys.argv[1]) #Prediction Dataset Actual_glm = xr.open_dataset(sys.argv[2]) #Actual Lightning Dataset print(Pred) print(Actual_glm) #get data from datasets light_prob = Pred.data_vars['lightning_prob'] actual_light = Actual_glm.data_vars['lightning_counts'] lons = Pred.data_vars['lon'] lats = Pred.data_vars['lat'] #clean up the actual dataset actual_light.values = actual_light.values.astype('float64') actual_light.values[actual_light.values <= 0.0] = np.nan #plot data and create animation fig = plt.figure(figsize=(18, 12)) ax = plt.axes(projection=ccrs.Miller()) states = cfeature.STATES.with_scale('10m') ax.add_feature(states, edgecolor='black') pred_bounds = np.array([0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1]) norm = colors.BoundaryNorm(boundaries=pred_bounds, ncolors=200, clip=True) Pred = ax.pcolormesh(lons, lats, light_prob[0, :, :], transform=ccrs.Miller(), norm=norm, cmap='Reds', vmin=0.1, vmax=1) Actual = ax.pcolormesh(lons, lats, actual_light[0, :, :],
import cartopy.crs as ccrs import cartopy from cartopy.io.shapereader import Reader from cartopy.feature import ShapelyFeature root = '/Users/scoffiel/california/' SCENARIO = 'rcp85' results = xr.open_dataset( root + 'model_output/1_RF_regression/{}_mean.nc4'.format(SCENARIO)).carbon_change table = results.to_dataframe('change').dropna().reset_index() #first panel: map of change plot with offsets overlaid fig = plt.figure(figsize=(7, 9)) ax = fig.add_subplot(211, projection=ccrs.Miller()) ax.set_extent([235, 245, 39, 45], crs=ccrs.Miller()) ecoregions = ShapelyFeature( Reader(root + "epa_ecoregions3/level3_cali.shp").geometries(), ccrs.PlateCarree()) projects = ShapelyFeature( Reader(root + "carb_shapefiles/offsets/offsets_cali.shp").geometries(), ccrs.PlateCarree()) states = cartopy.feature.NaturalEarthFeature( category='cultural', name='admin_1_states_provinces_lakes_shp', scale='110m', facecolor='none') ax.add_feature(ecoregions, edgecolor='0.3', facecolor='none', linewidth=0.2) ax.add_feature(states, edgecolor='0.2') ax.add_feature(projects, edgecolor='0', facecolor='0')
dim=['variables', 'models']) p_change85 = (future_climate85.sel( variables=['p_fall', 'p_spring', 'p_summer', 'p_winter']).mean( dim=['variables', 'models']) - present_climate85.sel( variables=['p_fall', 'p_spring', 'p_summer', 'p_winter']).mean( dim=['variables', 'models'])) * 365.25 fig, axs = plt.subplots(2, 3, gridspec_kw={'width_ratios': [6, 5, 6]}, figsize=(17, 10), subplot_kw={'projection': ccrs.PlateCarree()}) (ax1, ax2, ax3), (ax4, ax5, ax6) = axs #1 - present temp ax1.set_extent([235.5, 246, 33, 45], crs=ccrs.Miller()) plot = ax1.pcolor(present_t.longitude, present_t.latitude, present_t, transform=ccrs.PlateCarree(), cmap='plasma') states = cartopy.feature.NaturalEarthFeature( category='cultural', name='admin_1_states_provinces_lakes_shp', scale='110m', facecolor='none') ax1.add_feature(states, edgecolor='0.2') ax1.set_title('Present-day temperature', fontsize=18) cbar = plt.colorbar(plot, orientation='vertical', shrink=0.8, pad=0.01, ax=ax1) cbar.set_label('\u00B0C', size=18) cbar.ax.tick_params(labelsize=15)
export.to_dataset(name='carbon_change').to_netcdf( root + 'model_output/3_climate_analogs/{}_{}.nc4'.format(SCENARIO, MODEL)) #save table as csv (at least for RCP85 mean scenario) for script 10 plots #table_cali.to_csv(root + 'model_output/3_climate_analogs/table_rcp85_mean.csv') #plotting ---------------------------------------------------------------------------------- states = cartopy.feature.NaturalEarthFeature( category='cultural', name='admin_1_states_provinces_lakes_shp', scale='110m', facecolor='none') #change plot fig = plt.figure(figsize=(7, 7)) ax2 = fig.add_subplot(111, projection=ccrs.Miller()) ax2.set_extent([235.5, 246, 33, 45], crs=ccrs.Miller()) ecoregions = ShapelyFeature( Reader(root + "epa_ecoregions3/level3_cali.shp").geometries(), ccrs.PlateCarree()) ax2.add_feature(ecoregions, edgecolor='0.3', facecolor='none', linewidth=0.2) ax2.add_feature(states, edgecolor='0.2') plot = ax2.scatter(table_cali.longitude - 360, table_cali.latitude, c=table_cali.change * 0.47, s=10, vmin=-75, vmax=75, marker='s', cmap='PRGn', transform=ccrs.PlateCarree()) #change scale as needed
def plot_cities_in_svg(cities: dict, out_dir=None, radius_m=2000): if out_dir is None: out_dir = Path(__file__).parent.parent / "out_svg" fig_dir = Path(out_dir) fig_dir.mkdir(exist_ok=True) # Define the CartoPy CRS object. crs = ccrs.Miller() # This can be converted into a `proj4` string/dict compatible with GeoPandas crs_proj4 = crs.proj4_init city_to_data = OrderedDict() city_to_extent = OrderedDict() # get the data and compute some things for ci, city in enumerate(cities): print(f"Downloading {city}") try: # blds = ox.buildings_from_place(city) blds = download_buildings_cached_for(city, cities, radius_m=radius_m) except TypeError: continue # blds.plot(facecolor="indigo", ax=ax) blds = blds.to_crs(crs_proj4) minx, miny, maxx, maxy = blds.total_bounds city_to_data[city] = blds city_to_extent[city] = [minx, maxx, miny, maxy] gs = GridSpec(1, 1, hspace=0, wspace=0) # plotting for ci, city in enumerate(cities): city_img = fig_dir / f"{city}.svg" if city_img.exists(): print(f"{city_img} already exists, remove to redraw.") else: fig = plt.figure(figsize=(5, 5), frameon=False) ax = fig.add_subplot(gs[0, 0], projection=crs) blds = city_to_data[city] # Plot print(f"Plotting {city}") ax.add_geometries(blds['geometry'], crs=crs, facecolor="k", edgecolor="none", linewidth=0) ax.set_extent(city_to_extent[city], crs=crs) ax.get_xaxis().set_visible(False) ax.get_yaxis().set_visible(False) ax.outline_patch.set_visible(False) ax.background_patch.set_visible(False) add_river_shapes(ax, city, crs=ccrs.PlateCarree()) # add_river_shapes(ax, city, crs=ccrs.epsg(5713)) # ax.add_geometries(Reader(river_shapes_path).geometries(), # ccrs.PlateCarree(), # facecolor=feature.COLORS["water"], linewidth=0, zorder=-10) # ax.add_feature(NaturalEarthFeature("physical", "rivers_lake_centerlines", "10m"), # linewidth=0.5, facecolor=feature.COLORS["water"], # edgecolor=feature.COLORS["water"]) fontsize = 10 scale_bar_only(ax, crs, length=10, fontsize=fontsize, location=(0.5, 0.06), linewidth=1) ax.set_title(city, fontsize=fontsize) fig.savefig(str(city_img), bbox_inches="tight") north_arrow(city_img)
def test_unsupported_projection(self): source = ogc.WMTSRasterSource(self.URI, self.layer_name) msg = 'Unable to find tile matrix for projection.' with self.assertRaisesRegexp(ValueError, msg): source.validate_projection(ccrs.Miller())
def plotmap(variable, data, masked_data, str_type='', plot_time='', save=False): # definitions for the axes left, width = 0.1, 0.8 bottom, height = 0.1, 0.7 spacing = 0.005 rect_map = [left, bottom + 0.15, width, height] rect_his = [left, bottom, width, 0.15] # Set up values for gridding the AI data latmin = 60 lat_gridder = latmin * 4. lat_ranges = np.arange(latmin, 90.1, 0.25) lon_ranges = np.arange(-180, 180.1, 0.25) # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # Plot the gridded data # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #print("Time to plot") mapcrs = ccrs.NorthPolarStereo() datacrs = ccrs.PlateCarree() colormap = plt.cm.jet # Set up the polar stereographic projection map plt.clf() plt.figure(figsize=(8, 8)) if (latmin < 45): axs_map = plt.axes(rect_map, projection=ccrs.Miller()) else: axs_map = plt.axes( rect_map, projection=ccrs.NorthPolarStereo(central_longitude=0.)) axs_map.gridlines() axs_map.coastlines(resolution='50m') # Use meshgrid to convert the 1-d lat/lon arrays into 2-d, which is needed # for pcolormesh. plot_lat, plot_lon = np.meshgrid(lat_ranges, lon_ranges) plt.title('OMI ' + variable + str_type + ' ' + plot_time) mesh = axs_map.pcolormesh(plot_lon, plot_lat,masked_data,transform = datacrs,cmap = colormap,\ vmin = var_dict[variable]['min'], vmax = var_dict[variable]['max']) # Center the figure over the Arctic axs_map.set_extent([-180, 180, latmin, 90], ccrs.PlateCarree()) axs_his = plt.axes(rect_his) axs_his.hist(masked_data.flatten(), 1000, log=True, range=(var_dict[variable]['min'], var_dict[variable]['max'])) axs_his.tick_params( axis='x', # changes apply to the x-axis which='both', # both major and minor ticks are affected bottom=False, # ticks along the bottom edge are off top=False, # ticks along the top edge are off labelbottom=False) # labels along the bottom edge are off # Depending on the desired variable, set the appropriate colorbar ticks if (variable == 'NormRadiance'): tickvals = np.arange(0.0, 0.101, 0.01) elif (variable == 'Reflectivity'): tickvals = np.arange(0.0, 1.1, 0.10) else: tickvals = np.arange(-2.0, 4.1, 0.5) cbar = plt.colorbar(mesh,ticks = tickvals,orientation='horizontal',pad=.01,\ aspect=50,shrink = 0.905,label=variable) if (save == True): out_name = 'figs/omi_climo_' + name_dict[ variable] + str_type + '_' + plot_time + '.png' plt.savefig(out_name) print('Saved image ' + out_name) plt.close() else: plt.show() plt.close()
def test_unsupported_projection(self): source = ogc.WMSRasterSource(self.URI, self.layer) msg = 'was not convertible to a suitable WMS SRS.' with self.assertRaisesRegexp(ValueError, msg): source.validate_projection(ccrs.Miller())
def animate_map(ds: xr.Dataset, var: VarName.TYPE = None, animate_dim: str = 'time', interval: int = 200, true_range: bool = False, indexers: DictLike.TYPE = None, region: PolygonLike.TYPE = None, projection: str = 'PlateCarree', central_lon: float = 0.0, title: str = None, contour_plot: bool = False, cmap_params: DictLike.TYPE = None, plot_properties: DictLike.TYPE = None, file: str = None, monitor: Monitor = Monitor.NONE) -> HTML: """ Create a geographic map animation for the variable given by dataset *ds* and variable name *var*. Creates an animation of the given variable from the given dataset on a map with coastal lines. In case no variable name is given, the first encountered variable in the dataset is animated. It is also possible to set extents of the animation. If no extents are given, a global animation is created. The following file formats for saving the animation are supported: html :param ds: the dataset containing the variable to animate :param var: the variable's name :param animate_dim: Dimension to animate, if none given defaults to time. :param interval: Delay between frames in milliseconds. Defaults to 200. :param true_range: If True, calculates colormap and colorbar configuration parameters from the whole dataset. Can potentially take a lot of time. Defaults to False, in which case the colormap is calculated from the first frame. :param indexers: Optional indexers into data array of *var*. The *indexers* is a dictionary or a comma-separated string of key-value pairs that maps the variable's dimension names to constant labels. e.g. "layer=4". :param region: Region to animate :param projection: name of a global projection, see http://scitools.org.uk/cartopy/docs/v0.15/crs/projections.html :param central_lon: central longitude of the projection in degrees :param title: an optional title :param contour_plot: If true plot a filled contour plot of data, otherwise plots a pixelated colormesh :param cmap_params: optional additional colormap configuration parameters, e.g. "vmax=300, cmap='magma'" For full reference refer to http://xarray.pydata.org/en/stable/generated/xarray.plot.contourf.html :param plot_properties: optional plot properties for Python matplotlib, e.g. "bins=512, range=(-1.5, +1.5)" For full reference refer to https://matplotlib.org/api/lines_api.html and https://matplotlib.org/api/_as_gen/matplotlib.axes.Axes.contourf.html :param file: path to a file in which to save the animation :param monitor: A progress monitor. :return: An animation in HTML format """ if not isinstance(ds, xr.Dataset): raise NotImplementedError('Only gridded datasets are currently supported') var_name = None if not var: for key in ds.data_vars.keys(): var_name = key break else: var_name = VarName.convert(var) try: var = ds[var_name] except KeyError: raise ValidationError('Provided variable name "{}" does not exist in the given dataset'.format(var_name)) indexers = DictLike.convert(indexers) or {} properties = DictLike.convert(plot_properties) or {} cmap_params = DictLike.convert(cmap_params) or {} extents = None bounds = handle_plot_polygon(region) if bounds: lon_min, lat_min, lon_max, lat_max = bounds extents = [lon_min, lon_max, lat_min, lat_max] if len(ds.lat) < 2 or len(ds.lon) < 2: # Matplotlib can not plot datasets with less than these dimensions with # contourf and pcolormesh methods raise ValidationError('The minimum dataset spatial dimensions to create a map' ' plot are (2,2)') # See http://scitools.org.uk/cartopy/docs/v0.15/crs/projections.html# if projection == 'PlateCarree': proj = ccrs.PlateCarree(central_longitude=central_lon) elif projection == 'LambertCylindrical': proj = ccrs.LambertCylindrical(central_longitude=central_lon) elif projection == 'Mercator': proj = ccrs.Mercator(central_longitude=central_lon) elif projection == 'Miller': proj = ccrs.Miller(central_longitude=central_lon) elif projection == 'Mollweide': proj = ccrs.Mollweide(central_longitude=central_lon) elif projection == 'Orthographic': proj = ccrs.Orthographic(central_longitude=central_lon) elif projection == 'Robinson': proj = ccrs.Robinson(central_longitude=central_lon) elif projection == 'Sinusoidal': proj = ccrs.Sinusoidal(central_longitude=central_lon) elif projection == 'NorthPolarStereo': proj = ccrs.NorthPolarStereo(central_longitude=central_lon) elif projection == 'SouthPolarStereo': proj = ccrs.SouthPolarStereo(central_longitude=central_lon) else: raise ValidationError('illegal projection: "%s"' % projection) figure = plt.figure(figsize=(8, 4)) ax = plt.axes(projection=proj) if extents: ax.set_extent(extents, ccrs.PlateCarree()) else: ax.set_global() ax.coastlines() if not animate_dim: animate_dim = 'time' indexers[animate_dim] = var[animate_dim][0] var_data = get_var_data(var, indexers, remaining_dims=('lon', 'lat')) with monitor.starting("animate", len(var[animate_dim]) + 3): if true_range: data_min, data_max = _get_min_max(var, monitor=monitor) else: data_min, data_max = _get_min_max(var_data, monitor=monitor) cmap_params = determine_cmap_params(data_min, data_max, **cmap_params) plot_kwargs = {**properties, **cmap_params} # Plot the first frame to set-up the axes with the colorbar properly # transform keyword is for the coordinate our data is in, which in case of a # 'normal' lat/lon dataset is PlateCarree. if contour_plot: var_data.plot.contourf(ax=ax, transform=ccrs.PlateCarree(), subplot_kws={'projection': proj}, add_colorbar=True, **plot_kwargs) else: var_data.plot.pcolormesh(ax=ax, transform=ccrs.PlateCarree(), subplot_kws={'projection': proj}, add_colorbar=True, **plot_kwargs) if title: ax.set_title(title) figure.tight_layout() monitor.progress(1) def run(value): ax.clear() if extents: ax.set_extent(extents, ccrs.PlateCarree()) else: ax.set_global() ax.coastlines() indexers[animate_dim] = value var_data = get_var_data(var, indexers, remaining_dims=('lon', 'lat')) var_data.plot.contourf(ax=ax, transform=ccrs.PlateCarree(), subplot_kws={'projection': proj}, add_colorbar=False, **plot_kwargs) if title: ax.set_title(title) monitor.progress(1) return ax anim = animation.FuncAnimation(figure, run, [i for i in var[animate_dim]], interval=interval, blit=False, repeat=False) anim_html = anim.to_jshtml() # Prevent the animation for running after it's finished del anim # Delete the rogue temp-file try: os.remove('None0000000.png') except FileNotFoundError: pass if file: with open(file, 'w') as outfile: outfile.write(anim_html) monitor.progress(1) return HTML(anim_html)
def plot_trajectories_ens(traj, savepath, ls=None, config=None): """ plot multiple trajectories into one scene Args: traj (:class:`.trajectory`): trajectory to plot instance to plot savepath (str): path to save ls (:class:`trace_source.land_sfc.land_sfc`, optional): pre loaded land surface information config (dict, optional): the toml derived config dict Returns: None """ import matplotlib matplotlib.use('Agg') import cartopy.crs as ccrs import matplotlib.pyplot as plt if ls is None: ls = trace_source.land_sfc.land_sfc() colors = ['purple', 'darkorange', 'hotpink', 'dimgrey'] linecolor = 'grey' if not os.path.isdir(savepath): os.makedirs(savepath) ### # the map ### fig = plt.figure(figsize=(8, 10)) if config is not None and "centerlon" in config['plotmap']: ax = plt.axes(projection=ccrs.Miller( central_longitude=config['plotmap']['centerlon'])) else: ax = plt.axes(projection=ccrs.Miller(central_longitude=-170.)) ax = plt.axes(projection=ccrs.Miller()) # Projection for the north pole # ax = plt.axes(projection=ccrs.NorthPolarStereo()) raise ValueError('provide plotmap.centerlon in the config file') #ax = plt.axes(projection=ccrs.NorthPolarStereo()) #### # make a color map of fixed colors # cmap = matplotlib.colors.ListedColormap(['lightskyblue', 'darkgreen', 'khaki', 'palegreen', 'red', 'white', 'tan']) # fainter colors as in the flexpart plot colors = [ 'lightskyblue', 'seagreen', 'khaki', '#6edd6e', 'darkmagenta', 'lightgray', 'tan' ] #colors = ['lightskyblue', 'seagreen', 'khaki', '#a4dd6e', 'red', 'white', 'tan'] cmap = matplotlib.colors.ListedColormap(colors) cs = [] for ind in range(cmap.N): c = [] for x in cmap(ind)[:3]: c.append(x * 1.1 * 255.) cs.append([sc / 255. for sc in redistribute_rgb(*c)]) cmap = matplotlib.colors.ListedColormap(cs) bounds = [-0.5, 0.5, 1.5, 2.5, 3.5, 4.5, 5.5, 6.5] norm = matplotlib.colors.BoundaryNorm(bounds, cmap.N) #### pcm = ax.pcolormesh(ls.longs, ls.lats, ls.land_sfc_data.astype(np.float64), cmap=cmap, norm=norm, transform=ccrs.PlateCarree()) # high resolution coastlines #ax.coastlines(resolution='110m') ax.coastlines(resolution='50m') # ax.coastlines(resolution='10m') for k, v in traj.data.items(): ax.plot(v['longitude'], v['latitude'], linewidth=0.7, zorder=2, color=linecolor, transform=ccrs.Geodetic()) # ax.plot(v['longitude'][::24], v['latitude'][::24], '.', # color='k', # transform=ccrs.Geodetic()) scat = ax.scatter(v['longitude'][::12], v['latitude'][::12], s=3, c=v['height'][::12] / 1000., cmap='plasma', vmin=0.1, vmax=7.0, zorder=4, transform=ccrs.PlateCarree()) cbar = fig.colorbar(scat, fraction=0.025, pad=0.01) cbar.ax.set_ylabel('Height [km]', fontweight='semibold', fontsize=12) cbar.ax.tick_params(axis='both', which='major', labelsize=12, width=2, length=4) ax.gridlines(linestyle=':') if config is not None and "bounds" in config['plotmap']: ax.set_extent(config['plotmap']['bounds'], crs=ccrs.PlateCarree()) else: # bounds for punta arenas ax.set_extent([-180, 180, -75, 0], crs=ccrs.PlateCarree()) # bounds for atlantic #ax.set_extent([-180, 80, -70, 75], crs=ccrs.PlateCarree()) # bounds for the north pole raise ValueError('provide plotmap.bounds in the config file') #ax.set_extent([-180, 180, 50, 90], crs=ccrs.PlateCarree()) ax.set_title('Trajectories {}UTC\n{} {} {:5.0f}m'.format( traj.info['date'].strftime('%Y-%m-%d %H'), traj.info['lat'], traj.info['lon'], traj.info['height']), fontweight='semibold', fontsize=13) savename = savepath + "/" + traj.info['date'].strftime("%Y%m%d_%H") \ + '_' + '{:0>5.0f}'.format(traj.info['height']) + "_trajectories_map.png" fig.savefig(savename, dpi=250) plt.close() ### # the profile ### fig, ax = plt.subplots(4, 1, figsize=(6, 7), sharex=True) ax[0].grid(True, axis='y') for k, v in traj.data.items(): ax[0].plot(v['time'], v['height']) ax[1].plot(v['time'], v['AIR_TEMP'][:] - 273.15) ax[2].plot(v['time'], v['RELHUMID'][:]) ax[3].plot(v['time'], v['RAINFALL'][:]) ax[0].set_ylim(0, 10000) # ax[0].set_ylim(0, 13000) ax[0].set_ylabel('Height [m]') ax[0].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[0].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[0].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) # ax[1].set_ylim(0,10000) ax[1].set_ylabel('Temperature [°C]') ax[1].set_ylim(-40, 10) # ax[1].set_ylim(-60, 10) ax[1].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[1].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[1].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) # ax[2].grid(True, axis='y') ax[2].set_ylim(0, 100) ax[2].set_ylabel('rel Humidity [%]') ax[2].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[2].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[2].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) # ax[3].grid(True, axis='y') ax[3].set_ylim(0, 20) # modified plot for publication # ax[3].set_ylim(0, 5) ax[3].set_xlabel('Day') ax[3].set_ylabel('Precip [mm]') ax[3].xaxis.set_major_locator(matplotlib.dates.DayLocator(interval=2)) ax[3].xaxis.set_minor_locator(matplotlib.dates.HourLocator([0, 12])) ax[3].xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m-%d')) for axis in ax: axis.tick_params(axis='both', which='both', right=True, top=True, direction='in') ax[0].set_title('Trajectory {}UTC\n{} {} '.format( traj.info['date'].strftime('%Y-%m-%d %H'), traj.info['lat'], traj.info['lon']), fontweight='semibold', fontsize=13) fig.tight_layout() savename = savepath + "/" + traj.info['date'].strftime("%Y%m%d_%H") \ + '_' + '{:0>5.0f}'.format(traj.info['height']) + "_trajectories_prof.png" fig.savefig(savename, dpi=250) plt.close()
def 250hPa_GFS_jet_stream_jet_dyn(lon_west, lon_east, lat_south, lat_north): # 500: VORTICITY, GEOPOTENTIAL HEIGHT, VORTICITY ADVECTION def 500hPa_GFS_vorticity(lon_west, lon_east, lat_south, lat_north): LATEST_DATA.variables('Geopotential_height_isobaric', 'u-component_of_wind_isobaric', 'v-component_of_wind_isobaric').add_lonlat() LATEST_DATA.lonlat_box(lon_west, lon_east, lat_south, lat_north) LATEST_DATA.vertical_level(50000) DATA = NCSS_DATA.get_data(LATEST_DATA) DTIME = DATA.variables['Geopotential_height_isobaric'].dimensions[0] DLAT = DATA.variables['Geopotential_height_isobaric'].dimensions[2] DLON = DATA.variables['Geopotential_height_isobaric'].dimensions[3] LAT = DATA.variables[DLAT][:] LON = DATA.variables[DLON][:] TIMES = DATA.variables[DTIME] VTIMES = num2date(TIMES[:], TIMES.units) H500 = DATA.variables['Geopotential_height_isobaric'][0, 0, :, :] U500 = DATA.variables['u-component_of_wind_isobaric'][0, 0, :, :]*units('m/s') V500 = DATA.variables['v-component_of_wind_isobaric'][0, 0, :, :]*units('m/s') DTIME = DATA.variables['Geopotential_height_isobaric'].dimensions[:] f = mpcalc.coriolis_parameter(np.deg2rad(LAT)).to(units('1/sec')) DX, DY = mpcalc.lat_lon_grid_spacing(LON, LAT) VORT500 = mpcalc.vorticity(U500, V500, DX, DY, dim_order='YX') VORT500 = (VORT500*(units('1/s'))) # 700: Q-VECTORS+CONVERGENCE, GEOPOTENTIAL HEIGHT, POTENTIAL TEMPERATURE # 850: GEOPOTENTIAL HEIGHT, WINDS, TEMP-ADVECTION, FRONTOGENESIS # 925: GEOPOTENTIAL HEIGHT, WINDS, TEMP-ADVECTION, FRONTOGENESIS # SFC: MSLP, WIND, TEMPERATURE # ============================================================================= # THERMODYNAMIC VARIABLES # ============================================================================= #MUCAPE: Pre-computed in HRRR #LATEST_DATA.variables('Convective_available_potential_energy_surface').add_lonlat() #LATEST_DATA.lonlat_box(280, 295, 35, 50) #DATA = NCSS_DATA.get_data(LATEST_DATA) #SCAPE = DATA.variables['Convective_available_potential_energy_surface'][:] #LAT = DATA.variables['lat'][:] #LON = DATA.variables['lon'][:] #MLCAPE: Pre-computed in HRRR #SBCAPE: Pre-computed in HRRR #LCL: Pre-computed in HRRR #LI: Pre-computed in HRRR #EL: Pre-computed in HRRR #LAPSE RATES: Needs Temps various levels to compute. Easy. #CIN: Pre-computed in HRRR # ============================================================================= # WIND VARIABLES # ============================================================================= # SFC-1km SHEAR: Pre-computed in HRRR # SFC-6km SHEAR: Pre-computed in HRRR # SFC-1km HELICITY: Pre-computed in HRRR # SFC-3km HELICITY: Pre-computed in HRRR # UPSLOPE FLOW: Requires 80-m Wind and Terrain Height[requires surface pressure and temps] # ============================================================================= # COMPOSITE INDICES # ============================================================================= # SUPERCELL # FIXED-LAYER SIG TORNADO # LARGE HAIL # CRAVEN BROOKS # ============================================================================= # PRECIPITATION # ============================================================================= # SIMULATED REFLECTIVITY # PRECIPITATION ACCUMULATION # PRECIPITABLE WATER # MOISTURE FLUX/MOISTURE FLUX CONVERGENCE # SNOWFALL datacrs = ccrs.PlateCarree() plotcrs = ccrs.Miller(central_longitude=-95.0) # Make a grid of lat/lon values to use for plotting with Basemap. lons, lats = np.meshgrid(np.squeeze(LON), np.squeeze(LAT)) fig = plt.figure(1, figsize=(12., 13.)) gs = gridspec.GridSpec(2, 1, height_ratios=[1, .02], bottom=.07, top=.99, hspace=0.01, wspace=0.01) ax = plt.subplot(gs[0], projection=plotcrs) ax.set_title('500-hPa Geopotential Heights (m)', loc='left') ax.set_title('VALID: {}'.format(VTIMES[0]), loc='right') # ax.set_extent([west long, east long, south lat, north lat]) ax.set_extent([230, 300, 25, 55], ccrs.PlateCarree()) ax.coastlines('50m', edgecolor='black', linewidth=0.5) ax.add_feature(cfeature.STATES, linewidth=0.5) clev250 = np.arange(4800, 6600, 60) cs = ax.contour(lons, lats, H500, clev250, colors='k', linewidths=1.0, linestyles='solid', transform=datacrs) plt.clabel(cs, fontsize=8, inline=1, inline_spacing=10, fmt='%i', rightside_up=True, use_clabeltext=True) clevsped250 = np.arange(0, 55, 5) cmap = plt.cm.get_cmap('YlOrBr') cf = ax.contourf(lons, lats, np.squeeze(VORT500*10**5), clevsped250, cmap=cmap, transform=datacrs) cax = plt.subplot(gs[1]) cbar = plt.colorbar(cf, cax=cax, orientation='horizontal', extend='max', extendrect=True) gs.tight_layout(fig) plt.show()
if MODEL == 'wet': #get last 8 models only present_climate = present_climate.sel(models=slice(24, 31)) future_climate = future_climate.sel(models=slice(24, 31)) present_climate = present_climate.mean(dim='models') future_climate = future_climate.mean(dim='models') #read in vegetation data from GEE #Use GEE script 7 to simplify land cover classes and reproject to 1/8 degree #fill in NaN for anything veg = xr.open_rasterio(root + 'land_cover/landcover_eighth.tif')[0, :, :] veg = veg.where(veg > 0) #Make map of dom veg type -------------------------------------------------------------- fig = plt.figure(figsize=(8, 8)) ax = fig.add_subplot(111, projection=ccrs.Miller()) ax.set_extent([235.5, 246, 33, 45], crs=ccrs.Miller()) plot = ax.contourf(veg.x, veg.y, veg, transform=ccrs.PlateCarree(), levels=[0, 1, 2], cmap='YlGn') #PiYG states = cartopy.feature.NaturalEarthFeature( category='cultural', name='admin_1_states_provinces_lakes_shp', scale='110m', facecolor='none') ax.add_feature(states, edgecolor='0.2') ecoregions = ShapelyFeature( Reader(root + "epa_ecoregions3/level3_cali.shp").geometries(),
def pointstomap(points: list, marker_style, contourfile='ne_10m_admin_0_countries.geojson') -> io.BytesIO: #load points from actual blog with open(contourfile, 'r') as f: js = json.load(f) features = [ x for x in js['features'] if len([y for y in points if shape(x['geometry']).contains(Point(y))]) > 0 ] proj = ccrs.Miller() fig = plt.figure(dpi=96, facecolor='w', frameon=False) ax = fig.add_subplot(1, 1, 1, projection=proj) fig.patch.set_visible(False) ax.patch.set_visible(False) fig.patch.set_alpha(0) ax.patch.set_alpha(0) if marker_style == MARKER_STYLE_DOT: ax.scatter(*np.array(points).T, s=1, color='black', marker=".", linewidth=3, transform=ccrs.PlateCarree()) elif marker_style == MARKER_STYLE_LINE: ax.plot(*np.array(points).T, color='black', linewidth=1, transform=ccrs.PlateCarree()) ax.get_xaxis().set_visible(False) ax.get_yaxis().set_visible(False) plt.autoscale(tight=True) ax.spines['top'].set_visible(False) ax.spines['right'].set_visible(False) ax.spines['bottom'].set_visible(False) ax.spines['left'].set_visible(False) plt.box(False) plt.axis('off') plt.subplots_adjust(left=0, bottom=0, right=1, top=1, wspace=0, hspace=0) for feature in features: geo = shape(feature['geometry']) if geo.geom_type == 'MultiPolygon': polygons = list(geo) for polygon in polygons: ax.plot(*np.array(polygon.exterior.xy), color='grey', linewidth=1, solid_capstyle='round', transform=ccrs.PlateCarree()) elif geo.geom_type == 'Polygon': ax.plot(*np.array(geo.exterior.xy), color='grey', linewidth=1, solid_capstyle='round', transform=ccrs.PlateCarree()) imgdata = io.BytesIO() plt.savefig(imgdata, format='svg', bbox_inches=0, transparent=True) plt.close(fig) imgdata.seek(0) # rewind the data return imgdata
def sat_plot(ds): timestamp = datetime.strptime(ds.start_date_time, '%Y%j%H%M%S') print(timestamp) data_var = ds.metpy.parse_cf('Sectorized_CMI') sat_height = ds.satellite_altitude x = (ds['x'].data * sat_height) / 1000000 y = (ds['y'].data * sat_height) / 1000000 c = data_var[:].data globe = ccrs.Globe(ellipse='sphere', semimajor_axis=6378137.0, semiminor_axis=6356752.31414) proj = ccrs.Geostationary(central_longitude=-75, sweep_axis='x', satellite_height=sat_height, globe=globe) trans = ccrs.Miller(central_longitude=-75) fig = plt.figure(figsize=(15, 15)) ax = fig.add_subplot(1, 1, 1, projection=trans) vmin = .012 vmax = .8 colormap = 'Greys_r' im = ax.pcolormesh(x, y, c, cmap=colormap, vmin=vmin, vmax=vmax, transform=proj) ax.add_feature(cfeature.STATES, linewidth=2, edgecolor='black') ax.coastlines(resolution='10m', linewidth=1, edgecolor='black') ax.add_feature(cfeature.BORDERS, linewidth=1, edgecolor='black') # Colorbar cbar_ticks = np.arange(vmin, vmax, round(((abs(vmax) - abs(vmin)) / 6), 2)) cbar = fig.colorbar(im, ticks=cbar_ticks, orientation='horizontal', shrink=0.6, pad=.02) cbar.ax.set_yticklabels(str(cbar_ticks)) cbar_label = data_var.standard_name cbar.set_label(cbar_label, rotation=0, labelpad=5, fontsize=13) cbar.ax.invert_yaxis() # Figure Text txt = open('channel_title.txt', "r") titles = txt.readlines() ch = titles[int(channel)][:-1] time = str(timestamp.strftime('%Y-%m-%dT%H:%M:%SUTC')) orbital_slot = ds.satellite_id sector = ds.source_scene savetime = timestamp.strftime('%Y%m%d%H%M%S') ax.set_title(orbital_slot + ': ' + sector + '\n' + ch + '\n' + str(time), fontsize=15) savelocation = '/home/scarani/Desktop/output/goes/' + sector + '/' plt.savefig(savelocation + str(savetime) + '_' + str(channel) + '_' + str(sector) + '.png', bbox_inches='tight', dpi=300) plt.show() plt.close() del fig
def test_unsupported_projection(self): source = ogc.WMTSRasterSource(self.URI, self.layer_name) with mock.patch('cartopy.io.ogc_clients._URN_TO_CRS', {}): match = r'Unable to find tile matrix for projection\.' with pytest.raises(ValueError, match=match): source.validate_projection(ccrs.Miller())
plt.style.use('default') # ccrs.Miller works # NearsidePerspective da_p_values_binary = da_p_values.where(da_p_values < .05, 0) da_p_values_binary = da_p_values_binary.where(da_p_values >= .05, 1) da_p_values_binary = da_p_values_binary.where(~xr.ufuncs.isnan(da_p_values)) da_p_values_binary_ = da_p_values_binary + 1 da_positive = da_p_values_binary_.coarsen(lat=30, lon=30, boundary='trim').sum() da_positive = da_positive.where(da_positive > 0) p = da_positive.plot(col='Variable', col_wrap=2, transform=ccrs.PlateCarree(), subplot_kws={ 'projection': ccrs.Miller(), }, alpha=.7, levels=[0, 1], colors=['w', 'k'], add_colorbar=False, figsize=[10, 5]) titles = [r'a) PM$_{2.5}$', r'b) PM$_{10}$', r'c) CO', r'd) NO$_{2}$'] for idx, ax in enumerate(p.axes.flatten()): # ax.coastlines(linewidths=) da_p_values_binary.isel(Variable=idx).plot(cmap=cmr.watermelon_r, vmin=-.1, vmax=1.1, add_colorbar=False,
def test_non_native_projection(self): source = ogc.WMTSRasterSource(self.URI, self.layer_name) source.validate_projection(ccrs.Miller())
#create a new column for the sum of all inflows for each day #this creates the ring to highlight the project area lats = [29.61501, 29.64978, 29.65036, 29.61558] lons = [-94.8749, -94.8755, -94.8345, -94.8338] ring = LinearRing(list(zip(lons, lats))) #create the big loop for scenarios #for key, Key in zip(['wet'], ['Wet']): for key, Key in zip(['wet', 'dry', 'avg'], ['Wet', 'Dry', 'Average']): #create the figure and axes fig, ax1, ax2, ax3, ax4, ax5, ax6 = make_plot() #loop through the map axes for ax in [ax1, ax2, ax3]: #set the spatial bounds of the map ax.set_extent(extent, ccrs.Miller()) #add the shapefile ax.add_geometries(shp.geometries(), ccrs.Miller(), facecolor='none', edgecolor='black') #add the project area ring ax.add_geometries([ring], ccrs.Miller(), facecolor='none', edgecolor='black') fig.tight_layout() #adjust the figure to make room for labels and titles fig.subplots_adjust(left=0.07, bottom=0.07, top=0.95) #create the title fig.suptitle(r'{} Months'.format(Key),
U2M_DATA = nc.Dataset(SFC_DATA[3]) V2M_DATA = nc.Dataset(SFC_DATA[4]) # ============================================================================= # Preliminary data cleaning (Setting Time, Using Lat Lon Grids, ETC.) # ============================================================================= AIR_TIME_VAR = AIR_DATA.variables['time'] TIME_INDEX = nc.date2index(DATE, AIR_TIME_VAR) LAT = AIR_DATA['lat'][:] LON = AIR_DATA['lon'][:] SFLAT = T2M_DATA['lat'][:] SFLON = T2M_DATA['lon'][:] DX, DY = mpcalc.lat_lon_grid_spacing(LON, LAT) # ============================================================================= # Projection # ============================================================================= crs = ccrs.Miller(central_longitude=-95) def plot_background(ax): ax.set_extent([WLON, ELON, SLAT, NLAT]) ax.add_feature(cfeature.COASTLINE.with_scale('50m'), linewidth=0.5) ax.add_feature(cfeature.LAKES.with_scale('50m'), linewidth=0.5) ax.add_feature(cfeature.STATES, linewidth=0.5) ax.add_feature(cfeature.BORDERS, linewidth=0.5) return ax # ============================================================================= # FIG #1: 250: JET STREAM, GEOPOTENTIAL HEIGHT, DIVERGENCE # ============================================================================= H250 = HGT_DATA.variables['hgt'][TIME_INDEX, 8, :, :]
def to_cartopy_proj(self): """ Creates a `cartopy.crs.Projection` instance from PROJ4 parameters. Returns ------- cartopy.crs.projection Cartopy projection representing the projection of the spatial reference system. """ proj4_params = self.to_proj4_dict() proj4_name = proj4_params.get('proj') central_longitude = proj4_params.get('lon_0', 0.) central_latitude = proj4_params.get('lat_0', 0.) false_easting = proj4_params.get('x_0', 0.) false_northing = proj4_params.get('y_0', 0.) scale_factor = proj4_params.get('k', 1.) standard_parallels = (proj4_params.get('lat_1', 20.), proj4_params.get('lat_2', 50.)) if proj4_name == 'longlat': ccrs_proj = ccrs.PlateCarree(central_longitude) elif proj4_name == 'aeqd': ccrs_proj = ccrs.AzimuthalEquidistant(central_longitude, central_latitude, false_easting, false_northing) elif proj4_name == 'merc': ccrs_proj = ccrs.Mercator(central_longitude, false_easting=false_easting, false_northing=false_northing, scale_factor=scale_factor) elif proj4_name == 'eck1': ccrs_proj = ccrs.EckertI(central_longitude, false_easting, false_northing) elif proj4_name == 'eck2': ccrs_proj = ccrs.EckertII(central_longitude, false_easting, false_northing) elif proj4_name == 'eck3': ccrs_proj = ccrs.EckertIII(central_longitude, false_easting, false_northing) elif proj4_name == 'eck4': ccrs_proj = ccrs.EckertIV(central_longitude, false_easting, false_northing) elif proj4_name == 'eck5': ccrs_proj = ccrs.EckertV(central_longitude, false_easting, false_northing) elif proj4_name == 'eck6': ccrs_proj = ccrs.EckertVI(central_longitude, false_easting, false_northing) elif proj4_name == 'aea': ccrs_proj = ccrs.AlbersEqualArea(central_longitude, central_latitude, false_easting, false_northing, standard_parallels) elif proj4_name == 'eqdc': ccrs_proj = ccrs.EquidistantConic(central_longitude, central_latitude, false_easting, false_northing, standard_parallels) elif proj4_name == 'gnom': ccrs_proj = ccrs.Gnomonic(central_longitude, central_latitude) elif proj4_name == 'laea': ccrs_proj = ccrs.LambertAzimuthalEqualArea(central_longitude, central_latitude, false_easting, false_northing) elif proj4_name == 'lcc': ccrs_proj = ccrs.LambertConformal( central_longitude, central_latitude, false_easting, false_northing, standard_parallels=standard_parallels) elif proj4_name == 'mill': ccrs_proj = ccrs.Miller(central_longitude) elif proj4_name == 'moll': ccrs_proj = ccrs.Mollweide(central_longitude, false_easting=false_easting, false_northing=false_northing) elif proj4_name == 'stere': ccrs_proj = ccrs.Stereographic(central_latitude, central_longitude, false_easting, false_northing, scale_factor=scale_factor) elif proj4_name == 'ortho': ccrs_proj = ccrs.Orthographic(central_longitude, central_latitude) elif proj4_name == 'robin': ccrs_proj = ccrs.Robinson(central_longitude, false_easting=false_easting, false_northing=false_northing) elif proj4_name == 'sinus': ccrs_proj = ccrs.Sinusoidal(central_longitude, false_easting, false_northing) elif proj4_name == 'tmerc': ccrs_proj = ccrs.TransverseMercator(central_longitude, central_latitude, false_easting, false_northing, scale_factor) else: err_msg = "Projection '{}' is not supported.".format(proj4_name) raise ValueError(err_msg) return ccrs_proj