BOOL ImageDib::Read(LPCTSTR lpszPathName)
{
	CFile file;
	if (!file.Open(lpszPathName, CFile::modeRead | CFile::shareDenyWrite))
		return FALSE;
	BITMAPFILEHEADER bmfh;

	int nCount=file.Read((LPVOID) &bmfh, sizeof(BITMAPFILEHEADER));

	if(m_lpDib!=NULL)	delete []m_lpDib;
	m_lpDib=new BYTE[file.GetLength() -sizeof(BITMAPFILEHEADER)];
	file.Read(m_lpDib, file.GetLength() -sizeof(BITMAPFILEHEADER));

	m_lpBmpInfoHead = (LPBITMAPINFOHEADER)m_lpDib;

	m_imgWidth=m_lpBmpInfoHead->biWidth;
	m_imgHeight=m_lpBmpInfoHead->biHeight;
	m_nBitCount=m_lpBmpInfoHead->biBitCount; 

	m_nColorTableLength=	ComputeColorTabalLength(m_lpBmpInfoHead->biBitCount);

	m_hPalette = NULL;
	if(m_nColorTableLength!=0){m_lpColorTable=
	(LPRGBQUAD)(m_lpDib+sizeof(BITMAPINFOHEADER));
	    MakePalette();
	}

	m_pImgData = (LPBYTE)m_lpDib+sizeof(BITMAPINFOHEADER) +
		sizeof(RGBQUAD) * m_nColorTableLength;
	return TRUE;
}
Exemple #2
0
BOOL CDib::AttachMemory(LPVOID lpvMem, BOOL bMustDelete, HGLOBAL hGlobal)
{
	// asume que BITMAPINFOHEADER, la tabla de colores y la imagen son contiguos
	// la tabla de colores podría ser de longitud cero
	Empty();
	m_hGlobal = hGlobal;
	if(bMustDelete == FALSE) {
		m_nBmihAlloc = noAlloc;
	}
	else {
		m_nBmihAlloc = ((hGlobal == NULL) ? crtAlloc : heapAlloc);
	}
	try {
		m_lpBMIH = (LPBITMAPINFOHEADER) lpvMem;
		ComputeMetrics();
		ComputePaletteSize(m_lpBMIH->biBitCount);
		m_lpImage = (LPBYTE) m_lpvColorTable + sizeof(RGBQUAD) * m_nColorTableEntries;
		MakePalette();
	}
	catch(CException* pe) {
		AfxMessageBox(_T("Error de AttachMemory"));
		pe->Delete();
		return FALSE;
	}
	return TRUE;
}
Exemple #3
0
CImageBMP::CImageBMP( const CBitmap* bmp)
{
    bgindex = -1;
    lpbi = 0;
    RawImage = 0;
    imagePalette = 0;
    if (bmp) {     
        BITMAP bm;
        HBITMAP hBitmap = (HBITMAP)(bmp->GetSafeHandle());
        GetObject(hBitmap, sizeof(BITMAP), (LPSTR) &bm);
        int width = bm.bmWidth;
        int height = bm.bmHeight;
        //      int depth = bm.bmPlanes;
        int depth = bm.bmBitsPixel;
        Create(width, height, depth);
        HDC dc = ::GetDC(NULL);
        if (GetDIBits(dc, hBitmap, 0, GetHeight(),
            RawImage, (LPBITMAPINFO)lpbi, DIB_RGB_COLORS) == 0)
        {
            TRACE0("GetDIBits failed");       
        }
        // Create a palette - PJO
        HPALETTE palette;
        if (palette = MakePalette((const BITMAPINFO FAR*)lpbi, 0))
        {
            imagePalette = new CImagePalette;
            imagePalette->Attach(palette);
            DibSetUsage(lpbi, (HPALETTE) (*imagePalette), CIMAGE_COLORS);
            ColorType = (COLORTYPE_PALETTE | COLORTYPE_COLOR);
        } 
        ::ReleaseDC(NULL, dc);
    }
}
//------------------------------------------------------------------------------
Example::Example(void)
 : glfw_error_handler(glfwSetErrorCallback(HandleGLFWError))
 , glfw_init_ok(glfwInit())
 , glfw_window(InitWindow())
 , gl()
 , palette(MakePalette())
 , program(MakeProgram())
 , view_matrix(program, "ViewMatrix")
 , screen(
	oglplus::List("Position").Get(),
	oglplus::shapes::Screen(),
	program
), screen_width(800)
 , screen_height(600)
 , view_aspect(4.0/3.0)
 , view_divs(4)
 , view_tile(0)
 , view_tile_index(view_divs*view_divs)
 , mouse_left_down(false)
 , mouse_middle_down(false)
 , frame_no(0)
{
	oglplus::UniformSampler(program, "Palette").Set(0);


	for(unsigned i=0; i!=view_tile_index.size(); ++i)
		view_tile_index[i] = i;
	CenterView();
	UpdateView();

	screen.Use();
	self_ptr(this);

	gl.Enable(oglplus::Capability::ScissorTest);
}
Exemple #5
0
/*************************************************************************
 *
 * \函数名称:
 *   Read()
 *
 * \输入参数:
 *   CFile*	pFile			- 指向CFile对象的指针
 *
 * \返回值:
 *   BOOL				- 如果成功,则返回TRUE
 *
 * \说明:
 *   该函数DIB从一个文件读入CDib对象。该文件必须成功打开。如果该文件是BMP文件
 *   读取工作从文件头开始。如果该文件是一个文档,读取工作则从当前文件指针处开始 
 *
 ************************************************************************
 */
BOOL CDib::Read(CFile* pFile)
{
	// 释放已经分配的内存
	Empty();

	// 临时存放信息的变量
	int nCount, nSize;
	BITMAPFILEHEADER bmfh;

	// 进行读操作
	try 
	{
		// 读取文件头
		nCount = pFile->Read((LPVOID) &bmfh, sizeof(BITMAPFILEHEADER));
		if(nCount != sizeof(BITMAPFILEHEADER)) {
			throw new CException;
		}

		// 如果文件类型部位"BM",则返回并进行相应错误处理
		if(bmfh.bfType != 0x4d42) {
			throw new CException;
		}

		// 计算信息头加上调色板的大小,并分配相应的内存
		nSize = bmfh.bfOffBits - sizeof(BITMAPFILEHEADER);
		m_lpBMIH = (LPBITMAPINFOHEADER) new char[nSize];
		m_nBmihAlloc = m_nImageAlloc = crtAlloc;

		// 读取信息头和调色板
		nCount = pFile->Read(m_lpBMIH, nSize); 

		// 计算图象数据大小并设置调色板指针
		ComputeMetrics();

		// 计算调色板的表项数
		ComputePaletteSize(m_lpBMIH->biBitCount);

		// 如果DIB中存在调色板,则创建一个Windows调色板
		MakePalette();

		// 分配图象数据内存,并从文件中读取图象数据
		m_lpImage = (LPBYTE) new char[m_dwSizeImage];
		nCount = pFile->Read(m_lpImage, m_dwSizeImage); 
	}

	// 错误处理
	catch(CException* pe) 
	{
		AfxMessageBox("Read error");
		pe->Delete();
		return FALSE;
	}

	// 返回
	return TRUE;
}
ImageDib::ImageDib(CSize size, int nBitCount, LPRGBQUAD lpColorTable,
			   unsigned char *pImgData)
{
	if(pImgData==NULL){
		m_lpDib=NULL;
		m_lpColorTable=NULL;
		m_pImgData=NULL;  
		m_lpBmpInfoHead=NULL;
		m_hPalette = NULL;
	}
	else{

		m_imgWidth=size.cx;
		m_imgHeight=size.cy;
		m_nBitCount=nBitCount;
		
		m_nColorTableLength=ComputeColorTabalLength(nBitCount);
		
		int lineByte=(m_imgWidth*nBitCount/8+3)/4*4;
		
		int imgBufSize=m_imgHeight*lineByte;
		
		m_lpDib=new BYTE [sizeof(BITMAPINFOHEADER) + 
			sizeof(RGBQUAD) * m_nColorTableLength+imgBufSize];
		
		m_lpBmpInfoHead = (LPBITMAPINFOHEADER) m_lpDib;
		m_lpBmpInfoHead->biSize = sizeof(BITMAPINFOHEADER);
		m_lpBmpInfoHead->biWidth = m_imgWidth;
		m_lpBmpInfoHead->biHeight = m_imgHeight;
		m_lpBmpInfoHead->biPlanes = 1;
		m_lpBmpInfoHead->biBitCount = m_nBitCount;
		m_lpBmpInfoHead->biCompression = BI_RGB;
		m_lpBmpInfoHead->biSizeImage = 0;
		m_lpBmpInfoHead->biXPelsPerMeter = 0;
		m_lpBmpInfoHead->biYPelsPerMeter = 0;
		m_lpBmpInfoHead->biClrUsed = m_nColorTableLength;
		m_lpBmpInfoHead->biClrImportant = m_nColorTableLength;
		
		m_hPalette = NULL;

		if(m_nColorTableLength!=0){
			
			m_lpColorTable=(LPRGBQUAD)(m_lpDib+sizeof(BITMAPINFOHEADER));
			
			memcpy(m_lpColorTable,lpColorTable,sizeof(RGBQUAD) * m_nColorTableLength);
			
			MakePalette();
		}
		
		m_pImgData = (LPBYTE)m_lpDib+sizeof(BITMAPINFOHEADER)+
			sizeof(RGBQUAD) * m_nColorTableLength;
		
		memcpy(m_pImgData,pImgData,imgBufSize);
	}
	
}
Exemple #7
0
BOOL CDib::ReadSection(CFile* pFile, CDC* pDC /* = NULL */)
{
	// nueva función que lee el BMP del disco y crea una sección de DIB
	//    permite la modificación de mapas de bits de disco
	// 1. leer cabecera de archivo para obtener el tamaño de la cabecera de info + tabla de colores
	// 2. leer cabecera de info (para obtener el tamaño de la imagen) y la tabla de colores
	// 3. crear sección de DIB en función de los parámetros de la cabecera
	// 4. leer la imagen en memoria que asigna CreateDibSection
	Empty();
	int nCount, nSize;
	BITMAPFILEHEADER bmfh;
	try {
		nCount = pFile->Read((LPVOID) &bmfh, sizeof(BITMAPFILEHEADER));
		if(nCount != sizeof(BITMAPFILEHEADER)) {
			//throw new CException;
			throw new std::exception;

		}
		if(bmfh.bfType != 0x4d42) {
			//throw new CException;
			throw new std::exception;

		}
		nSize = bmfh.bfOffBits - sizeof(BITMAPFILEHEADER);
		m_lpBMIH = (LPBITMAPINFOHEADER) new char[nSize];
		m_nBmihAlloc = crtAlloc;
		m_nImageAlloc = noAlloc;
		nCount = pFile->Read(m_lpBMIH, nSize); // cabecera de info y tabla de colores
		if(m_lpBMIH->biCompression != BI_RGB) {
			//throw new CException;
			throw new std::exception;

		}
		ComputeMetrics();
		ComputePaletteSize(m_lpBMIH->biBitCount);
		MakePalette();
		UsePalette(pDC);
		m_hBitmap = ::CreateDIBSection(pDC->GetSafeHdc(), (LPBITMAPINFO) m_lpBMIH,
			DIB_RGB_COLORS,	(LPVOID*) &m_lpImage, NULL, 0);
		ASSERT(m_lpImage != NULL);
		nCount = pFile->Read(m_lpImage, m_dwSizeImage); // solo la imagen
	}
	catch(CException* pe) {
		AfxMessageBox(_T("Error de ReadSection"));
		pe->Delete();
		return FALSE;
	}
	return TRUE;
}
Exemple #8
0
BOOL CDib::CopyToMapFile(const TCHAR* strPathname)
{
	// copia el DIB en un nuevo archivo, libera los punteros antes 
	// si se ha utilizado previamente CreateSection, el HBITMAP será NULL (y no utilizable)
	BITMAPFILEHEADER bmfh;
	bmfh.bfType = 0x4d42;  // 'BM'
	bmfh.bfSize = m_dwSizeImage + sizeof(BITMAPINFOHEADER) +
			sizeof(RGBQUAD) * m_nColorTableEntries + sizeof(BITMAPFILEHEADER);
	// el significado de bfSize abierto a la interpretación
	bmfh.bfReserved1 = bmfh.bfReserved2 = 0;
	bmfh.bfOffBits = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) +
			sizeof(RGBQUAD) * m_nColorTableEntries;	
	HANDLE hFile = ::CreateFile(strPathname, GENERIC_WRITE | GENERIC_READ, 0, NULL,
		CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
	ASSERT(hFile != INVALID_HANDLE_VALUE);
	int nSize =  sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) +
				sizeof(RGBQUAD) * m_nColorTableEntries +  m_dwSizeImage;
	HANDLE hMap = ::CreateFileMapping(hFile, NULL, PAGE_READWRITE, 0, nSize, NULL);
	DWORD dwErr = ::GetLastError();
	ASSERT(hMap != NULL);
	LPVOID lpvFile = ::MapViewOfFile(hMap, FILE_MAP_WRITE, 0, 0, 0); // proyectar archivo completo
	ASSERT(lpvFile != NULL);
	LPBYTE lpbCurrent = (LPBYTE) lpvFile;
	memcpy(lpbCurrent, &bmfh, sizeof(BITMAPFILEHEADER)); // cabecera de archivo
	lpbCurrent += sizeof(BITMAPFILEHEADER);
	LPBITMAPINFOHEADER lpBMIH = (LPBITMAPINFOHEADER) lpbCurrent;
	memcpy(lpbCurrent, m_lpBMIH,
		sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * m_nColorTableEntries); // información
	lpbCurrent += sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * m_nColorTableEntries;
	memcpy(lpbCurrent, m_lpImage, m_dwSizeImage); // imagen de bits
	DWORD dwSizeImage = m_dwSizeImage;
	Empty();
	m_dwSizeImage = dwSizeImage;
	m_nBmihAlloc = m_nImageAlloc = noAlloc;
	m_lpBMIH = lpBMIH;
	m_lpImage = lpbCurrent;
	m_hFile = hFile;
	m_hMap = hMap;
	m_lpvFile = lpvFile;
	ComputePaletteSize(m_lpBMIH->biBitCount);
	ComputeMetrics();
	MakePalette();
	return TRUE;
}
Exemple #9
0
CDib::CDib(CSize size, int nBitCount, BOOL bInitialize)
{
	m_pntOrigo = CPoint(0,0);	//default origo
	m_hPalette = NULL;
	m_lpBMIH = NULL;
	m_lpImage = NULL;
	Empty();
	ComputePaletteSize(nBitCount);
	m_lpBMIH = (LPBITMAPINFOHEADER) new 
		char[sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*m_nColorTableEntries];
	m_lpBMIH->biSize = sizeof(BITMAPINFOHEADER);
	m_lpBMIH->biWidth = size.cx;
	m_lpBMIH->biHeight = size.cy;
	m_lpBMIH->biPlanes = 1;
	m_lpBMIH->biBitCount = nBitCount;
	m_lpBMIH->biCompression = BI_RGB;
	m_lpBMIH->biSizeImage = 0;
	m_lpBMIH->biXPelsPerMeter = 0;
	m_lpBMIH->biYPelsPerMeter = 0;
	m_lpBMIH->biClrUsed = m_nColorTableEntries;
	m_lpBMIH->biClrImportant = m_nColorTableEntries;
	ComputeMetrics();
	m_lpImage=(LPBYTE) new char[m_dwSizeImage];
	if (bInitialize) {
		//make default palette from def256pal_x constants
		int i;
		switch (nBitCount) {
			case 1:
				SetPaletteEntry(0,0);					//black
				SetPaletteEntry(1,RGB(255,255,255));	//white
				break;
			case 8:
				for (i=0; i<=255; i++) {
					SetPaletteEntry(i,RGB(def256pal_r[i],def256pal_g[i],def256pal_b[i]));
				}
				break;
			case 24:
				break;
		}
		memset(m_lpImage, 0, m_dwSizeImage); //initialize image bits to zero
	}
	MakePalette();
}
Exemple #10
0
/*************************************************************************
 *
 * \函数名称:
 *   AttachMemory()
 *
 * \输入参数:
 *   LPVOID	lpvMem			- 要关联的内存地址
 *   BOOL	bMustDelete		- 如果CDib类负责删除这个内存,标记为TRUE
 *					- 默认值为FALSE
 *   HGLOBAL	hGlobal			- 如果内存是通过Win32 GlobalAlloc得到的,
 *					- 则CDib对象必须保存该句柄,这样,以后
 *					- 可以释放句柄。这里假设bMustDelete设置为TRUE
 *
 * \返回值:
 *   BOOL					- 如果成功,则为TRUE 
 *
 * \说明:
 *   用内存中的DIB与已有的CDib对象关联。此内存可能是程序的资源,或者是可能是剪贴板
 *   或者OLE数据对象内存。内存可能已经由CRT堆栈用new运算符分配了,或者可能已经由
 *   Windows堆栈用GlobalAlloc分配了。
 *
 ************************************************************************
 */
BOOL CDib::AttachMemory(LPVOID lpvMem, BOOL bMustDelete, HGLOBAL hGlobal)
{
	// 首先释放已经分配的内存
	Empty();

	m_hGlobal = hGlobal;
	
	// bMustDelete为TRUE表示此CDib类分配的内存,负责删除
	// 否则的设置信息头分配状态为noAlloc
	if(bMustDelete == FALSE) {
		m_nBmihAlloc = noAlloc;
	}
	else {
		m_nBmihAlloc = ((hGlobal == NULL) ? crtAlloc : heapAlloc);
	}
	try {
		// 设置信息头指针
		m_lpBMIH = (LPBITMAPINFOHEADER) lpvMem;

		// 重新计算得到图象数据块的大小,并设置调色板的指针
		ComputeMetrics();

		// 计算调色板的尺寸
		ComputePaletteSize(m_lpBMIH->biBitCount);

		// 设置图象数据指针
		m_lpImage = (LPBYTE) m_lpvColorTable + sizeof(RGBQUAD) * m_nColorTableEntries;

		// 如果调色板存在的话,读取它,并创建一个Windows调色板,
		// 并将调色板的句柄存放在数据成员中
		MakePalette();
	}

	// 错误处理
	catch(CException* pe) {
		AfxMessageBox("AttachMemory error");
		pe->Delete();
		return FALSE;
	}

	// 返回
	return TRUE;
}
Exemple #11
0
CDib& CDib::operator=(const CDib& dib)
{
	ASSERT(this != &dib); //beware of dib=dib

	if (dib.m_lpBMIH) {
		Empty(); //clear left operand (dib we are coping to)
		int headerSize = sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*dib.m_nColorTableEntries;
		//copy header
		m_lpBMIH = (LPBITMAPINFOHEADER) new char[headerSize];
		memcpy(m_lpBMIH,dib.m_lpBMIH,headerSize);
		//copy member variables
		ComputeMetrics();
		ComputePaletteSize(dib.m_lpBMIH->biBitCount);
		MakePalette();
		m_pntOrigo = dib.m_pntOrigo;
		//copy bits
		m_lpImage = (LPBYTE)new char[dib.m_dwSizeImage];
		memcpy(m_lpImage,dib.m_lpImage,dib.m_dwSizeImage);
	}
	return *this;
}
Exemple #12
0
CDib::CDib(const CDib& dib,CRect rect)
//copy area of interest from dib
{
    int headerSize = sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*dib.m_nColorTableEntries;
    //copy header
    m_lpBMIH = (LPBITMAPINFOHEADER) new char[headerSize];
    memcpy(m_lpBMIH,dib.m_lpBMIH,headerSize);
	//correct size
	m_lpBMIH->biWidth=rect.Width();
	m_lpBMIH->biHeight=rect.Height();
	m_lpBMIH->biSizeImage = 0;
    //compute member variables
    ComputeMetrics();
    ComputePaletteSize(dib.m_lpBMIH->biBitCount);
    MakePalette();
	m_pntOrigo = CPoint(0,0);	//default origo
    //copy bits
    m_lpImage = (LPBYTE)new char[m_dwSizeImage];
	for(int y=rect.top; y<=rect.bottom; y++){
		for(int x=rect.left; x<=rect.right; x++){
			SetPixel(CPoint(x-rect.left,y-rect.top),dib.GetPixel(CPoint(x,y)));
		}
	}
}
Exemple #13
0
BOOL CDib::Read(CFile* pFile)
{
	// 1. leer cabecera de archivo para obtener el tamaño de la cabecera de info + tabla de colores
	// 2. leer cabecera de info (para obtener el tamaño de la imagen) y la tabla de colores
	// 3. leer la imagen
	// no se puede utilizar bfSize de la cabecera de info
	Empty();
	int nCount, nSize;
	BITMAPFILEHEADER bmfh;
	try {
		nCount = pFile->Read((LPVOID) &bmfh, sizeof(BITMAPFILEHEADER));
		if(nCount != sizeof(BITMAPFILEHEADER)) {
			//throw new CException;
			throw new std::exception;
		}
		if(bmfh.bfType != 0x4d42) {
			//throw new CException;
			throw new std::exception;
		}
		nSize = bmfh.bfOffBits - sizeof(BITMAPFILEHEADER);
		m_lpBMIH = (LPBITMAPINFOHEADER) new char[nSize];
		m_nBmihAlloc = m_nImageAlloc = crtAlloc;
		nCount = pFile->Read(m_lpBMIH, nSize); // cabecera de info y tabla de colores
		ComputeMetrics();
		ComputePaletteSize(m_lpBMIH->biBitCount);
		MakePalette();
		m_lpImage = (LPBYTE) new char[m_dwSizeImage];
		nCount = pFile->Read(m_lpImage, m_dwSizeImage); // sólo la imagen
	}
	catch(CException* pe) {
		AfxMessageBox(_T("Error de lectura"));
		pe->Delete();
		return FALSE;
	}
	return TRUE;
}
Exemple #14
0
BOOL CImageBMP::ReadFile(const CString& imageFileName)
{
  if (imageFileName != "")
	 filename = imageFileName;

  if (lpbi = DibOpenFile((char *)(const char *)filename))  {
		Width =  DibWidth(lpbi);
		Height = DibHeight(lpbi);
		Depth = DibBitCount(lpbi);
		RawImage = (ImagePointerType)DibPtr(lpbi);
		EffWidth = (long)(((long)Width*Depth + 31) / 32) * 4;
		HPALETTE palette;
		if (palette = MakePalette((const BITMAPINFO FAR*)lpbi, 0))
		{
		  imagePalette = new CImagePalette;
		  imagePalette->Attach(palette);
		  DibSetUsage(lpbi, (HPALETTE) (*imagePalette), CIMAGE_COLORS);
		  ColorType = (COLORTYPE_PALETTE | COLORTYPE_COLOR);
		} 

		return TRUE;
  }
  return FALSE;
}
Exemple #15
0
/*************************************************************************
 *
 * \函数名称:
 *   Compress()
 *
 * \输入参数:
 *   CDC*	pDC			- 设备上下文指针
 *   BOOL	bCompress		- TRUE对应于压缩的DIB,FALSE对应于不压缩的DIB
 *
 * \返回值:
 *   BOOL				- 如果成功,则返回TRUE
 *
 * \说明:
 *   该函数将DIB重新生成为压缩或者不压缩的DIB。在内部,它转换已有的DIB为DDB位图
 *   然后生成一个新的压缩或者不压缩的DIB。压缩仅为4bpp和8bpp的DIB所支持。不能
 *   压缩DIB段
 *
 ************************************************************************
 */
BOOL CDib::Compress(CDC* pDC, BOOL bCompress /* = TRUE */)
{
	// 判断是否为4bpp或者8bpp位图,否则,不进行压缩,返回FALSE
	if((m_lpBMIH->biBitCount != 4) && (m_lpBMIH->biBitCount != 8)) return FALSE;
	
	// 如果为DIB段,也不能支持压缩,返回FALSE
	if(m_hBitmap) return FALSE; 

	TRACE("Compress: original palette size = %d\n", m_nColorTableEntries); 
	
	// 获得设备上下文句柄
	HDC hdc = pDC->GetSafeHdc();

	// 将此DIB的调色板选入设备上下文,并保存以前的调色板句柄
	HPALETTE hOldPalette = ::SelectPalette(hdc, m_hPalette, FALSE);

	HBITMAP hBitmap;  

	// 创建一个DDB位图,如果不成功,则返回FALSE
	if((hBitmap = CreateBitmap(pDC)) == NULL) return FALSE;

	// 计算信息头加上调色板的大小尺寸,并给它们分配内存
	int nSize = sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * m_nColorTableEntries;
	LPBITMAPINFOHEADER lpBMIH = (LPBITMAPINFOHEADER) new char[nSize];

	// 将信息头和调色板拷贝到内存中
	memcpy(lpBMIH, m_lpBMIH, nSize);  // new header

	// 如果需要进行压缩,设置相应的信息,并创建压缩格式的DIB
	if(bCompress) {
		switch (lpBMIH->biBitCount) {
		case 4:
			lpBMIH->biCompression = BI_RLE4;
			break;
		case 8:
			lpBMIH->biCompression = BI_RLE8;
			break;
		default:
			ASSERT(FALSE);
		}

		// 设置位图数据指针为NULL,调用GetDIBits来得到压缩格式的DIB的尺寸
		// 如果不能创建DIB,则进行相应的错误处理。
		if(!::GetDIBits(pDC->GetSafeHdc(), hBitmap, 0, (UINT) lpBMIH->biHeight,
					NULL, (LPBITMAPINFO) lpBMIH, DIB_RGB_COLORS)) {
			AfxMessageBox("Unable to compress this DIB");			

			// 删除临时变量,并释放已分配内存
	 		::DeleteObject(hBitmap);
			delete [] lpBMIH;

			// 重新将以前的调色板选入,并返回FALSE
			::SelectPalette(hdc, hOldPalette, FALSE);
			return FALSE; 
		}

		// 如果位图数据为空,则进行相应的错误处理
		if (lpBMIH->biSizeImage == 0) {
			AfxMessageBox("Driver can't do compression");

			// 删除临时变量,并释放已分配内存
	 		::DeleteObject(hBitmap);
			delete [] lpBMIH;

			// 重新将以前的调色板选入,并返回FALSE
			::SelectPalette(hdc, hOldPalette, FALSE);
			return FALSE; 
		}

		// 将位图数据尺寸赋值给类的成员变量
		else {
			m_dwSizeImage = lpBMIH->biSizeImage;
		}
	}

	// 如果是解压缩,进行相应的处理
	else {

		// 设置压缩格式为不压缩
		lpBMIH->biCompression = BI_RGB; 

		// 根据位图的宽度和高度计算位图数据内存的大小		
		DWORD dwBytes = ((DWORD) lpBMIH->biWidth * lpBMIH->biBitCount) / 32;
		if(((DWORD) lpBMIH->biWidth * lpBMIH->biBitCount) % 32) {
			dwBytes++;
		}
		dwBytes *= 4;
		
		// 将得到位图数据的大小尺寸保存在类的成员变量中
		m_dwSizeImage = dwBytes * lpBMIH->biHeight; 

		// 将位图数据内存的大小赋值给临时的信息头中的相应的变量
		lpBMIH->biSizeImage = m_dwSizeImage;
	} 

	// 再次调用GetDIBits来生成DIB数据

	// 分配临时存放位图数据
	LPBYTE lpImage = (LPBYTE) new char[m_dwSizeImage];

	// 再次调用GetDIBits来生成DIB数据,注意此时位图数据指针不为空
	VERIFY(::GetDIBits(pDC->GetSafeHdc(), hBitmap, 0, (UINT) lpBMIH->biHeight,
    		lpImage, (LPBITMAPINFO) lpBMIH, DIB_RGB_COLORS));
	TRACE("dib successfully created - height = %d\n", lpBMIH->biHeight);
	
	// 压缩转换完毕,进行相应的其他处理

	// 删除临时的DDB位图
	::DeleteObject(hBitmap);

	// 释放原来的DIB分配的内存
	Empty();

	// 重新设置图象信息头和图象数据内存分配状态
	m_nBmihAlloc = m_nImageAlloc = crtAlloc;

	// 重新定位信息头和图象数据指针
	m_lpBMIH = lpBMIH;
	m_lpImage = lpImage;

	// 计算图象数据尺寸,并设置DIB中调色板的指针
	ComputeMetrics();

	// 计算DIB中调色板的尺寸
	ComputePaletteSize(m_lpBMIH->biBitCount);

	// 如果DIB中调色板存在的话,读取并创建一个Windows调色板
	MakePalette();

	// 恢复以前的调色板
	::SelectPalette(hdc, hOldPalette, FALSE);
	TRACE("Compress: new palette size = %d\n", m_nColorTableEntries); 

	// 返回
	return TRUE;
}
Exemple #16
0
static int ImageToGif(UCHAR **Image,int ImageWidth,int ImageHeight,
		char *GifFileName,int Paleta,int Laplas)
 {
    int	NumLevels=255,i;	/* Konwersja ekranu wirtualnego do postaci */
    GifColorType *ColorMap;     /* obrazu w formacie GIF */
    GifFileType *GifFile;	/* Oparte na bibliotece giflib */

    if(prn==ON)
      fprintf(stdout,"<<< TWORZENIE OBRAZU W FORMACIE GIF'A : %s >>>\n",GifFileName);

    if((GifFile=EGifOpenFileName(GifFileName,0))==NULL)
     {
       QuitGifError(GifFile);
       return -1;
     }

    if((ColorMap=(GifColorType *)malloc(NumLevels*sizeof(GifColorType)))==NULL)
     {
      fprintf(stderr,"Failed to allocate memory required, aborted.\n");
      QuitGifError(GifFile);
      return -1;
     }

    if(prn==ON)
      fprintf(stdout,"<<< GENERACJA PALETY BARW (%s) >>>\n",
	      ((Paleta==COLOR) ? "TERM" : 
	       ( (Paleta==INVERT_GRAY) ? "INVERT GARY" : "GRAY") ) );

    MakePalette(ColorMap,Paleta,Laplas);
    if(EGifPutScreenDesc(GifFile,ImageWidth,ImageHeight,8,0,
       8,ColorMap)==GIF_ERROR)
     {
       QuitGifError(GifFile);
       free((void *)ColorMap);
       return -1;
     }

    if(EGifPutImageDesc(GifFile,0,0,ImageWidth,ImageHeight,
       FALSE,8,NULL)==GIF_ERROR)
     {
       QuitGifError(GifFile);
       free((void *)ColorMap);
       return -1;
     }

    if(prn==ON)
      fprintf(stdout,"<<< KODOWANIE OBRAZU >>>\n");

    for(i=0 ; i<ImageHeight ; i++)
     if(EGifPutLine(GifFile,Image[i],ImageWidth)==GIF_ERROR)
      {
	QuitGifError(GifFile);
	free((void *)ColorMap);
	return -1;
     }

    if(EGifCloseFile(GifFile)==GIF_ERROR)
     {
       QuitGifError(GifFile);
       free((void *)ColorMap);
       return -1;
     }

    free((void *)ColorMap);
    return 0;
 }
Exemple #17
0
/*************************************************************************
 *
 * \函数名称:
 *   CopyToMapFile()
 *
 * \输入参数:
 *   const	char* strPathname		- 映射文件的路径名
 *
 * \返回值:
 *   BOOL					- 如果成功,则为TRUE 
 *
 * \说明:
 *   该函数可以创建一个新的内存映射文件,并将现有的CDib数据复制到该文件的内存
 *   释放以前的所有内存。并关闭现有的所有内存映射文件。实际上,直到新文件
 *   关闭的时候,才将这个数据写到磁盘,但是,当CDib对象被重复使用或被破坏
 *   时,也会发生写磁盘操作
 *
 ************************************************************************
 */
BOOL CDib::CopyToMapFile(const char* strPathname)
{
	BITMAPFILEHEADER bmfh;

	// 设置文件头信息
	bmfh.bfType	= 0x4d42;  
	bmfh.bfSize	= m_dwSizeImage + sizeof(BITMAPINFOHEADER) +
			sizeof(RGBQUAD) * m_nColorTableEntries + sizeof(BITMAPFILEHEADER);
	bmfh.bfReserved1= bmfh.bfReserved2 = 0;
	bmfh.bfOffBits	= sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) +
			sizeof(RGBQUAD) * m_nColorTableEntries;	
	
	// 创建接收数据的文件
	HANDLE hFile	= ::CreateFile(strPathname, GENERIC_WRITE | GENERIC_READ, 0, NULL,
		CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
	ASSERT(hFile != INVALID_HANDLE_VALUE);

	// 计算文件的大小尺寸
	int nSize	= sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) +
				sizeof(RGBQUAD) * m_nColorTableEntries +  m_dwSizeImage;

	// 创建内存映射文件对象
	HANDLE hMap = ::CreateFileMapping(hFile, NULL, PAGE_READWRITE, 0, nSize, NULL);
	DWORD dwErr = ::GetLastError();
	ASSERT(hMap != NULL);

	// 映射整个文件
	LPVOID lpvFile = ::MapViewOfFile(hMap, FILE_MAP_WRITE, 0, 0, 0); 
	ASSERT(lpvFile != NULL);

	// 临时文件指针
	LPBYTE lpbCurrent = (LPBYTE) lpvFile;

	// 拷贝文件头信息到内存映射文件中
	memcpy(lpbCurrent, &bmfh, sizeof(BITMAPFILEHEADER)); 

	// 计算信息头在文件中的地址,并拷贝信息头信息
	lpbCurrent += sizeof(BITMAPFILEHEADER);
	LPBITMAPINFOHEADER lpBMIH = (LPBITMAPINFOHEADER) lpbCurrent;
	memcpy(lpbCurrent, m_lpBMIH,
		sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * m_nColorTableEntries); 

	// 计算调色板在文件中的地址,并拷贝调色板
	lpbCurrent += sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * m_nColorTableEntries;
	memcpy(lpbCurrent, m_lpImage, m_dwSizeImage); 

	// 暂时存放图象数据尺寸变量
	DWORD dwSizeImage = m_dwSizeImage;

	// 释放一起分配的所有内存
	Empty();

	// 设置图象数据尺寸并设置内存分配状态
	m_dwSizeImage = dwSizeImage;
	m_nBmihAlloc  = m_nImageAlloc = noAlloc;

	// 信息头指针重新指向文件中的位置
	m_lpBMIH = lpBMIH;

	// 图象数据指针重新指向文件中的数据地址
	m_lpImage = lpbCurrent;

	// 设置文件句柄
	m_hFile = hFile;

	// 设置映射对象句柄
	m_hMap = hMap;

	// 设置映射文件指针
	m_lpvFile = lpvFile;

	// 重新计算得到调色板尺寸
	ComputePaletteSize(m_lpBMIH->biBitCount);

	// 重新计算图象数据块大小,并设置调色板指针
	ComputeMetrics();

	// 如果调色板存在的话,读取并创建一个Windows调色板
	MakePalette();

	// 返回
	return TRUE;
}
Exemple #18
0
BOOL CDib::Compress(CDC* pDC, BOOL bCompress /* = TRUE */)
{
	// 1. crea un mapa de bits GDI a partir de un DIB existente
	// 2. crea un nuevo DIB a partir del mapa de bits GDI con compresión
	// 3. libera el DIB original
	// 4. pone el nuevo DIB en el objeto
	if((m_lpBMIH->biBitCount != 4) && (m_lpBMIH->biBitCount != 8)) return FALSE;
		// sólo se admite la compresión para DIBs de 4 y 8 bpp
	if(m_hBitmap) return FALSE; // ¡no se puede comprimir una sección de DIB!
	TRACE("Compresión: tamaño original de la paleta = %d\n", m_nColorTableEntries); 
	HDC hdc = pDC->GetSafeHdc();
	HPALETTE hOldPalette = ::SelectPalette(hdc, m_hPalette, FALSE);
	HBITMAP hBitmap;  // temporal
	if((hBitmap = CreateBitmap(pDC)) == NULL) return FALSE;
	int nSize = sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * m_nColorTableEntries;
	LPBITMAPINFOHEADER lpBMIH = (LPBITMAPINFOHEADER) new char[nSize];
	memcpy(lpBMIH, m_lpBMIH, nSize);  // nueva cabecera
	if(bCompress) {
		switch (lpBMIH->biBitCount) {
		case 4:
			lpBMIH->biCompression = BI_RLE4;
			break;
		case 8:
			lpBMIH->biCompression = BI_RLE8;
			break;
		default:
			ASSERT(FALSE);
		}
		// llama a GetDIBits con un puntero de datos nulo para obtener el tamaño del DIB comprimido
		if(!::GetDIBits(pDC->GetSafeHdc(), hBitmap, 0, (UINT) lpBMIH->biHeight,
						NULL, (LPBITMAPINFO) lpBMIH, DIB_RGB_COLORS)) {
			AfxMessageBox(_T("No se ha podido comprimir este DIB"));
			// probablemente un problema con la tabla de colores
	 		::DeleteObject(hBitmap);
			delete [] lpBMIH;
			::SelectPalette(hdc, hOldPalette, FALSE);
			return FALSE; 
		}
		if (lpBMIH->biSizeImage == 0) {
			AfxMessageBox(_T("El controlador no puede realizar la compresión"));
	 		::DeleteObject(hBitmap);
			delete [] lpBMIH;
			::SelectPalette(hdc, hOldPalette, FALSE);
			return FALSE; 
		}
		else {
			m_dwSizeImage = lpBMIH->biSizeImage;
		}
	}
	else {
		lpBMIH->biCompression = BI_RGB; // descomprimir
		// descubrir el tamaño de la imagen a partir de la anchura y altura del mapa de bits
		DWORD dwBytes = ((DWORD) lpBMIH->biWidth * lpBMIH->biBitCount) / 32;
		if(((DWORD) lpBMIH->biWidth * lpBMIH->biBitCount) % 32) {
			dwBytes++;
		}
		dwBytes *= 4;
		m_dwSizeImage = dwBytes * lpBMIH->biHeight; // sin compresión
		lpBMIH->biSizeImage = m_dwSizeImage;
	} 
	// segunda llamada a GetDIBits para crear el DIB
	LPBYTE lpImage = (LPBYTE) new char[m_dwSizeImage];
	VERIFY(::GetDIBits(pDC->GetSafeHdc(), hBitmap, 0, (UINT) lpBMIH->biHeight,
    		lpImage, (LPBITMAPINFO) lpBMIH, DIB_RGB_COLORS));
    TRACE("dib creado con éxito - altura = %d\n", lpBMIH->biHeight);
	::DeleteObject(hBitmap);
	Empty();
	m_nBmihAlloc = m_nImageAlloc = crtAlloc;
	m_lpBMIH = lpBMIH;
	m_lpImage = lpImage;
	ComputeMetrics();
	ComputePaletteSize(m_lpBMIH->biBitCount);
	MakePalette();
	::SelectPalette(hdc, hOldPalette, FALSE);
	TRACE("Compresión: nuevo tamaño de la paleta = %d\n", m_nColorTableEntries); 
	return TRUE;
}
void ProcessImageLine(char buffer[])
{
	char *token;
	long whattodo;
	int i;
	char ImageName[200];
	char ParentID[32];
	char *img;
	BITMAPINFO bmi;
	long colors;
	WORD *Palette;
	WORD *Image16;
	char *Image8;
	long x,y,w,h,cx,cy,size;
	ImageList *ImageRecord;

	x=0;
	y=0;
	w=0;
	h=0;
	cx=0;
	cy=0;
	size=0;
	Image8=NULL;
	Image16=NULL;
	Palette=NULL;

	token=strtok(buffer," ,\t\n");
	if(!token)
		return;

	whattodo=FindTODO(token);
	if(!whattodo)
		return;

	if(whattodo == LOAD_PATH || whattodo == LOAD_PATH_TRANSPARENT)
	{
		token=strtok(NULL," ,\t\n");
		if(!token)
			return;
		if(token[0] != '"')
		{
			printf("Error in output filename (%s)\n",token);
			return;
		}
		token++;
		i=0;
		while(token[i] && token[i] != '"')
			i++;
		token[i]=0;
		strcpy(OutputFile,token);
	}

	token=strtok(NULL," ,\t\n");
	if(!token)
		return;
	strcpy(Label,token);

	token=strtok(NULL," ,\t\n");
	if(!token)
		return;

	if(whattodo == LOAD_IMAGE || whattodo == LOAD_DISCARD || whattodo == LOAD_TRANSPARENT || whattodo == LOAD_DISCARD_TRANSPARENT || whattodo == LOAD_PATH || whattodo == LOAD_PATH_TRANSPARENT)
	{
		if(token[0] != '"')
		{
			printf("Error in filename (%s)\n",token);
			return;
		}
		token++;
		i=0;
		while(token[i] && token[i] != '"')
			i++;
		token[i]=0;
		strcpy(ImageName,token);
		token=strtok(NULL," ,\t\n");
	}

	if(whattodo == LOAD_IMAGE || whattodo == LOAD_TRANSPARENT || whattodo == LOAD_DISCARD || whattodo == LOAD_DISCARD_TRANSPARENT || whattodo == LOAD_PATH || whattodo == LOAD_PATH_TRANSPARENT)
	{
		if(OriginalImage)
			delete OriginalImage;
		if(!LoadTarga16File(ImageName, &OriginalImage, &bmi ))
		{
			printf("Error loading (%s)... ignoring this line\n",ImageName);
			OriginalImage=NULL;
			return;
		}
		ImageW=bmi.bmiHeader.biWidth;
		ImageH=bmi.bmiHeader.biHeight;
		x=0;
		y=0;
		w=ImageW;
		h=ImageH;
	}

	if(!OriginalImage)
	{
		printf("No image to process\n");
		return;
	}

	if(whattodo == LOAD_IMAGE || whattodo == LOAD_DISCARD)
		UseColorKey=0;
	if(whattodo == LOAD_TRANSPARENT || whattodo == LOAD_DISCARD_TRANSPARENT || whattodo == LOAD_PATH_TRANSPARENT)
		UseColorKey=_RSC_COLORKEY_;

	if(whattodo == LOAD_IMAGE || whattodo == LOAD_TRANSPARENT || whattodo == LOAD_PATH || whattodo == LOAD_PATH_TRANSPARENT)
	{
		if(token)
		{
			cx=atol(token);

			token=strtok(NULL," ,\t\n");
			if(token)
				cy=atol(token);
		}
	}
	else if(whattodo != LOAD_DISCARD && whattodo != LOAD_DISCARD_TRANSPARENT)
	{
		i=0;
		while(token)
		{
			switch(i)
			{
				case 0:
					x=atol(token);
					break;
				case 1:
					y=atol(token);
					break;
				case 2:
					w=atol(token);
					break;
				case 3:
					h=atol(token);
					break;
				case 4:
					cx=atol(token);
					break;
				case 5:
					cy=atol(token);
					break;
			}
			i++;
			token=strtok(NULL," ,\t\n");
		}
		if(i < 4)
		{
			printf("Not enough parameters...\n");
			return;
		}
	}

	if(whattodo != LOAD_DISCARD && whattodo != LOAD_DISCARD_TRANSPARENT && whattodo != LOAD_PATH && whattodo != LOAD_PATH_TRANSPARENT)
	{
		if(cx == -1)
			cx=w/2;
		if(cy == -1)
			cy=h/2;
		ImageRecord=new ImageList;
		memset(ImageRecord,0,sizeof(ImageList));

		colors=BuildColorTable((WORD*)OriginalImage,x,y,w,h,ImageW,ImageH-1);
		if(colors && colors <= 256)
		{
			size=w*h;
			Palette=MakePalette(colors);
			Image8=(char *)ConvertTo8Bit((WORD*)OriginalImage,x,y,w,h,ImageW,ImageH-1);

			ImageRecord->Header.Type=_RSC_IS_IMAGE_;
			strcpy(ImageRecord->Header.ID,Label);
			ImageRecord->Header.flags=_RSC_8_BIT_ | UseColorKey;
			ImageRecord->Header.centerx=cx;
			ImageRecord->Header.centery=cy;
			ImageRecord->Header.w=w;
			ImageRecord->Header.h=h;
			ImageRecord->Header.imageoffset=0;
			ImageRecord->Header.palettesize=colors;
			ImageRecord->Header.paletteoffset=0;

			ImageRecord->ImageSize=size;
			ImageRecord->PaletteSize=colors*sizeof(WORD);
			ImageRecord->Image=Image8;
			ImageRecord->Palette=Palette;

			HeaderSize+=sizeof(ImageFmt);
			DataSize+=(ImageRecord->ImageSize+ImageRecord->PaletteSize);
		}
		else
		{
			size=w*h*sizeof(WORD);

			Image16=CopySubArea((WORD*)OriginalImage,x,y,w,h,ImageW,ImageH-1);

			ImageRecord->Header.Type=_RSC_IS_IMAGE_;
			strcpy(ImageRecord->Header.ID,Label);
			ImageRecord->Header.flags=_RSC_16_BIT_ | UseColorKey;
			ImageRecord->Header.centerx=cx;
			ImageRecord->Header.centery=cy;
			ImageRecord->Header.w=w;
			ImageRecord->Header.h=h;
			ImageRecord->Header.imageoffset=0;
			ImageRecord->Header.paletteoffset=0;

			ImageRecord->ImageSize=size;
			ImageRecord->PaletteSize=0;
			ImageRecord->Image=Image16;

			HeaderSize+=sizeof(ImageFmt);
			DataSize+=(ImageRecord->ImageSize);
		}
		ImageTable->Add(UniqueID++,ImageRecord);
	}
}
Exemple #20
0
/*************************************************************************
 *
 * \函数名称:
 *   ReadSection()
 *
 * \输入参数:
 *   CFile*	pFile			- 指向CFile对象的指针;对应的磁盘
 *					- 文件中包含DIB
 *   CDC*	pDC			- 设备上下文指针
 *
 * \返回值:
 *   BOOL				- 如果成功,则返回TRUE
 *
 * \说明:
 *   该函数从BMP文件中读取信息头,调用CreateDIBSection来分配图象内存,然后将
 *   图象从该文件读入刚才分配的内存。如果你想从磁盘读取一个DIB,然后通过调用
 *   GDI函数编辑它的话,可以使用该函数。你可以用Write或CopyToMapFile将DIB写
 *   回到磁盘
 *
 ************************************************************************
 */
