Hi,
I got a tiff image already converted to unsigned short*.
How can I display the image from the unsigned short* in QT?
I am using QT4.1.
Thank you....
Hi,
I got a tiff image already converted to unsigned short*.
How can I display the image from the unsigned short* in QT?
I am using QT4.1.
Thank you....
Why not unsigned char*?Originally Posted by spawnwj
What does the bitmap contain? Only the pixell data? If so, then you can use QImage::bits() to access QImage pixell storage and copy the data there.How can I display the image from the unsigned short* in QT?
The image comes in unsigned short*. I can't do anything about that.Originally Posted by wysota
I think if it is in unsigned char* we can load it directly into QPixel or QImage right?
Hm... I have to check if the bitmap only contain pixel data.
Any hints on how to do this?
I am new to image processing so I do not really know how to proceed from here.
Thanks
Where did you get those ushort* from? Ask the author what they contain But it should still be uchar*, because ushort can be 16 bits long and uchar is always 8bits.
Hi....Originally Posted by wysota
The images I am getting is 16 bit greyscale image converted from tiff. It is more for image processing. But I just need to display it in QT. Can anyone tell me how I can go about doing it?
The images comes in ushort*. Therefore I do not know how I can display it.
Thanks
You should convert a 16bit raster to the 8bit raster. After that you will be able to show this image through Qt's classes.
Here is a simple function for converting 16 to 8 bit.
Qt Code:
// data - the souce 16bit raster // dest - the destination 8bit raster // len - raster length (width * height) template<typename T> bool conv16to8bit(const T * const data, unsigned char * const dest, unsigned len) { if ( !data || !dest || !len ) return false; size_t type_size = sizeof(T); if ( type_size != 2 ) return false; bool isSigned = ( typeid(T) == typeid(signed short) ); T minValue = ( isSigned ? static_cast<T>(::pow(2, type_size * 8 - 1)/2)-1 : static_cast<T>(::pow(2, type_size * 8 - 1)) ); T maxValue = ( isSigned ? static_cast<T>(::pow(2, type_size * 8 - 1)/2) * (-1) : 0 ); for (const T * pix = data; pix < data+len; pix++) { if ( *pix < minValue ) minValue = *pix; if ( *pix > maxValue ) maxValue = *pix; } const char VBLACK = 16; float K = (4096.f * ( 256 - VBLACK )) / ( maxValue - minValue ); float B = minValue * K / 4096.f - VBLACK; unsigned char * dst = dest; for (const T * pix = data; pix < data+len; pix++) { int c = static_cast<int>( 0.5f + (::abs(*pix) * K / 4096 - B)); if ( c < 0 ) c = 0; if ( c > 255 ) c = 255; *dst++ = static_cast<unsigned char>(c); } return true; };To copy to clipboard, switch view to plain text mode
void CMMMGui::setImageInGUI(ushort* image, int page)
{
uchar* finalImage = new uchar[300 * 300];
_conv16to8bit(image, finalImage, 90000);
QImage img = QImage(finalImage,300,300,QImage::Format_ARGB32);
QPixmap pix = QPixmap(300,300);
ui.label_Photo->setPixmap( QPixmap::fromImage( img ) );
}
Thanks for the code.
I have tried to call your function to convert it to 8bit. The image is looking slightly better. But still not the same image yet
Anything I do wrong here?
I think there is something wrong with the format define in the QImage. I cant seem to get a right one for it.
QImage img = QImage(finalImage,300,300,QImage::Format_ARGB32);
Thanks
Originally Posted by Mad Max
Try to set to zero a value of the variable VBLACK.
I have updated the code as shown below...
I can see the full image now but it is rotated anticlockwise 90 degree....
Any idea why?
Thanks
uchar* finalImage = new uchar[300*300];
_conv16to8bit(image, finalImage, 90000);
QImage img(300, 300,QImage::Format_Indexed8);
img.setNumColors(256);
for(int i = 0; i <= 255; i++)
{
int myColor = qRgb(i, i, i);
img.setColor(i, myColor);
}
for(int i = 0; i<300; i++)
for(int j = 0; j<300; ++j)
img.setPixel(i, j, finalImage[(i*300)+j]);
ui.label_Photo->setPixmap( QPixmap::fromImage( img ) );
Hi the image looks fine now. I just swap i and j at setPixel.Originally Posted by spawnwj
So far so good.
Thanks for all the help
I'm surprised with this behaviour. Do you sure that it happened because of the function of convert?Originally Posted by spawnwj
I want to explain a bit. This function was made only for display of images, not for processing. This algorithm does scale 16bit values to the 8bit range and considers min and max values of pixels at the same time. If you will processing 8bit image and you need to keep the source image as far as possible you should change the algorithm of convert. It should be such as:
Qt Code:
template<typename T> bool conv16to8bit(const T * const data, unsigned char * const dest, unsigned len) { if ( !data || !dest || !len ) return false; size_t type_size = sizeof(T); if ( type_size != 2 ) return false; bool isSigned = ( typeid(T) == typeid(signed short) ); T maxValue = ( isSigned ? static_cast<T>(::pow(2, type_size * 8 - 1)/2)-1 : static_cast<T>(::pow(2, type_size * 8 - 1)) ); unsigned char * dst = dest; for (const T * pix = data; pix < data+len; pix++) { int c = static_cast<int>( 0.5f + (::abs(*pix) / maxValue * 255)); if ( c < 0 ) c = 0; if ( c > 255 ) c = 255; *dst++ = static_cast<unsigned char>(c); } return true; };To copy to clipboard, switch view to plain text mode
I didn't check this code. May be it has a couple errors.
I have further reduce the code to the one below.
It looks ok without the rotation issue.
However I got one question...
If the source is 16 bit, I got a full image with the right size.
If the source is 8bit, I got a image that is 1/4 of the size and repeat 2 times.
For example... The actual full image size is defined below.
1 2
3 4
It will have 2 repeating image on 1 and 2 while 3 and 4 is empty.
Is this normal?
uchar* finalImage = new uchar[imageSize.width()*imageSize.height()];
_conv16to8bit(imageData, finalImage, imageSize.width()*imageSize.height());
QImage img(finalImage, imageSize.width(), imageSize.height(),QImage::Format_Indexed8);
img.setNumColors(256);
for(int i = 0; i <= 255; i++)
{
int myColor = qRgb(i, i, i);
img.setColor(i, myColor);
}
Originally Posted by Mad Max
Yes, I think this is normal behaviour for this function. I never used it in such way. It seems you've too much oversimplified my function. In original it checks the dimension of source type. Just don't use this function for 8bit images.Originally Posted by spawnwj
you might want to check out TiffIO as well.
Thanks... I got that in my system.Originally Posted by jrideout
But my source is already converted to ushort*. I can only start working for there.
Bookmarks