[gdal-dev] reading arbitrary raster into rgb

Even Rouault even.rouault at spatialys.com
Sat Oct 18 02:10:08 PDT 2014


Le samedi 18 octobre 2014 02:16:19, Michael Katz - NOAA Affiliate a écrit :
> Even, thanks for the reply and for pointing out the dataset version of
> RasterIO().
> 
> But I still don't understand a few things. The main one is that you say:
> >>> Regarding color space conversions, GDAL generally doesn't do anything
> 
> if the
> 
> >>> underlying library doesn't do it. But in the case of JPEG or JPEG2000,
> 
> they do
> 
> >>> YCbCr -> RGB conversion transparently. CMYK is quite esoteric, but I
> 
> think
> 
> >>> JPEG will translate it to RGB.
> 
> I don't understand what would direct the output to be RGB.
> 
> I understand nPixelSpace, nLineSpace, and nBandSpace to be purely a matter
> of how you want the data laid out in the output buffer, but nothing about
> what data (type, color space) gets written. So by setting nPixelSpace=3 and
> nBandSpace=1 as you suggest, I understand that you get sequential RGB
> triplets, but that in itself doesn't direct RasterIO() to output RGB,
> right? My understanding is that the only thing that controls the output
> type is eBuffType, but setting it to GDT_Byte doesn't mean "rgb", it just
> means "byte". So if the input file had HSL, those bytes would be HSL.

Yes. But GDAL doesn't do everything itself. When reading a JPEG file it uses 
libjpeg, and it configures libjpeg to do YCbCr->RGB colorspace conversion 
transparently. So from GDAL point of view, and its users, the bands will be 
R,G,B and not Y,Cb,Cr.

> And
> if the input file had RGB or HSL using floats, those byte values would be
> pinned (i.e., destroyed) versions of the floating point values.
> 
> So I don't see where the "transparent" color space conversion comes in.

See above explanation. It is driver/underlying library specific logic 

> 
> Overall, it's still sounding to me like if I want a function to read an
> arbitrary file (tiff, JPEG200) into an RGB byte buffer, I need to handle
> quite a bit of logic myself. I have to:
> 
> (a) Look at the number of bands and step through the bands one by one and
> deduce what color space is being used. For instance, I might see that there
> are four bands and the first band is *GCI_RedBand* , but that does not
> guarantee that the next two bands are green and blue (although they
> probably are).
> 
> (b) Allocate a buffer A to read the file in using its existing color space
> and data type.
> 
> (c) Allocate a buffer B in RGB for the given number of pixels.
> 
> (d) For all the incoming color spaces and data types I choose to support
> (my understanding is that the possibilities are RBG, HSL, CMYK, YCbCr), for
> each pixel, grab data from the appropriate channels (in whatever order
> those channels happen to be laid out) and do both a color space conversion
> and a data type conversion from the pixel in A to the pixel in B.
> 
> (e) Possibly deal with other things like the file having a color table (not
> sure if JPEG200 or tiff can have color tables?), which would modify my code
> for (d).

Both can have, although paletted JPEG2000 is quite uncommon (have only seen 
paletted JPEG2000 in compliance test suite). Paletted TIFF is not so uncommon.

> 
> Does that sound correct to you? Do you know of someone who has that code,
> even if it's not part of GDAL itself?

Your theory is correct, but in practice you will hardly find datasets in those 
exotic colorspaces (well at least for most people I guess).
The GeoTIFF driver also uses the TIFFReadRGBAStrip()/TIFFReadRGBATile() API of 
libtiff to expose RGBA bands for some of thoese exotic colorspaces

The only thing you would have to deal yourself is color table expansion.
gdal_translate -expand RGB does the later. It uses VRT internally to do that. 
See AddComplexSource() in http://www.gdal.org/classVRTSourcedRasterBand.html. 
Color table expansion is done if you specified nColorTableComponent = 1, 2 or 
3.

> 
> It still seems to me natural that GDAL would provide an overarching
> function that would do all of this, since there are a lot of cases to
> consider and everybody wants basically the same thing.
> 
> I understand the point about people possibly wanting to map values in a
> non-linear way or whatever, but it seems like that could be handled with a
> default behavior with the option for a user callback function to customize.

Regarding user callback function, you could actually use VRT derived bands to 
do that. See the "Using Derived Bands" paragraph of 
http://www.gdal.org/gdal_vrttut.html

I can imagine there could be some helper API that would use RasterIO() 
internally and would expose to the user a RGBA dataset. Someone has to do it.. 
:-)

Even

-- 
Spatialys - Geospatial professional services
http://www.spatialys.com


More information about the gdal-dev mailing list