Skip to content

Instantly share code, notes, and snippets.

@barronh
Last active June 9, 2026 14:47
Show Gist options
  • Select an option

  • Save barronh/f8b646307d4a116c9a093d73769a1399 to your computer and use it in GitHub Desktop.

Select an option

Save barronh/f8b646307d4a116c9a093d73769a1399 to your computer and use it in GitHub Desktop.
NASA GIBS Colormaps for Python
def xmlcmap2cmap(xmlcmap):
import numpy as np
import matplotlib.colors as mc
inf = np.inf
nan = np.nan
for elem in xmlcmap:
if elem.tag == 'Entries':
los = []
his = []
rgbs = []
exclusivestart = 0
for cme in elem:
rgbs.append(eval(cme.attrib['rgb']))
vrange = cme.attrib.get('value', '[nan,nan)').lower()
if not ',' in vrange:
if vrange.startswith('[') and vrange.endswith(']'):
bnds = eval(vrange)
if isinstance(bnds[0], int):
bnds.append(bnds[0] + 1e-20)
elif vrange.startswith('[') and vrange.endswith(')'):
bnds = eval(vrange[:-1] + ']')
if isinstance(bnds[0], int):
bnds.append(bnds[0] + 1e-20)
else:
title = xmlcmap.attrib.get('title', 'unknown')
msg = f'Not sure what to do with {vrange} on {title}'
raise ValueError(msg)
elif vrange.startswith('[') and vrange.endswith(')'):
bnds = eval(vrange[:-1] + ']')
elif vrange.startswith('(') and vrange.endswith(')'):
bnds = eval('[' + vrange[1:-1] + ']')
exclusivestart += 1
los.append(bnds[0])
his.append(bnds[1])
edges = np.append(los, his[-1])
if np.isneginf(los[0]):
edges[0] = 2 * edges[1] - edges[2]
if np.isneginf(his[-1]):
edges[-1] = 2 * edges[-2] - edges[-3]
cmap, norm = mc.from_levels_and_colors(edges, np.array(rgbs) / 255)
if np.isneginf(los[0]):
cmap.set_under(cmap(0))
if np.isposinf(his[-1]):
cmap.set_over(cmap(1))
if exclusivestart > 0:
print('WARN:: Inclusive left, but BoundaryNorm is exclusive left')
return cmap, norm
def getnasacmaps(key='', nodata=False):
import xml.etree.ElementTree as ET
import requests
import re
rurl = 'https://gibs.earthdata.nasa.gov/colormaps/v1.3'
r = requests.get(rurl)
rtext = r.text
hrr = re.compile('href="([^"]+?\\.xml)"')
paths = hrr.findall(rtext)
mycmaps = {}
for path in paths:
if path.startswith(key):
pkey = path[:-4]
print(path)
cr = requests.get(rurl + '/' + path)
ctext = cr.text
nasacmaps = ET.fromstring(ctext)
for nasacmap in nasacmaps:
title = nasacmap.attrib.get('title', 'unknown')
if title.lower() == 'no data' or nodata:
continue
try:
cmap, norm = xmlcmap2cmap(nasacmap)
mycmaps[pkey + ':' + title] = {'cmap': cmap, 'norm': norm}
except Exception as e:
print('ERROR::', e)
return mycmaps
if __name__ == '__main__':
import numpy as np
import matplotlib.pyplot as plt
exmaps = getnasacmaps('ASTER')
plt.pcolormesh(np.array([[1, 400, 800], [1200, 4000, 8000]]), **exmaps['ASTER_GDEM_Color_Index:Elevation'])
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment