コード例 #1
0
ファイル: ximahist.cpp プロジェクト: JimLiu/asptools
////////////////////////////////////////////////////////////////////////////////
// HistogramLog function by <dave> : dave(at)posortho(dot)com
bool CxImage::HistogramLog()
{
	if (!pDib) return false;

	//q(i,j) = 255/log(1 + |high|) * log(1 + |p(i,j)|);
    int x, y, i;
	RGBQUAD color;
	RGBQUAD	yuvClr;

	unsigned int YVal, high = 1;

    // Find Highest Luminance Value in the Image
	if( head.biClrUsed == 0 ){ // No Palette
		for(y=0; y < head.biHeight; y++){
			info.nProgress = (long)(50*y/head.biHeight);
			for(x=0; x < head.biWidth; x++){
				color = GetPixelColor( x, y );
				YVal = (unsigned int)RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
				if (YVal > high ) high = YVal;
			}
		}
	} else { // Palette
		for(i = 0; i < (int)head.biClrUsed; i++){
			color = GetPaletteColor((BYTE)i);
			YVal = (unsigned int)RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
			if (YVal > high ) high = YVal;
		}
	}

	// Logarithm Operator
	double k = 255.0 / ::log( 1.0 + (double)high );
	if( head.biClrUsed == 0 ){
		for( y = 0; y < head.biHeight; y++ ){
			info.nProgress = (long)(50+50*y/head.biHeight);
			for( x = 0; x < head.biWidth; x++ ){

				color = GetPixelColor( x, y );
				yuvClr = RGBtoYUV( color );
                
				yuvClr.rgbRed = (BYTE)(k * ::log( 1.0 + (double)yuvClr.rgbRed ) );

				color = YUVtoRGB( yuvClr );
				SetPixelColor( x, y, color );
			}
		}
	} else {
		for(i = 0; i < (int)head.biClrUsed; i++){

			color = GetPaletteColor( (BYTE)i );
			yuvClr = RGBtoYUV( color );

            yuvClr.rgbRed = (BYTE)(k * ::log( 1.0 + (double)yuvClr.rgbRed ) );
			
			color = YUVtoRGB( yuvClr );
 			SetPaletteColor( (BYTE)i, color );
		}
	}
 
	return true;
}
コード例 #2
0
ファイル: ximalpha.cpp プロジェクト: BeaconDev/xray-16
/**
 * Resets the alpha palette 
 */
void CxImage::AlphaPaletteClear()
{
	RGBQUAD c;
	for(WORD ip=0; ip<head.biClrUsed;ip++){
		c=GetPaletteColor((BYTE)ip);
		c.rgbReserved=0;
		SetPaletteColor((BYTE)ip,c);
	}
}
コード例 #3
0
/**
 * Resets the alpha palette 
 */
void CxImage::AlphaPaletteClear()
{
	RGBQUAD c;
	for(uint16_t ip=0; ip<head.biClrUsed;ip++){
		c=GetPaletteColor((uint8_t)ip);
		c.rgbReserved=0;
		SetPaletteColor((uint8_t)ip,c);
	}
}
コード例 #4
0
ファイル: ximahist.cpp プロジェクト: Bitlsoft/Imagenius_SDK
////////////////////////////////////////////////////////////////////////////////
// HistogramRoot function by <dave> : dave(at)posortho(dot)com
bool CxImage::HistogramRoot()
{
	
	

	if (!pDib) return false;
	//q(i,j) = sqrt(|p(i,j)|);

    int x, y, i;
	RGBQUAD color;
	RGBQUAD	 yuvClr;
	double	dtmp;
	unsigned int YVal, high = 1;

     // Find Highest Luminance Value in the Image
	if( head.biClrUsed == 0 ){ // No Palette
		for(y=0; y < head.biHeight; y++){
			info.nProgress = (long)(50*y/head.biHeight);
			if (info.nEscape) break;
			for(x=0; x < head.biWidth; x++){
				color = BlindGetPixelColor( x, y );
				YVal = (unsigned int)RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
				if (YVal > high ) high = YVal;
			}
		}
	} else { // Palette
		for(i = 0; i < (int)head.biClrUsed; i++){
			color = GetPaletteColor((BYTE)i);
			YVal = (unsigned int)RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
			if (YVal > high ) high = YVal;
		}
	}

	// Root Operator
	double k = 128.0 / ::log( 1.0 + (double)high );
	if( head.biClrUsed == 0 ){
		for( y = 0; y < head.biHeight; y++ ){
			info.nProgress = (long)(50+50*y/head.biHeight);
			if (info.nEscape) break;
			for( x = 0; x < head.biWidth; x++ ){

				color = BlindGetPixelColor( x, y );
				yuvClr = RGBtoYUV( color );

				dtmp = k * ::sqrt( (double)yuvClr.rgbRed );
				if ( dtmp > 255.0 )	dtmp = 255.0;
				if ( dtmp < 0 )	dtmp = 0;
                yuvClr.rgbRed = (BYTE)dtmp;

				color = YUVtoRGB( yuvClr );
				BlindSetPixelColor( x, y, color );
			}
		}
	} else {
		for(i = 0; i < (int)head.biClrUsed; i++){

			color = GetPaletteColor( (BYTE)i );
			yuvClr = RGBtoYUV( color );

			dtmp = k * ::sqrt( (double)yuvClr.rgbRed );
			if ( dtmp > 255.0 )	dtmp = 255.0;
			if ( dtmp < 0 ) dtmp = 0;
            yuvClr.rgbRed = (BYTE)dtmp;

			color = YUVtoRGB( yuvClr );
 			SetPaletteColor( (BYTE)i, color );
		}
	}
 
	return true;
}
コード例 #5
0
ファイル: ximahist.cpp プロジェクト: Bitlsoft/Imagenius_SDK
////////////////////////////////////////////////////////////////////////////////
// HistogramNormalize function by <dave> : dave(at)posortho(dot)com
bool CxImage::HistogramNormalize()
{
	
	

	if (!pDib) return false;

	int histogram[256];
	int threshold_intensity, intense;
	int x, y, i;
	unsigned int normalize_map[256];
	unsigned int high, low, YVal;

	RGBQUAD color;
	RGBQUAD	yuvClr;

	memset( &histogram, 0, sizeof( int ) * 256 );
	memset( &normalize_map, 0, sizeof( unsigned int ) * 256 );
 
     // form histogram
	for(y=0; y < head.biHeight; y++){
		info.nProgress = (long)(50*y/head.biHeight);
		if (info.nEscape) break;
		for(x=0; x < head.biWidth; x++){
			color = BlindGetPixelColor( x, y );
			YVal = (unsigned int)RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
			histogram[YVal]++;
		}
	}

	// find histogram boundaries by locating the 1 percent levels
	threshold_intensity = ( head.biWidth * head.biHeight) / 100;

	intense = 0;
	for( low = 0; low < 255; low++ ){
		intense += histogram[low];
		if( intense > threshold_intensity )	break;
	}

	intense = 0;
	for( high = 255; high != 0; high--){
		intense += histogram[ high ];
		if( intense > threshold_intensity ) break;
	}

	if ( low == high ){
		// Unreasonable contrast;  use zero threshold to determine boundaries.
		threshold_intensity = 0;
		intense = 0;
		for( low = 0; low < 255; low++){
			intense += histogram[low];
			if( intense > threshold_intensity )	break;
		}
		intense = 0;
		for( high = 255; high != 0; high-- ){
			intense += histogram [high ];
			if( intense > threshold_intensity )	break;
		}
	}
	if( low == high ) return false;  // zero span bound

	// Stretch the histogram to create the normalized image mapping.
	for(i = 0; i <= 255; i++){
		if ( i < (int) low ){
			normalize_map[i] = 0;
		} else {
			if(i > (int) high)
				normalize_map[i] = 255;
			else
				normalize_map[i] = ( 255 - 1) * ( i - low) / ( high - low );
		}
	}

	// Normalize
	if( head.biClrUsed == 0 ){
		for( y = 0; y < head.biHeight; y++ ){
			info.nProgress = (long)(50+50*y/head.biHeight);
			if (info.nEscape) break;
			for( x = 0; x < head.biWidth; x++ ){

				color = BlindGetPixelColor( x, y );
				yuvClr = RGBtoYUV( color );

                yuvClr.rgbRed = (BYTE)normalize_map[yuvClr.rgbRed];

				color = YUVtoRGB( yuvClr );
				BlindSetPixelColor( x, y, color );
			}
		}
	} else {
		for(i = 0; i < (int)head.biClrUsed; i++){

			color = GetPaletteColor( (BYTE)i );
			yuvClr = RGBtoYUV( color );

            yuvClr.rgbRed = (BYTE)normalize_map[yuvClr.rgbRed];

			color = YUVtoRGB( yuvClr );
 			SetPaletteColor( (BYTE)i, color );
		}
	}
	return true;
}
コード例 #6
0
ファイル: ximahist.cpp プロジェクト: Bitlsoft/Imagenius_SDK
////////////////////////////////////////////////////////////////////////////////
// HistogramEqualize function by <dave> : dave(at)posortho(dot)com
bool CxImage::HistogramEqualize()
{
	
	

	if (!pDib) return false;

    int histogram[256];
	int map[256];
	int equalize_map[256];
    int x, y, i, j;
	RGBQUAD color;
	RGBQUAD	yuvClr;
	unsigned int YVal, high, low;

	memset( &histogram, 0, sizeof(int) * 256 );
	memset( &map, 0, sizeof(int) * 256 );
	memset( &equalize_map, 0, sizeof(int) * 256 );
 
     // form histogram
	for(y=0; y < head.biHeight; y++){
		info.nProgress = (long)(50*y/head.biHeight);
		if (info.nEscape) break;
		for(x=0; x < head.biWidth; x++){
			color = BlindGetPixelColor( x, y );
			YVal = (unsigned int)RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
			histogram[YVal]++;
		}
	}

	// integrate the histogram to get the equalization map.
	j = 0;
	for(i=0; i <= 255; i++){
		j += histogram[i];
		map[i] = j; 
	}

	// equalize
	low = map[0];
	high = map[255];
	if (low == high) return false;
	for( i = 0; i <= 255; i++ ){
		equalize_map[i] = (unsigned int)((((double)( map[i] - low ) ) * 255) / ( high - low ) );
	}

	// stretch the histogram
	if(head.biClrUsed == 0){ // No Palette
		for( y = 0; y < head.biHeight; y++ ){
			info.nProgress = (long)(50+50*y/head.biHeight);
			if (info.nEscape) break;
			for( x = 0; x < head.biWidth; x++ ){

				color = BlindGetPixelColor( x, y );
				yuvClr = RGBtoYUV(color);

                yuvClr.rgbRed = (BYTE)equalize_map[yuvClr.rgbRed];

				color = YUVtoRGB(yuvClr);
				BlindSetPixelColor( x, y, color );
			}
		}
	} else { // Palette
		for( i = 0; i < (int)head.biClrUsed; i++ ){

			color = GetPaletteColor((BYTE)i);
			yuvClr = RGBtoYUV(color);

            yuvClr.rgbRed = (BYTE)equalize_map[yuvClr.rgbRed];

			color = YUVtoRGB(yuvClr);
			SetPaletteColor( (BYTE)i, color );
		}
	}
	return true;
}
コード例 #7
0
ファイル: ximahist.cpp プロジェクト: JimLiu/asptools
/**
 * HistogramStretch
 * \param method: 0 = luminance (default), 1 = linked channels , 2 = independent channels.
 * \return true if everything is ok
 * \author [dave] and [nipper]
 */
bool CxImage::HistogramStretch(long method)
{
  if (!pDib) return false;

  if ((head.biBitCount==8) && IsGrayScale()){
	// get min/max info
	BYTE minc = 255, maxc = 0;
	BYTE gray;
	long y;

	double dbScaler = 50.0/head.biHeight;

	for (y=0; y<head.biHeight; y++)
	{
		info.nProgress = (long)(y*dbScaler);
		for (long x=0; x<head.biWidth; x++)	{
			gray = GetPixelIndex(x, y);
			if (gray < minc)   minc = gray;
			if (gray > maxc)   maxc = gray; 
		}
	}

	if (minc == 0 && maxc == 255) return true;
	
	// calculate LUT
	BYTE lut[256];
	BYTE range = maxc - minc;
	if (range != 0){
		for (long x = minc; x <= maxc; x++){
			lut[x] = (BYTE)(255 * (x - minc) / range);
		}
	} else lut[minc] = minc;

	for (y=0; y<head.biHeight; y++)	{
		info.nProgress = (long)(50.0+y*dbScaler);
		for (long x=0; x<head.biWidth; x++)
		{
			SetPixelIndex(x, y, lut[GetPixelIndex(x, y)]);
		}
	}
  } else {
	switch(method){
	case 1:
	  { // <nipper>
		// get min/max info
		BYTE minc = 255, maxc = 0;
		RGBQUAD color;
		long y;

		for (y=0; y<head.biHeight; y++)
		{

			for (long x=0; x<head.biWidth; x++)
			{
				color = GetPixelColor(x, y);

				if (color.rgbRed < minc)   minc = color.rgbRed;
				if (color.rgbBlue < minc)  minc = color.rgbBlue;
				if (color.rgbGreen < minc) minc = color.rgbGreen;

				if (color.rgbRed > maxc)   maxc = color.rgbRed; 
				if (color.rgbBlue > maxc)  maxc = color.rgbBlue; 
				if (color.rgbGreen > maxc) maxc = color.rgbGreen; 
			}
		}

		if (minc == 0 && maxc == 255)
			return true;
		
		// calculate LUT
		BYTE lut[256];
		BYTE range = maxc - minc;

		if (range != 0){
			for (long x = minc; x <= maxc; x++){
				lut[x] = (BYTE)(255 * (x - minc) / range);
			}
		} else lut[minc] = minc;

		// normalize image
		double dbScaler = 100.0/head.biHeight;

		for (y=0; y<head.biHeight; y++)	{
			info.nProgress = (long)(y*dbScaler);

			for (long x=0; x<head.biWidth; x++)
			{
				color = GetPixelColor(x, y);

				color.rgbRed = lut[color.rgbRed];
				color.rgbBlue = lut[color.rgbBlue];
				color.rgbGreen = lut[color.rgbGreen];

				SetPixelColor(x, y, color);
			}
		}
	  }
		break;
	case 2:
	  { // <nipper>
		// get min/max info
		BYTE minR = 255, maxR = 0;
		BYTE minG = 255, maxG = 0;
		BYTE minB = 255, maxB = 0;
		RGBQUAD color;
		long y;

		for (y=0; y<head.biHeight; y++)
		{
			for (long x=0; x<head.biWidth; x++)
			{
				color = GetPixelColor(x, y);

				if (color.rgbRed < minR)   minR = color.rgbRed;
				if (color.rgbBlue < minB)  minB = color.rgbBlue;
				if (color.rgbGreen < minG) minG = color.rgbGreen;

				if (color.rgbRed > maxR)   maxR = color.rgbRed; 
				if (color.rgbBlue > maxB)  maxB = color.rgbBlue; 
				if (color.rgbGreen > maxG) maxG = color.rgbGreen; 
			}
		}

		if (minR == 0 && maxR == 255 && minG == 0 && maxG == 255 && minB == 0 && maxB == 255)
			return true;

		// calculate LUT
		BYTE lutR[256];
		BYTE range = maxR - minR;
		if (range != 0)	{
			for (long x = minR; x <= maxR; x++){
				lutR[x] = (BYTE)(255 * (x - minR) / range);
			}
		} else lutR[minR] = minR;

		BYTE lutG[256];
		range = maxG - minG;
		if (range != 0)	{
			for (long x = minG; x <= maxG; x++){
				lutG[x] = (BYTE)(255 * (x - minG) / range);
			}
		} else lutG[minG] = minG;
			
		BYTE lutB[256];
		range = maxB - minB;
		if (range != 0)	{
			for (long x = minB; x <= maxB; x++){
				lutB[x] = (BYTE)(255 * (x - minB) / range);
			}
		} else lutB[minB] = minB;

		// normalize image
		double dbScaler = 100.0/head.biHeight;

		for (y=0; y<head.biHeight; y++)
		{
			info.nProgress = (long)(y*dbScaler);

			for (long x=0; x<head.biWidth; x++)
			{
				color = GetPixelColor(x, y);

				color.rgbRed = lutR[color.rgbRed];
				color.rgbBlue = lutB[color.rgbBlue];
				color.rgbGreen = lutG[color.rgbGreen];

				SetPixelColor(x, y, color);
			}
		}
	  }
		break;
	default:
	  { // <dave>
		// S = ( R - C ) ( B - A / D - C )
		double alimit = 0.0;
		double blimit = 255.0;
		double lowerc = 255.0;
		double upperd = 0.0;
		double tmpGray;

		RGBQUAD color;
		RGBQUAD	yuvClr;
		double  stretcheds;

		if ( head.biClrUsed == 0 ){
			long x, y, xmin, xmax, ymin, ymax;
			xmin = ymin = 0;
			xmax = head.biWidth; 
			ymax = head.biHeight;

			for( y = ymin; y < ymax; y++ ){
				info.nProgress = (long)(50*y/ymax);
				for( x = xmin; x < xmax; x++ ){
					color = GetPixelColor( x, y );
					tmpGray = RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
					if ( tmpGray < lowerc )	lowerc = tmpGray;
					if ( tmpGray > upperd )	upperd = tmpGray;
				}
			}
			if (upperd==lowerc) return false;
			
			for( y = ymin; y < ymax; y++ ){
				info.nProgress = (long)(50+50*y/ymax);
				for( x = xmin; x < xmax; x++ ){

					color = GetPixelColor( x, y );
					yuvClr = RGBtoYUV(color);

					// Stretch Luminance
					tmpGray = (double)yuvClr.rgbRed;
					stretcheds = (double)(tmpGray - lowerc) * ( (blimit - alimit) / (upperd - lowerc) ); // + alimit;
					if ( stretcheds < 0.0 )	stretcheds = 0.0;
					else if ( stretcheds > 255.0 ) stretcheds = 255.0;
					yuvClr.rgbRed = (BYTE)stretcheds;

					color = YUVtoRGB(yuvClr);
					SetPixelColor( x, y, color );
				}
			}
		} else {
			DWORD  j;
			for( j = 0; j < head.biClrUsed; j++ ){
				color = GetPaletteColor( (BYTE)j );
				tmpGray = RGB2GRAY(color.rgbRed, color.rgbGreen, color.rgbBlue);
				if ( tmpGray < lowerc )	lowerc = tmpGray;
				if ( tmpGray > upperd )	upperd = tmpGray;
			}
			if (upperd==lowerc) return false;

			for( j = 0; j < head.biClrUsed; j++ ){

				color = GetPaletteColor( (BYTE)j );
				yuvClr = RGBtoYUV( color );

				// Stretch Luminance
				tmpGray = (double)yuvClr.rgbRed;
				stretcheds = (double)(tmpGray - lowerc) * ( (blimit - alimit) / (upperd - lowerc) ); // + alimit;
				if ( stretcheds < 0.0 )	stretcheds = 0.0;
				else if ( stretcheds > 255.0 ) stretcheds = 255.0;
				yuvClr.rgbRed = (BYTE)stretcheds;

				color = YUVtoRGB(yuvClr);
				SetPaletteColor( (BYTE)j, color );
			}
		}
	  }
	}
  }
  return true;
}
コード例 #8
0
ファイル: ximapcx.cpp プロジェクト: AnthonyNystrom/GenXSource
bool CxImagePCX::Decode(CxFile *hFile)
{
	if (hFile == NULL) return false;

	PCXHEADER pcxHeader;
	int i, x, y, y2, nbytes, count, Height, Width;
	BYTE c, ColorMap[PCX_MAXCOLORS][3];
	BYTE *pcximage = NULL, *lpHead1 = NULL, *lpHead2 = NULL;
	BYTE *pcxplanes, *pcxpixels;

  try
  {
	if (hFile->Read(&pcxHeader,sizeof(PCXHEADER),1)==0) throw "Can't read PCX image";

    if (pcxHeader.Manufacturer != PCX_MAGIC) throw "Error: Not a PCX file";
    // Check for PCX run length encoding
    if (pcxHeader.Encoding != 1) throw "PCX file has unknown encoding scheme";
 
    Width = (pcxHeader.Xmax - pcxHeader.Xmin) + 1;
    Height = (pcxHeader.Ymax - pcxHeader.Ymin) + 1;
	info.xDPI = pcxHeader.Hres;
	info.yDPI = pcxHeader.Vres;

    // Check that we can handle this image format
    if (pcxHeader.ColorPlanes > 4)
		throw "Can't handle image with more than 4 planes";

	// Create the image
	if (pcxHeader.ColorPlanes >= 3 && pcxHeader.BitsPerPixel == 8){
		Create (Width, Height, 24, CXIMAGE_FORMAT_PCX);
#if CXIMAGE_SUPPORT_ALPHA
		if (pcxHeader.ColorPlanes==4) AlphaCreate();
#endif //CXIMAGE_SUPPORT_ALPHA
	} else if (pcxHeader.ColorPlanes == 4 && pcxHeader.BitsPerPixel == 1)
		Create (Width, Height, 4, CXIMAGE_FORMAT_PCX);
	else
		Create (Width, Height, pcxHeader.BitsPerPixel, CXIMAGE_FORMAT_PCX);

	if (info.nEscape) throw "Cancelled"; // <vho> - cancel decoding

	//Read the image and check if it's ok
    nbytes = pcxHeader.BytesPerLine * pcxHeader.ColorPlanes * Height;
    lpHead1 = pcximage = (BYTE*)malloc(nbytes);
    while (nbytes > 0){
		if (hFile == NULL || hFile->Eof()) throw "corrupted PCX";

		hFile->Read(&c,1,1);
		if ((c & 0XC0) != 0XC0){ // Repeated group
			*pcximage++ = c;
			--nbytes;
			continue;
		}
		count = c & 0X3F; // extract count
		hFile->Read(&c,1,1);
		if (count > nbytes) throw "repeat count spans end of image";

		nbytes -= count;
		while (--count >=0) *pcximage++ = c;
	}
    pcximage = lpHead1;

	//store the palette
    for (i = 0; i < 16; i++){
		ColorMap[i][0] = pcxHeader.ColorMap[i][0];
		ColorMap[i][1] = pcxHeader.ColorMap[i][1];
		ColorMap[i][2] = pcxHeader.ColorMap[i][2];
	}
    if (pcxHeader.BitsPerPixel == 8 && pcxHeader.ColorPlanes == 1){
		hFile->Read(&c,1,1);
		if (c != PCX_256_COLORS) throw "bad color map signature";
		
		for (i = 0; i < PCX_MAXCOLORS; i++){
			hFile->Read(&ColorMap[i][0],1,1);
			hFile->Read(&ColorMap[i][1],1,1);
			hFile->Read(&ColorMap[i][2],1,1);
		}
	}
    if (pcxHeader.BitsPerPixel == 1 && pcxHeader.ColorPlanes == 1){
		ColorMap[0][0] = ColorMap[0][1] = ColorMap[0][2] = 0;
		ColorMap[1][0] = ColorMap[1][1] = ColorMap[1][2] = 255;
	}

	for (DWORD idx=0; idx<head.biClrUsed; idx++) SetPaletteColor((BYTE)idx,ColorMap[idx][0],ColorMap[idx][1],ColorMap[idx][2]);

    lpHead2 = pcxpixels = (BYTE *)malloc(Width + pcxHeader.BytesPerLine * 8);
    // Convert the image
    for (y = 0; y < Height; y++){

		if (info.nEscape) throw "Cancelled"; // <vho> - cancel decoding

		y2=Height-1-y;
		pcxpixels = lpHead2;
		pcxplanes = pcximage + (y * pcxHeader.BytesPerLine * pcxHeader.ColorPlanes);

		if (pcxHeader.ColorPlanes == 3 && pcxHeader.BitsPerPixel == 8){
			// Deal with 24 bit color image
			for (x = 0; x < Width; x++){
				SetPixelColor(x,y2,RGB(pcxplanes[x],pcxplanes[pcxHeader.BytesPerLine + x],pcxplanes[2*pcxHeader.BytesPerLine + x]));
			}
			continue;
#if CXIMAGE_SUPPORT_ALPHA
		} else if (pcxHeader.ColorPlanes == 4 && pcxHeader.BitsPerPixel == 8){
			for (x = 0; x < Width; x++){
				SetPixelColor(x,y2,RGB(pcxplanes[x],pcxplanes[pcxHeader.BytesPerLine + x],pcxplanes[2*pcxHeader.BytesPerLine + x]));
				AlphaSet(x,y2,pcxplanes[3*pcxHeader.BytesPerLine + x]);
			}
			continue;
#endif //CXIMAGE_SUPPORT_ALPHA
		} else if (pcxHeader.ColorPlanes == 1) {
			PCX_UnpackPixels(pcxpixels, pcxplanes, pcxHeader.BytesPerLine, pcxHeader.ColorPlanes, pcxHeader.BitsPerPixel);
		} else {
			PCX_PlanesToPixels(pcxpixels, pcxplanes, pcxHeader.BytesPerLine, pcxHeader.ColorPlanes, pcxHeader.BitsPerPixel);
		}
		for (x = 0; x < Width; x++)	SetPixelIndex(x,y2,pcxpixels[x]);
	}

  } catch (char *message) {
	strncpy(info.szLastError,message,255);
	if (lpHead1){ free(lpHead1); lpHead1 = NULL; }
    if (lpHead2){ free(lpHead2); lpHead2 = NULL; }
	return false;
  }
	if (lpHead1){ free(lpHead1); lpHead1 = NULL; }
    if (lpHead2){ free(lpHead2); lpHead2 = NULL; }
	return true;
}
コード例 #9
0
ファイル: ximatif.cpp プロジェクト: dehilsterlexis/eclide-1
bool CxImageTIF::EncodeBody(TIFF *m_tif, bool multipage, int page, int pagecount)
{
    uint32 height=head.biHeight;
    uint32 width=head.biWidth;
    uint16 bitcount=head.biBitCount;
    uint16 bitspersample;
    uint16 samplesperpixel;
    uint16 photometric=0;
    uint16 compression;
//	uint16 pitch;
//	int line;
    uint32 x, y;

    samplesperpixel = ((bitcount == 24) || (bitcount == 32)) ? (BYTE)3 : (BYTE)1;
#if CXIMAGE_SUPPORT_ALPHA
    if (bitcount==24 && AlphaIsValid()) { bitcount=32; samplesperpixel=4; }
#endif //CXIMAGE_SUPPORT_ALPHA

    bitspersample = bitcount / samplesperpixel;

    //set the PHOTOMETRIC tag
    RGBQUAD *rgb = GetPalette();
    switch (bitcount) {
        case 1:
            if (CompareColors(&rgb[0],&rgb[1])<0) {
                /* <abe> some viewers do not handle PHOTOMETRIC_MINISBLACK:
                 * let's transform the image in PHOTOMETRIC_MINISWHITE
                 */
                //invert the colors
                RGBQUAD tempRGB=GetPaletteColor(0);
                SetPaletteColor(0,GetPaletteColor(1));
                SetPaletteColor(1,tempRGB);
                //invert the pixels
                BYTE *iSrc=info.pImage;
                for (unsigned long i=0;i<head.biSizeImage;i++){
                    *iSrc=(BYTE)~(*(iSrc));
                    iSrc++;
                }
                photometric = PHOTOMETRIC_MINISWHITE;
                //photometric = PHOTOMETRIC_MINISBLACK;
            } else {
                photometric = PHOTOMETRIC_MINISWHITE;
            }
            break;
        case 4:	// Check if the DIB has a color or a greyscale palette
        case 8:
            photometric = PHOTOMETRIC_MINISBLACK; //default to gray scale
            for (x = 0; x < head.biClrUsed; x++) {
                if ((rgb->rgbRed != x)||(rgb->rgbRed != rgb->rgbGreen)||(rgb->rgbRed != rgb->rgbBlue)){
                    photometric = PHOTOMETRIC_PALETTE;
                    break;
                }
                rgb++;
            }
            break;
        case 24:
        case 32:
            photometric = PHOTOMETRIC_RGB;			
            break;
    }

#if CXIMAGE_SUPPORT_ALPHA
    if (AlphaIsValid() && bitcount==8) samplesperpixel=2; //8bpp + alpha layer
#endif //CXIMAGE_SUPPORT_ALPHA

//	line = CalculateLine(width, bitspersample * samplesperpixel);
//	pitch = (uint16)CalculatePitch(line);

    //prepare the palette struct
    RGBQUAD pal[256];
    if (GetPalette()){
        BYTE b;
        memcpy(pal,GetPalette(),GetPaletteSize());
        for(WORD a=0;a<head.biClrUsed;a++){	//swap blue and red components
            b=pal[a].rgbBlue; pal[a].rgbBlue=pal[a].rgbRed; pal[a].rgbRed=b;
        }
    }

    // handle standard width/height/bpp stuff
    TIFFSetField(m_tif, TIFFTAG_IMAGEWIDTH, width);
    TIFFSetField(m_tif, TIFFTAG_IMAGELENGTH, height);
    TIFFSetField(m_tif, TIFFTAG_SAMPLESPERPIXEL, samplesperpixel);
    TIFFSetField(m_tif, TIFFTAG_BITSPERSAMPLE, bitspersample);
    TIFFSetField(m_tif, TIFFTAG_PHOTOMETRIC, photometric);
    TIFFSetField(m_tif, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG);	// single image plane 
    TIFFSetField(m_tif, TIFFTAG_ORIENTATION, ORIENTATION_TOPLEFT);

    uint32 rowsperstrip = TIFFDefaultStripSize(m_tif, (uint32) -1);  //<REC> gives better compression
    TIFFSetField(m_tif, TIFFTAG_ROWSPERSTRIP, rowsperstrip);

    // handle metrics
    TIFFSetField(m_tif, TIFFTAG_RESOLUTIONUNIT, RESUNIT_INCH);
    TIFFSetField(m_tif, TIFFTAG_XRESOLUTION, (float)info.xDPI);
    TIFFSetField(m_tif, TIFFTAG_YRESOLUTION, (float)info.yDPI);
//	TIFFSetField(m_tif, TIFFTAG_XPOSITION, (float)info.xOffset);
//	TIFFSetField(m_tif, TIFFTAG_YPOSITION, (float)info.yOffset);

    // multi-paging - Thanks to Abe <God(dot)bless(at)marihuana(dot)com>
    if (multipage)
    {
        char page_number[20];
        sprintf(page_number, "Page %d", page);

        TIFFSetField(m_tif, TIFFTAG_SUBFILETYPE, FILETYPE_PAGE);
        TIFFSetField(m_tif, TIFFTAG_PAGENUMBER, page,pagecount);
        TIFFSetField(m_tif, TIFFTAG_PAGENAME, page_number);
    } else {
        TIFFSetField(m_tif, TIFFTAG_SUBFILETYPE, 0);
    }

    // palettes (image colormaps are automatically scaled to 16-bits)
    if (photometric == PHOTOMETRIC_PALETTE) {
        uint16 *r, *g, *b;
        r = (uint16 *) _TIFFmalloc(sizeof(uint16) * 3 * 256);
        g = r + 256;
        b = g + 256;

        for (int i = 255; i >= 0; i--) {
            b[i] = (uint16)SCALE((uint16)pal[i].rgbRed);
            g[i] = (uint16)SCALE((uint16)pal[i].rgbGreen);
            r[i] = (uint16)SCALE((uint16)pal[i].rgbBlue);
        }

        TIFFSetField(m_tif, TIFFTAG_COLORMAP, r, g, b);
        _TIFFfree(r);
    }

    // compression
    if (GetCodecOption(CXIMAGE_FORMAT_TIF)) {
        compression = (WORD)GetCodecOption(CXIMAGE_FORMAT_TIF);
    } else {
        switch (bitcount) {
            case 1 :
                compression = COMPRESSION_CCITTFAX4;
                break;
            case 4 :
            case 8 :
                compression = COMPRESSION_LZW;
                break;
            case 24 :
            case 32 :
                compression = COMPRESSION_JPEG;
                break;
            default :
                compression = COMPRESSION_NONE;
                break;
        }
    }
    TIFFSetField(m_tif, TIFFTAG_COMPRESSION, compression);

    switch (compression) {
    case COMPRESSION_JPEG:
        TIFFSetField(m_tif, TIFFTAG_JPEGQUALITY, info.nQuality);
        TIFFSetField(m_tif, TIFFTAG_ROWSPERSTRIP, ((7+rowsperstrip)>>3)<<3);
        break;
    case COMPRESSION_LZW:
        if (bitcount>=8) TIFFSetField(m_tif, TIFFTAG_PREDICTOR, 2);
        break;
    }

    // read the DIB lines from bottom to top and save them in the TIF

    BYTE *bits;
    switch(bitcount) {				
        case 1 :
        case 4 :
        case 8 :
        {
            if (samplesperpixel==1){
                for (y = 0; y < height; y++) {
                    bits= info.pImage + (height - y - 1)*info.dwEffWidth;
                    if (TIFFWriteScanline(m_tif,bits, y, 0)==-1) return false;
                }
            }
#if CXIMAGE_SUPPORT_ALPHA
            else { //8bpp + alpha layer
                bits = (BYTE*)malloc(2*width);
                if (!bits) return false;
                for (y = 0; y < height; y++) {
                    for (x=0;x<width;x++){
                        bits[2*x]=GetPixelIndex(x,height - y - 1);
                        bits[2*x+1]=AlphaGet(x,height - y - 1);
                    }
                    if (TIFFWriteScanline(m_tif,bits, y, 0)==-1) {
                        free(bits);
                        return false;
                    }
                }
                free(bits);
            }
#endif //CXIMAGE_SUPPORT_ALPHA
            break;
        }				
        case 24:
        {
            BYTE *buffer = (BYTE *)malloc(info.dwEffWidth);
            if (!buffer) return false;
            for (y = 0; y < height; y++) {
                // get a pointer to the scanline
                memcpy(buffer, info.pImage + (height - y - 1)*info.dwEffWidth, info.dwEffWidth);
                // TIFFs store color data RGB instead of BGR
                BYTE *pBuf = buffer;
                for (x = 0; x < width; x++) {
                    BYTE tmp = pBuf[0];
                    pBuf[0] = pBuf[2];
                    pBuf[2] = tmp;
                    pBuf += 3;
                }
                // write the scanline to disc
                if (TIFFWriteScanline(m_tif, buffer, y, 0)==-1){
                    free(buffer);
                    return false;
                }
            }
            free(buffer);
            break;
        }				
        case 32 :
        {
#if CXIMAGE_SUPPORT_ALPHA
            BYTE *buffer = (BYTE *)malloc((info.dwEffWidth*4)/3);
            if (!buffer) return false;
            for (y = 0; y < height; y++) {
                // get a pointer to the scanline
                memcpy(buffer, info.pImage + (height - y - 1)*info.dwEffWidth, info.dwEffWidth);
                // TIFFs store color data RGB instead of BGR
                BYTE *pSrc = buffer + 3 * width;
                BYTE *pDst = buffer + 4 * width;
                for (x = 0; x < width; x++) {
                    pDst-=4;
                    pSrc-=3;
                    pDst[3] = AlphaGet(width-x-1,height-y-1);
                    pDst[2] = pSrc[0];
                    pDst[1] = pSrc[1];
                    pDst[0] = pSrc[2];
                }
                // write the scanline to disc
                if (TIFFWriteScanline(m_tif, buffer, y, 0)==-1){
                    free(buffer);
                    return false;
                }
            }
            free(buffer);
#endif //CXIMAGE_SUPPORT_ALPHA
            break;
        }				
    }
    return true;
}