Пример #1
0
//--------------------------------------------------------------------------//
//--------------------------------------------------------------------------//
void CAGSymImage::LoadDIB(const BITMAPINFOHEADER* pHdr, const BYTE* pBits)
{
	Free();

	if (pHdr->biCompression == BI_RGB && (pHdr->biBitCount == 1 || pHdr->biBitCount == 4 || pHdr->biBitCount == 8 || pHdr->biBitCount == 24))
	{
		BITMAPINFOHEADER bi;
		bi = *pHdr;
		bi.biCompression = BI_RGB;

		if (!bi.biSizeImage)
			bi.biSizeImage = DibSizeImage(&bi);
		if (!bi.biClrUsed)
			bi.biClrUsed = DibNumColors(&bi);

		if (m_pDIB = (BITMAPINFOHEADER*)malloc(DibSize(&bi)))
		{
			*m_pDIB = bi;

			if (bi.biClrUsed)
				memcpy((void*)DibColors(m_pDIB), (void*)DibColors(pHdr), DibPaletteSize(pHdr));

			BYTE* pNewBits = (BYTE*)DibPtr(m_pDIB);
			const BYTE* pSrcBits;
			if (pBits)
				pSrcBits = pBits;
			else
				pSrcBits = (BYTE*)(DibColors(pHdr) + bi.biClrUsed);

			memcpy(pNewBits, pSrcBits, bi.biSizeImage);
		}
	}
}
Пример #2
0
BOOL FAR PASCAL DibClear(PDIB pdibDst, LPVOID pbitsDst, BYTE value)
{
	WORD selDst;
	DWORD offDst;

	if ((pdibDst == NULL)
	||  (pbitsDst == NULL))
		return FALSE;

	if ((long)pbitsDst & 3)
		return FALSE;	// we must be dword aligned

	selDst = HIWORD(pbitsDst);
	offDst = LOWORD(pbitsDst);

	ClearMem32(selDst, offDst, DibSizeImage(pdibDst), value);
	return TRUE;
}
Пример #3
0
HGLOBAL CPng::PNGToDIB(png_structp png_ptr, png_infop info_ptr)
{
	//Read the image
	png_read_info(png_ptr, info_ptr);

	int nBitDepth = 0;
	int nColorType = 0;
	png_uint_32 width = 0;
	png_uint_32 height = 0;
	png_get_IHDR(png_ptr, info_ptr, &width, &height, &nBitDepth, &nColorType, NULL, NULL, NULL);

	IMAGE img;
	img.width = (LONG)width;
	img.height = (LONG)height;

	//Determine the type of format
	if (nColorType==PNG_COLOR_TYPE_RGB || nColorType==PNG_COLOR_TYPE_RGB_ALPHA)
	{
		img.pixdepth = 24;		// nBitDepth 8, 16
		img.palnum   = 0;
	}
	else
	{
		switch(nBitDepth) // bit depths 1, 2, 4, 8, 16
		{	
			case 2:  
				img.pixdepth = 4;		
				break;
			case 16: 
				img.pixdepth = 8;		
				break;
			default: 
				img.pixdepth = nBitDepth;
		}

		img.palnum = 1 << img.pixdepth;
	}

	//Allocate the image struct that will be used to transport file info
	if (!AllocImageStruct(&img))
	{
		longjmp(png_ptr->jmpbuf, 1);
	}

	//Not sure if we can take advantage of this info in a BMP, thus remove it.
	if (nColorType & PNG_COLOR_MASK_ALPHA)
		png_set_strip_alpha(png_ptr);

	//Set user transform function to deal with a Bitdepth of 2
	if (nBitDepth == 2)
	{
		png_set_user_transform_info(png_ptr, NULL, 4, 1);
		png_set_read_user_transform_fn(png_ptr, ConvertTo4BitsPerPix);
	}

	//Tell libpng to strip 16 bit/color files down to 8 bits/color
	if (nBitDepth == 16) 
		png_set_strip_16(png_ptr);

	if (nColorType==PNG_COLOR_TYPE_RGB || nColorType==PNG_COLOR_TYPE_RGB_ALPHA)
	{
		png_set_bgr(png_ptr);
	}

	png_read_update_info(png_ptr, info_ptr);

	//If palette, get it and fill our img struct
	if (img.palnum > 0)
	{
		if (nColorType == PNG_COLOR_TYPE_PALETTE)
		{
			png_colorp palette;
			int num_palette;
			png_get_PLTE(png_ptr, info_ptr, &palette, &num_palette);
			if (num_palette > (int)img.palnum) 
				num_palette = img.palnum;

			memset(img.palette, 0, img.palnum * sizeof(png_color));
			memcpy(img.palette, palette, num_palette * sizeof(png_color));
		}
		else
		{
			int depth = (nBitDepth == 16)? 8 : nBitDepth ;
			png_build_grayscale_palette(depth, img.palette);
		}
	}

	png_read_image(png_ptr, img.rowptr);

	png_infop end_info = NULL;
	png_read_end(png_ptr, end_info);

	// Alloc the buffer to be big enough to hold all the bits
	DWORD dwLen = (DWORD)sizeof(BITMAPINFOHEADER) + (img.palnum * sizeof(RGBQUAD)) + img.imgbytes;

	// Allocate enough memory to hold the entire DIB
	HGLOBAL hMemory = ::GlobalAlloc(GMEM_FIXED | GMEM_ZEROINIT, dwLen);
	if (!hMemory)
		return NULL;

	//Begin filling out DIB info
	BITMAPINFOHEADER* pDib = (BITMAPINFOHEADER*)::GlobalLock(hMemory);
	if (!pDib)
	{
		::GlobalFree(hMemory);
		return NULL;
	}

	::ZeroMemory(pDib, dwLen);
	pDib->biSize			= sizeof(BITMAPINFOHEADER);
	pDib->biWidth			= (DWORD)img.width; 
	pDib->biHeight			= (DWORD)img.height; 
	pDib->biPlanes			= 1;
	pDib->biCompression		= BI_RGB;
	pDib->biXPelsPerMeter	= 3937; // 100 pixels/inch
	pDib->biYPelsPerMeter	= 3937;
	pDib->biSizeImage		= img.imgbytes;
	pDib->biBitCount		= img.pixdepth; 
	pDib->biClrUsed			= img.palnum;

	if (pDib->biBitCount >= 16)
		pDib->biBitCount = 24;	

	if (pDib->biClrUsed)
	{
		RGBQUAD* pRgb = DibColors(pDib);
		BYTE rgbq[RGBQUAD_SIZE];
		PALETTE* pal;
		UINT nIndex;
		memset(rgbq, 0, sizeof(rgbq));
		for (pal = img.palette, nIndex = img.palnum ; nIndex > 0 ; nIndex--, pal++)
		{
			rgbq[RGBQ_RED]			= pal->red;
			rgbq[RGBQ_GREEN]		= pal->green;
			rgbq[RGBQ_BLUE]			= pal->blue;
			rgbq[RGBQ_RESERVED]		= 0;
			memcpy((LPVOID)pRgb, rgbq, sizeof(RGBQUAD));
			pRgb++;
		}
	}

	memcpy(DibPtr(pDib), img.bmpbits, DibSizeImage(pDib));

	FreeImageStruct(&img);

	::GlobalUnlock(hMemory);
	return hMemory;
}
Пример #4
0
PDIB DibReadBitmapInfo(int fh)
{
    DWORD     off;
    HANDLE    hbi = NULL;
    int       size;
    int       i;
    int       nNumColors;

    RGBQUAD FAR       *pRgb;
    BITMAPINFOHEADER   bi;
    BITMAPCOREHEADER   bc;
    BITMAPFILEHEADER   bf;
    PDIB               pdib;

    if (fh == -1)
        return NULL;

    off = lseek(fh,0L,SEEK_CUR);

    if (sizeof(bf) != read(fh,(LPSTR)&bf,sizeof(bf)))
        return FALSE;

    /*
     *  do we have a RC HEADER?
     */
    if (bf.bfType != BFT_BITMAP)
    {
        bf.bfOffBits = 0L;
        lseek(fh,off,SEEK_SET);
    }

    if (sizeof(bi) != read(fh,(LPSTR)&bi,sizeof(bi)))
        return FALSE;

    /*
     *  what type of bitmap info is this?
     */
    switch (size = (int)bi.biSize)
    {
    default:
    case sizeof(BITMAPINFOHEADER):
       break;
       
    case sizeof(BITMAPCOREHEADER):
       bc = *(BITMAPCOREHEADER*)&bi;
       bi.biSize               = sizeof(BITMAPINFOHEADER);
       bi.biWidth              = (DWORD)bc.bcWidth;
       bi.biHeight             = (DWORD)bc.bcHeight;
       bi.biPlanes             =  (UINT)bc.bcPlanes;
       bi.biBitCount           =  (UINT)bc.bcBitCount;
       bi.biCompression        = BI_RGB;
       bi.biSizeImage          = 0;
       bi.biXPelsPerMeter      = 0;
       bi.biYPelsPerMeter      = 0;
       bi.biClrUsed            = 0;
       bi.biClrImportant       = 0;
       
       lseek(fh,(LONG)sizeof(BITMAPCOREHEADER)-sizeof(BITMAPINFOHEADER),SEEK_CUR);
       
       break;
    }
    
    nNumColors = DibNumColors(&bi);
    
    if (bi.biSizeImage == 0)
        bi.biSizeImage = DibSizeImage(&bi);

    if (bi.biClrUsed == 0)
        bi.biClrUsed = DibNumColors(&bi);

    pdib = (PDIB) malloc((LONG)bi.biSize + nNumColors * sizeof(RGBQUAD));

    if (!pdib)
        return NULL;

    *pdib = bi;

    pRgb = DibColors(pdib);

    if (nNumColors == 0)
    {
       printf("Bitmap has no palette (24 bit)\n", NUM_COLORS, nNumColors);
       return NULL;
    }

    if (nNumColors != NUM_COLORS)
    {
       printf("Expecting %d color bitmap; found %d colors\n", NUM_COLORS, nNumColors);
       return NULL;
    }
       
    if (size == sizeof(BITMAPCOREHEADER))
    {
       /*
        * convert a old color table (3 byte entries) to a new
        * color table (4 byte entries)
        */
       read(fh,(LPVOID)pRgb,nNumColors * sizeof(RGBTRIPLE));
       
       for (i=nNumColors-1; i>=0; i--)
       {
          RGBQUAD rgb;
          
          rgb.rgbRed      = ((RGBTRIPLE FAR *)pRgb)[i].rgbtRed;
          rgb.rgbBlue     = ((RGBTRIPLE FAR *)pRgb)[i].rgbtBlue;
          rgb.rgbGreen    = ((RGBTRIPLE FAR *)pRgb)[i].rgbtGreen;
          rgb.rgbReserved = (BYTE)0;
          
          pRgb[i] = rgb;
       }
    }
    else
    {
       read(fh,(LPVOID)pRgb,nNumColors * sizeof(RGBQUAD));
    }

    if (bf.bfOffBits != 0L)
        lseek(fh,off + bf.bfOffBits,SEEK_SET);

    return pdib;
}