I want to to calculate NDVI time series from 2015 to 2018 using Landsat 7 and get the maximum NAVI value in this period and it's corresponding image index. That is, the horizontal and vertical axes value of this picture, I want to get the Image index in Google Earth Engine, not the time.


var landsat7_SR = ee.ImageCollection("LANDSAT/LE07/C01/T1_SR")
var ndvi_list = landsat7_SR.filterDate("1999-01-01", "2018-04-30")
               .map(function(image) { 
                 var ndvi=image.expression('float(b("B4") - b("B3")) / (b("B4") + b("B3"))').rename('ndvi');
                 return image.addBands(ndvi); 
  • 1
    Hi @Graylemon, what have you tried so far? You should post some (reproducible) code and tell us where you got stuck Nov 26 '18 at 10:28
  • thanks for your comment, I don't know how to do it, I just have a imagecollection that contain Landsat7 imgae from March 2, 2015 to May 2, 2015,I have caculate it's correspond NDVI image,but I wanna to get the every pixel's maximum NDVI value through the time.I need the NDVI peak value correspond red and NIR band value too.
    – Graylemon
    Nov 26 '18 at 12:48
  • 1
    Ok, try to improve a little your question if you want to keep it open (remove your graphic). I'll try to answer Nov 26 '18 at 13:01
  • 1
    You can show us how you invoke the collection, filter date, bounds?, computed ndvi, write some code Nov 26 '18 at 13:07
  • 1
    Good, but you have to edit the question (there is an edit options under the question) Nov 26 '18 at 13:29

To get the maximum ndvi you could use qualityMosaic function. To be able to know which image ID the pixel comes from is more complicated because as it is not a numerical property, you have to encode it some how. This is how I'd do it, but it's just one way, there could be other ways (may be easier)

l7 = ee.ImageCollection("LANDSAT/LE07/C01/T1_SR")
l7 = l7.filterDate("1999-01-01", "2018-04-30").filterBounds(geometry)
       .map(function(image) { 
          var ndvi=image.expression('float(b("B4") - b("B3")) / (b("B4") + b("B3"))').rename('ndvi');
          ndvi = ndvi.multiply(100)
          return image.addBands(ndvi); 
        // add date band
          var millis = img.date().millis()
          var days = millis.divide(1000).divide(60).divide(60).divide(24).toInt() // 86400000
          var dateband = ee.Image.constant(days).rename('date')
          return img.addBands(dateband)
        // add PATH ROW band
          var path = ee.Number(img.get('WRS_PATH')).toInt()
          var row = ee.Number(img.get('WRS_ROW')).toInt()
          var pathi = ee.Image.constant(path).rename('path')
          var rowi = ee.Image.constant(row).rename('row')
          return img.addBands(pathi).addBands(rowi)
        // cast to Int
          return img.toUint16()

// function to get the image ID from date, path and row
var get_id = function(date, path, row) {
  var d = ee.Date(ee.Number(date).multiply(86400000))
  var i = l7.filterDate(d, d.advance(1, 'day'))
            .filterMetadata('WRS_PATH', 'equals', path)
            .filterMetadata('WRS_ROW', 'equals', row)

  return ee.Image(i.first()).id()

// apply qualityMosaic
var mosaic = l7.qualityMosaic('ndvi')
Map.addLayer(mosaic, {bands:['ndvi'], min:0, max:80})

// function to be able to print the image ID when clicking on the Map over the image
var click = function(coords) {
  var lon = coords.lon
  var lat = coords.lat
  var p = ee.Geometry.Point([lon, lat])
  var values = mosaic.reduceRegion(ee.Reducer.first(), p, 30)
  var date = get_id(values.get('date'), values.get('path'), values.get('row'))
  print('ID on point', p, date)

I have given my suggestion regarding the "index problem" at this other question!

The problem can be solved basically in 3 steps (after you applied a cloudmask to Landsat data and attributed the NDVI band):

  1. Computing the Maximum NDVI value using .max() on your imageCollection
  2. Computing an image containing at each pixel the index of the max-value:
    • by transforming the imageCollection to a list,
      • mapping through it and applying .indexOf() and set the index as a property,
    • then transforming it back to an imageCollection,
      • mapping through it and setting the pixel value equal to the index where the NDVI band values correspond to the maximal NDVI values you computed in step 1, using .where() and .eq()
  3. You can then actually compute a mosaic showing the other bands from the original collection that are responsible for the maximal NDVI value of your series:
    • by mapping through a sequence of indexes calling the original image by the index created in step 2, but cutting each image using .updateMask() to the extent its index was responsible for the maximal NDVI value.

In the end you can use the inspector to check out at any point what band values caused which maximal NDVI at which index.

See the full code at link here: https://code.earthengine.google.com/e5537a444207f0e746b39910f62b23bd

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.