www.pudn.com > bitmappaint.rar > Wzdbtmap.cpp
// WzdBtmap.cpp : implementation of the CWzdBitmap class
//
#include "stdafx.h"
#include "wzdBtmap.h"
#include "resource.h"
/////////////////////////////////////////////////////////////////////////////
// CWzdBitmap
IMPLEMENT_DYNAMIC(CWzdBitmap, CBitmap)
CWzdBitmap::CWzdBitmap()
{
m_Width=0;
m_Height=0;
}
CWzdBitmap::~CWzdBitmap()
{
}
void CWzdBitmap::CreateBitmapEx(CSize size)
{
bitmapSize=size;
dcScreen.Attach(::GetDC(NULL));
// create our bitmap in memory
dcMem.CreateCompatibleDC(&dcScreen);
CreateCompatibleBitmap(&dcScreen, size.cx, size.cy);
dcMem.SelectObject(this);
}
HANDLE CWzdBitmap::CreateDIB(int *pbmData)
{
///////////////////////////////////////////
// create DIB header from our BITMAP header
///////////////////////////////////////////
BITMAPINFOHEADER bi;
memset(&bi, 0, sizeof(bi));
bi.biSize = sizeof(BITMAPINFOHEADER);
bi.biPlanes = 1;
bi.biCompression = BI_RGB;
// get and store dimensions of bitmap
BITMAP bm;
GetObject(sizeof(bm),(LPSTR)&bm);
bi.biWidth = bm.bmWidth;
bi.biHeight = bm.bmHeight;
// get number of bits required per pixel
int bits = bm.bmPlanes * bm.bmBitsPixel;
if (bits <= 1)
bi.biBitCount = 1;
else if (bits <= 4)
bi.biBitCount = 4;
else if (bits <= 8)
bi.biBitCount = 8;
else
bi.biBitCount = 24;
// calculate color table size
int biColorSize=0;
if (bi.biBitCount!=24) biColorSize=(1<biSize + biColorSize, (LPBITMAPINFO)lpbi,
DIB_RGB_COLORS);
// clean up
::GlobalUnlock(hDIB);
dc.SelectPalette(pPal,FALSE);
dc.RealizePalette();
// return handle to the DIB
return hDIB;
}
void CWzdBitmap::SaveBitmap(CString sFile)
{
// create a DIB bitmap
int bmData;
HANDLE hDIB = CreateDIB(&bmData);
// get a memory pointer to it
LPBYTE lpBitmap=(LPBYTE)::GlobalLock(hDIB);
int bmSize=::GlobalSize(hDIB);
// create file
CFile file;
file.Open(sFile, CFile::modeCreate|CFile::modeWrite);
// write the bitmap header
BITMAPFILEHEADER bmfh;
bmfh.bfType='MB'; //(actually 'BM' for bitmap)
bmfh.bfSize=sizeof(BITMAPFILEHEADER)+bmSize;
bmfh.bfReserved1=0;
bmfh.bfReserved2=0;
bmfh.bfOffBits=bmData;
file.Write(&bmfh,sizeof(BITMAPFILEHEADER));
// write the bitmap body
file.Write(lpBitmap,bmSize);
// cleanup
file.Close();
::GlobalUnlock(hDIB);
::GlobalFree(hDIB);
}
CDC* CWzdBitmap::GetDC()
{
return &dcMem;
}
void CWzdBitmap::PrepareBitmap()
{
int nColors=(1<<(dcScreen.GetDeviceCaps(BITSPIXEL)*
dcScreen.GetDeviceCaps(PLANES)));
LOGPALETTE *pLogPal=(LOGPALETTE*)new BYTE[
sizeof(LOGPALETTE)+(nColors*sizeof(PALETTEENTRY))];
pLogPal->palVersion=0x300;
pLogPal->palNumEntries=nColors;
::GetSystemPaletteEntries(dcScreen.m_hDC,0,nColors,
(LPPALETTEENTRY)(pLogPal->palPalEntry));
m_pPalette = new CPalette;
m_pPalette->CreatePalette(pLogPal);
delete []pLogPal;
// delete and release device contexts
dcMem.DeleteDC();
::ReleaseDC(NULL, dcScreen.Detach());
m_Width=bitmapSize.cx;
m_Height=bitmapSize.cy;
}
void CWzdBitmap::Print(CDC* pDC)
{
// get DIB version of bitmap
int bmData;
HANDLE hDIB = CreateDIB(&bmData);
// get memory pointers to the DIB's header and data bits
LPBITMAPINFOHEADER lpDIBHdr = (LPBITMAPINFOHEADER)::GlobalLock(hDIB);
LPSTR lpDIBBits = (LPSTR)lpDIBHdr+bmData;
// stretch bitmap to fill printed page with 1/4 inch borders
//int cxBorder=pDC->GetDeviceCaps(LOGPIXELSX)/4;
//int cyBorder=pDC->GetDeviceCaps(LOGPIXELSY)/4;
//int cxPage = pDC->GetDeviceCaps(HORZRES) - (cxBorder*2);
//int cyPage=(int)(((double)cxPage/(double)m_Width) * (double)m_Height);
// stretch the bitmap for the best fit on the printed page
pDC->SetStretchBltMode(COLORONCOLOR);
CRect rect(0,0,m_Width,m_Height);
pDC->DPtoLP(&rect);
::StretchDIBits(pDC->m_hDC,
//cxBorder,cyBorder,cxPage,cyPage, // destination dimensions
//0,0,cxPage,cyPage,
0,0,m_BitRect.Width(),-m_BitRect.Height(),
0,0,m_Width,m_Height, // source bitmap dimensions (use all of bitmap)
lpDIBBits, // bitmap picture data
(LPBITMAPINFO)lpDIBHdr, // bitmap header info
DIB_RGB_COLORS, // specify color table has RGB values
SRCCOPY // simple source to destination copy
);
// cleanup
::GlobalUnlock(hDIB);
::GlobalFree(hDIB);
return;
}