..

mapping colorado's high country, from the cloud

I recently had an idea to make a map of potential backcountry skiing areas in Colorado, based solely on landscape position. Because of the large spatial extent I dusted off Google Earth Engine, which is perfectly suited for these types of projects. Earth Engine has an extensive (and recently rebuilt) library of satellite and aerial datasets. The earth engine code editor itself is a Javascript API for Google’s vast cloud-based data library. Academics—or anyone with a fake mustache and a .edu email address—can get free access to the API. It’s also available as a Python API, but that one doesn’t currently support outputting maps. Google does put limits on the amount of resources and bandwidth you can consume, but these are reasonable given how easy it is to access files that would weigh in at the terabyte scale should you try to download directly from the provider.

var DEM = ee.Image('USGS/NED');
var elevation = DEM.select('elevation');
var elevationVis = {
  min: 0.0,
  max: 4000.0,
  gamma: 1.6,
};

The data for this project comes from the USGS National Elevation Dataset (NED), which is one component of the new 3D Elevation Program (3DEP). The spatial resolution is 1/3 arc-second, which is approximately 10m spacing. This dataset is a composite of several data sources, including lidar point clouds and satellite-based interferometric synthetic aperature radar. To stay within computational limits I had to downsample this resolution for image reductions involving the whole state.

// Load the TIGER2016 census date from a feature collection.
var featureCollection = ee.FeatureCollection('ft:1fRY18cjsHzDgGiJiS2nnpUU3v9JPDc2HNaR7Xk8');
// Filter the collection.
var filteredFC = featureCollection.filter(ee.Filter.eq('Name', 'Colorado'));
// Display the collection.
Map.addLayer(filteredFC, {}, 'Colorado');

Boundary shapefiles from the 2016 US Census data product.

// Mask land below 10,000 feet
var DEM_Masked = DEM.updateMask(DEM.gte(3048));
Map.addLayer(DEM_Masked, vizParams, 'DEM_Above_200m');
// Mask land below 10,500 feet
var DEM_Masked_Warming = DEM.updateMask(DEM.gte(3200.4));

// Create slope angle product using the SRTM DEM and EE’s ee.Terrain
var elevation = DEM_Masked.select('elevation');
var slope = ee.Terrain.slope(elevation);
Map.addLayer(slope, {min: 15, max: 90}, 'slope');

// Mask land below 10,000 and less thank 15 degree slope angle
var Slope_Masked = slope.updateMask(slope.gte(15));
Map.addLayer(Slope_Masked, vizParams, 'Slope and Elevation Mask');
print(Slope_Masked);

Visualization of skiable terrain is based on two parameters used to mask the DEM: elevation and slope angle.

var census = ee.FeatureCollection('TIGER/2016/Counties');

// Filter the collection for Boulder County.
var bouldercounty = census.filter(ee.Filter.eq('NAME', 'Boulder'));
print(bouldercounty);

// Display the collection.
Map.addLayer(bouldercounty, {}, 'bouder_county');

// Filter the collection.
var sanjuancounty = census.filter(ee.Filter.eq('NAME', 'Ouray'));
print(sanjuancounty);

// Display the collection.
Map.addLayer(sanjuancounty, {}, 'summit_county');

var histogram_slope_sanjuan = ui.Chart.image.histogram({
  image: Slope_Masked,
  region: sanjuancounty,
  scale: 30,
});

I exported the final image as a GeoTIFF to a Drive folder using the Export.image.toDrive function. I then opened the file in Illustrator and changed the color to match the image I wanted. I had originally intended to use Livepaint and brushes to create a sort of pop-art abstraction of the original image, but the detail and dendrite-like shape of the terrain looked best unaltered.

Image with caption The San Juan Mountains of southwestern Colorado.

The final image depicts the scale and distribution of Colorado’s rugged high mountain terrain. It also shows where much of the West’s water resources are stored. This snowpack is threatened by climate change. I was curious to see what how the distribution would change if the seasonal snowpack was bumped up in elevation. As a skier in the front range, I often think of 10,000 feet as the bottom limit of skiable terrain—much lower and the snow isn’t deep enough to ski safely. What happens if this line moves up to 10,500 feet?

var DEM_Masked = DEM.updateMask(DEM.gte(3048));
var Masked_Area = DEM_Masked.reduceRegion({
  reducer: ee.Reducer.count(),
  geometry: filteredFC.geometry(),
  scale: 30,
  maxPixels: 1e13
});

print(Masked_Area);
// Create a warming scenario
var DEM_Masked_Warming = DEM.updateMask(DEM.gte(3200.4));
var meanDictionary_Warming = DEM_Masked_Warming.reduceRegion({
  reducer: ee.Reducer.count(),
  geometry: filteredFC.geometry(),
  scale: 30,
  maxPixels: 1e13
});

print(meanDictionary_Warming);

According to this dataset, Colorado has 37,311 km2 of land above 10,000 feet, and 26,009 km2 above 10,500 feet. By moving the start of my (arbitrary) seasonal snowpack just 500 feet higher, we lose 30% of the available landscape for holding snow. As is shown in the above plot, there is simply less terrain at higher elevations. I can imagine the mountain snowpack as a pyramid. The majority of snow exists at the base, where there is the most terrain. By this line of reasoning, the majority of snow water equivalent (SWE) exists in this niche of temperature and terrain. It follows that warming climate effects land with the highest proportion of water storage first. This hypothesis presupposes that SWE is not correlated with elevation, that is—above the freezing line—there is no relationship between elevation and SWE. Snow hydrologists know that snowpack distribution has many controls including wind, aspect, and even dust loading. Additionally, different mountain ranges may have a different distribution of landscape elevation. Ranges with marine climates and more northern latitudes hold seasonal snow at much lower elevations than Colorado. This is just part of the story of mountain snow. In any case, it’s important to note that there isn’t enough reservoir capacity in Colorado for our needs; we rely on cold temperatures to safe guard our water.

Image with caption White River National Forest, North of I-70.

Anyone who as spent time walking around in Colorado’s backcountry will take notice of a major flaw in this projection. Colorado high-altitude forests are notoriously composed of smaller, tighty grouped trees. Skiing this terrain is challenging or impossible. Given the wide variability of treeline, much of this terrain is likely to be impossibly treed. The most obvious solution would be to add an NDVI mask, excluding pixels that exceed some threshold of greenness. Let me know if you get around to this, I’ll update the post if I do. Here’s a link to the full size image.