Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does MATLABs "imwrite" scale 12-bit images and how to circumvent this?

I have an image given as an N x M - matrix with 12-bit data and I want to use imwrite to save the image as a .pgm file.

Why does MATLAB scale the image to 16bit? How can I circumvent this?

Using the 'MaxValue' argument also seems to alter the image, as it can't be displayed properly afterwards e.g. in IrfanView.

like image 720
jolo Avatar asked Dec 15 '14 15:12

jolo


1 Answers

The MaxValue parameter is a little counter intuitive. It does specify to write the PGM tagged with a max value of a certain depth (e.g. 12-bit here), but it also tells iwwrite to rescale the data. The rescaling happens in writepnm>remap_pixel_values:

function newdata = remap_pixel_values(data, maxval)
%REMAP_PIXEL_VALUES Remap pixel values in array of pixel values.
%
%   NEWDATA = REMAP_PIXEL_VALUES(DATA, MAXVAL) remaps the pixel values in
%   DATA as follows
%
%   Class of DATA   Input                    Output
%   -------------   -----                    ------
%   uint8           The set {0,1,...,255}    The set {0,1,...,maxval}
%   uint16          The set {0,1,...,65535}  The set {0,1,...,maxval}
%   double          The interval [0,1]       The set {0,1,...,maxval}

So with uint16 data, it will rescale the data by applying a scale of 65535/maxval via the bit shift bitshift(data,-4);. You don't want it to rescale the data, but you also want it to write the file as 12-bit (this happens in writepnm>write_raw_data. The workaround is to apply the opposite scale before calling imwrite:

Iscaled = uint16(double(I)*(2^16-1)/(2^12-1))
imwrite(Iscaled,'test.pgm','MaxValue',2^12-1)

Note that you could use double values scaled between [0,1] too, according to the table in the above code comments.

For reading 12-bit PGM/PPM, see here.

like image 58
chappjc Avatar answered Oct 21 '22 07:10

chappjc