BOOL CDib::ReadSection(CFile* pFile, CDC* pDC /* = NULL */)
{
	
	// 释放已经分配的内存
	Empty();

	// 临时变量
	int nCount, nSize;
	BITMAPFILEHEADER bmfh;

	// 从文件中读取数据
	try {
		// 读取文件头
		nCount = pFile->Read((LPVOID) &bmfh, sizeof(BITMAPFILEHEADER));
		if(nCount != sizeof(BITMAPFILEHEADER)) {
			throw new CException;
		}

		// 如果文件类型部位"BM",则返回并进行相应错误处理
		if(bmfh.bfType != 0x4d42) {
			throw new CException;
		}

		// 计算信息头加上调色板的大小,并分配相应的内存
		nSize = bmfh.bfOffBits - sizeof(BITMAPFILEHEADER);
		m_lpBMIH = (LPBITMAPINFOHEADER) new char[nSize];
		m_nBmihAlloc = crtAlloc;
		m_nImageAlloc = noAlloc;

		// 读取信息头和调色板
		nCount = pFile->Read(m_lpBMIH, nSize); 

		// 如果图象为压缩格式,则不进行后续处理
		if(m_lpBMIH->biCompression != BI_RGB) {
			throw new CException;
		}

		// 计算图象数据大小并设置调色板指针
		ComputeMetrics();

		// 计算调色板的表项数
		ComputePaletteSize(m_lpBMIH->biBitCount);

		// 如果DIB中存在调色板,则创建一个Windows调色板
		MakePalette();

		// 将CDib对象的逻辑调色板选入设备上下文		
		UsePalette(pDC);

		// 创建一个DIB段,并分配图象内存
		m_hBitmap = ::CreateDIBSection(pDC->GetSafeHdc(), (LPBITMAPINFO) m_lpBMIH,
			DIB_RGB_COLORS,	(LPVOID*) &m_lpImage, NULL, 0);
		ASSERT(m_lpImage != NULL);

		// 从文件中读取图象数据
		nCount = pFile->Read(m_lpImage, m_dwSizeImage); 
	}

	// 错误处理
	catch(CException* pe) {
		AfxMessageBox("ReadSection error");
		pe->Delete();
		return FALSE;
	}
	return TRUE;
}