3

Through a combination of non-matlab/non-native tools (GDAL) as well as native tools (geoimread) I can ingest Sentinel-2A data either a indiviual bands or as an RGB image having employed gdal merge. I'm stuck at a point where using

imshow(I, [])

Produces a black image, with apparently no signal. The range of intensity values in the image are 271 - 4349. I know that there is a good signal in the image because when I do:

bit_depth = 2^15;
I = swapbytes(I);
[I_indexed, color_map] = rgb2ind(I, bit_depth);
I_double = im2double(I_indexed, 'indexed');
ax1 = figure;
colormap(ax1, color_map);
image(I_double)

i.e. index the image, collect a colormap, set the colormap and then call the image function, I get a likeness of the region I'm exploring (albeit very strangely colored)

I'm currently considering whether I should try:

  1. Find a low-level description of Sentinel-2A data, implement the scaling/correction

  2. Use a toolbox, possibly this one.

  3. Possibly adjust ouput settings in one of the earlier steps involving GDAL Comments or suggestions are greatly appreciated.

A basic scaling scheme is:

% convert image to double
I_double = im2double(I);

% scaling
max_intensity = max(I_double(:));
min_intensity = min(I_double(:));
range_intensity = max_intensity - min_intensity;
I_scaled = 2^16.*((I_double - min_intensity) ./ range_intensity);

% display
imshow(uint16(I_scaled))

noting the importance of casting to uint16 from double for imshow.

John Chris
  • 153
  • 5

1 Answers1

1

A couple points...

  • You mention that I is an RGB image (i.e. N-by-M-by-3 data). If this is the case, the [] argument to imshow will have no effect. That only applies automatic scaling of the display for grayscale images.

  • Given the range of intensity values you list (271 to 4349), I'm guessing you are dealing with a uint16 data type. Since this data type has a maximum value of 65535, your image data only covers about the lower 16th of this range. This is why your image looks practically black. It also explains why you can see the signal with your given code: you apply swapbytes to I before displaying it with image, which in this case will shift values into the higher intensity ranges (e.g. swapbytes(uint16(4349)) gives a value of 64784).

In order to better visualize your data, you'll need to scale it. As a simple test, you'll probably be able to see something appear by just scaling it by 8 (to cover a little more than half of your dynamic range):

imshow(8.*I);
gnovice
  • 125,304
  • 15
  • 256
  • 359
  • Thanks, @gnovice. I have updated my question to include a basic scaling scheme. You've helped me better understand what my issue is. The imagery/signal is clear but a little bit dark. This thread (https://gis.stackexchange.com/questions/233826/get-rgb-images-from-sentinel-2-using-gdal) alludes to a "cumulative count cut" and adjusting brightness, contrast and saturation. Identifying resources to achieve these adjustments, I believe, is my next question. – John Chris May 31 '19 at 01:00