Working with Images

Visualizing Images and Image Bands

Now that you're ready to begin writing Earth Engine JavaScript, start by copying the following code into the Code Editor:

// Instantiate an image with the Image constructor.
var image = ee.Image('CGIAR/SRTM90_V4');

// Zoom to a location.
Map.setCenter(-112.8598, 36.2841, 9); // Center on the Grand Canyon.

// Display the image on the map.
Map.addLayer(image);

Click the Run button at the top of the Code Editor and observe that a very gray image appears on the map. Don't worry, you'll make it look better soon.

Image Constructor

The first new thing in this example is the image constructor ee.Image(). The argument provided to the constructor is the string ID of an image in the Earth Engine data catalog. To discover an image ID, search in the Earth Engine data catalog using the search tool at the top of the Code Editor. For example, type 'elevation' into the search field and note that a list of rasters is returned. Click the 'SRTM Digital Elevation Data Version 4' entry to see more information about that dataset.

Configuring the Map

The second new part of this example is the Map.setCenter() call. This method on the Map object, which represents the Map display in the Code Editor, centers the map at the given longitude, latitude (in decimal degrees) and zoom level where 1 is zoomed out so that the map shows the entire Earth's surface. Larger numbers zoom in from there. Discover all the methods on the Map object by checking the Map section in the Docs tab on the left side of the Code Editor.

Adding a layer to the Map

The last line in the example says: use the Map object's addLayer() method to add an image to the map display in the Code Editor.

Customizing layer visualization

To change the way the data are stretched, you can provide another parameter to the Map.addLayer() call. Specifically, the second parameter, visParams, lets you specify the minimum and maximum values to display. To discover what values to use, activate the Inspector tab and click around on the map to get an idea of the range of pixel values. Alternatively, use the Layer manager to interactively stretch the data, then observe the minimum and maximum corresponding to percentiles or standard deviation stretches. Suppose that through such experimentation, you determine that the data should be stretched to [0, 3000]. To display the image using this range, use:

Map.addLayer(image, {min: 0, max: 3000}, 'custom visualization');

Note that the visParams parameter is an object, with properties specifying the min and the max, and the third parameter for Map.addLayer() is the name of the layer that is displayed in the Layer manager.

Figure 1. Elevation image as grayscale, stretched to [0, 3000].

To display a single band using a color palette, add a palette property to the visParams object:

var vis = {min: 0, max: 3000, palette: ['blue', 'green', 'red']};
Map.addLayer(image, vis, 'custom palette');

The result should look something like Figure 2.

Figure 2. Elevation image as a color ramp from blue to red, stretched to [0, 3000].

Apply a computation to an image

Now that you know how to load and display an image, it's time to apply a computation to it. For example, you can compute the slope of terrain, by passing the SRTM elevation image to the slope method of the ee.Terrain package.

// Load the SRTM image.
var srtm = ee.Image('CGIAR/SRTM90_V4');

// Apply an algorithm to an image.
var slope = ee.Terrain.slope(srtm);

// Display the result.
Map.setCenter(-112.8598, 36.2841, 9); // Center on the Grand Canyon.
Map.addLayer(slope, {min: 0, max :60}, 'slope');

Note that in the code ee.Terrain.slope(srtm), the srtm image is provided as an argument to the slope algorithm. The result should look something like Figure 3.

Figure 3. Slope image.

Image statistics

Another useful class of operations on images involves computing pixel statistics in image regions, or raster-vector overlays. To compute statistics in Earth Engine, use a reducer as represented by classes in the ee.Reducerpackage. For example, suppose you're interested in the mean of elevation in some region. You can define a region by drawing a polygon using the geometry drawing tools. To interactively draw a region, get the polygon drawing tool (), then digitize a polygon over your area of interest and click Exit when you're done. Note that the resultantee.Geometry object is automatically named geometry and added as an import at the top of your script. Rename that variable to 'polygon' by clicking on the variable name in the imports and typing the new name.

Next, get the mean pixel value in the polygon using the following code:

// Compute the mean elevation in the polygon.
var meanDict = srtm.reduceRegion({
  reducer: ee.Reducer.mean(),
  geometry: polygon,
  scale: 90
});

// Get the mean from the dictionary and print it.
var mean = meanDict.get('elevation');
print('Mean elevation', mean);

There a several things to note here. First, observe that reduceRegion() is a method available for Image objects (learn more about reducing regions here). Second, the method arguments are provided in a JavaScript object that is passed as a single argument. (Specifically, the keys of the object are the names of the method parameters. The values are the arguments to the method). Third, the reducer parameter specifies the type of statistic to compute and the geometry parameter specifies the region in which to compute the statistic. The scale parameter is the pixel size in meters to use. To avoid ambiguity, you should always specify scale when doing reductions as Earth Engine may not be able to automatically determine the appropriate scale from the inputs. (Learn more about scale in Earth Engine).

Lastly, the return value of reduceRegion() is a dictionary in which keys are band names and values are the pixel statistics for the bands. The get() method on a dictionary returns the value corresponding to the key provided as an argument. In this case, the srtm image has one band, 'elevation', so the example code gets that statistic from the dictionary and prints it.

When you run this code, if you get an error that looks like:

ComputedObject (Error)
  Image.reduceRegion: Too many pixels in the region. Found 527001545, but only 10000000 allowed.

Fear not! There are several things you can do to resolve the error. The reduceRegion() method has a check to make sure you consider whether you really want to include so many pixels in your computation. This is intended to prevent you from accidentally doing something silly, like trying compute the mean of every one-meter pixel in the world (don't do that). To resolve the error, either set the bestEffort parameter to true by adding bestEffort: true to the dictionary of parameters, or set the maxPixels parameter to a value higher than the default of 10 million pixels, or both. If bestEffort is true, Earth Engine will automatically recompute the scale such that maxPixels is not exceeded.

Head here if you want to know more about scale in Earth Engine.


Digression: Images in Earth Engine

Images in Earth Engine (see this page for more details) are made up of one or more bands. Each band in an image has its own name, pixel values, pixel resolution, and projection. As you'll soon discover, the SRTM image has one band: 'elevation'.

When you add an image to a map using Map.addLayer(), Earth Engine needs to determine how to map the values in the image band(s) to colors on the display. If a single-band image is added to a map, by default Earth Engine displays the band in grayscale, where the minimum value is assigned to black, and the maximum value is assigned to white. If you don't specify what the minimum and maximum should be, Earth Engine will use default values. For example, the image you just added to the map is displayed as a grayscale image stretched to the full range of the data, or signed 16-bit integer [-32768, 32767]. (float bands are stretched to [0, 1] and byte bands are stretched to [0, 255] by default).

You can discover the data type of the image by printing it and inspecting the image object in the Console tab. For example, paste the following after the previous code:

print('SRTM image', image);

When you click run, note that an object appears in the console. To investigate the object properties, expand it by clicking on the zippy () to the left of the object or property. Expand the image object, the 'bands' property, the 'elevation' band at index '0' and the 'data_type' property of the 'elevation' band to discover that it is a signed int16 data type.