?? bmpproc.cpp
字號:
* # 如果本身類中不存在位圖,函數將返回FALSE
*
************************************************************************/
BOOL CBmpProc::CopyTranCenter(CBmpProc& souBmp,
CRect* crArea,
COLORREF crColour,
int mode)
{
if (!IsValid())
return FALSE;
ASSERT(m_pInfo);
ASSERT(m_pInfo->bmiHeader.biSize == sizeof(BITMAPINFOHEADER));
if (!souBmp.IsValid())
return FALSE;
ASSERT(souBmp.m_pInfo);
ASSERT(souBmp.m_pInfo->bmiHeader.biSize == sizeof(BITMAPINFOHEADER));
CRect rect(Rect());
if (crArea)
rect = *crArea;
// 矩形坐標規范化
rect.NormalizeRect();
if ((rect.Width()==0)||(rect.Height()==0))
return FALSE;
// 復制源圖
CDC compDC;
CBitmap *pOldBmp;
// 創建與當前顯示設備兼容的內存設備描述表
compDC.CreateCompatibleDC(NULL);
pOldBmp = compDC.SelectObject((CBitmap*)this);
// 復制指定尺寸的源位圖到目標位圖
souBmp.DrawTranCenter(compDC, &rect, crColour, mode);
compDC.SelectObject(pOldBmp);
return TRUE;
}
/*************************************************************************
*
* CopyTranTile()
*
* 參數說明:
*
* CBmpProc& souBmp - 源位圖目標
* CRect* crArea - 平鋪的范圍(缺省值為NULL)
* COLORREF crColour - 要濾掉或保留的顏色(缺省值是白色)
* int mode - 如果是0則將不拷貝指定的顏色,如果是1則保留指定
* 的顏色(缺省值為0)
*
* 返回值:
*
* BOOL - 如果成功返回TRUE,否則返回FALSE
*
* 描述:
*
* 將源位圖透明的平鋪到本類的指定矩形中
*
* 如果入口參數crArea設為NULL,則平鋪矩形等于本身類中圖像的尺寸。
* 該函數不會拉伸或壓縮源位圖圖像。
*
* 注:# 本身類中原來必需已存在位圖,且調用之后的位圖不會被刪除
* # 如果源位圖類是空的,則返回FALSE
* # 如果本身類中不存在位圖,函數將返回FALSE
*
************************************************************************/
BOOL CBmpProc::CopyTranTile(CBmpProc& souBmp,
CRect* crArea,
COLORREF crColour,
int mode)
{
// 運行環境檢測
if (!IsValid())
return FALSE;
ASSERT(m_pInfo);
ASSERT(m_pInfo->bmiHeader.biSize == sizeof(BITMAPINFOHEADER));
if (!souBmp.IsValid())
return FALSE;
ASSERT(souBmp.m_pInfo);
ASSERT(souBmp.m_pInfo->bmiHeader.biSize == sizeof(BITMAPINFOHEADER));
// 缺省情況下鋪設范圍就是本身位圖的尺寸
CRect rect(Rect());
if (crArea)
rect = *crArea; // 另外指定尺寸
// 矩形坐標規范化
rect.NormalizeRect();
if ((rect.Width()==0)||(rect.Height()==0))
return FALSE;
// 復制源圖
CDC compDC;
CBitmap *pOldBmp;
// 創建與當前顯示設備兼容的內存設備描述表
compDC.CreateCompatibleDC(NULL);
pOldBmp = compDC.SelectObject((CBitmap*)this);
// 復制指定尺寸的源位圖到目標位圖
souBmp.DrawTranTile(compDC, &rect, crColour, mode);
compDC.SelectObject(pOldBmp);
return TRUE;
}
/*************************************************************************
*
* LoadFromClipboard()
*
* 參數說明:無
*
*
* 返回值:
*
* BOOL - 如果成功返回TRUE,否則返回FALSE
*
* 描述:
*
* 讀取剪貼板中的DIB位圖到類中
*
* 如果函數成功,則類中原來的位圖(如果有的話)將被刪除
*
************************************************************************/
BOOL CBmpProc::LoadFromClipboard()
{
// 檢查剪貼板的有效性
if (!PasteAvailable())
return FALSE;
// 打開剪貼板
if (::OpenClipboard(NULL))
{
// 獲取剪貼板中的DIB數據
HANDLE h = ::GetClipboardData(CF_DIB);
if (!h)
{
CloseClipboard();
return FALSE;
}
LPSTR lpDIB = (LPSTR)CreateMemoryBlockFromHandle(h);
if (!lpDIB)
{ // 讀入的剪貼板數據句柄不需要釋放,系統會自動釋放
CloseClipboard();
return FALSE;
}
CloseClipboard();
// 檢查DIB信息塊的有效性
if (*((DWORD*)lpDIB) != sizeof(BITMAPINFOHEADER))
{
::free((void*)lpDIB);
return FALSE;
}
// 復制信息塊
ASSERT(CalculateDIBInfoSize((LPBITMAPINFOHEADER)lpDIB) >= sizeof(BITMAPINFOHEADER));
LPBITMAPINFO pInfo = (LPBITMAPINFO)CreateMemoryBlockFromAddress(
(LPVOID)lpDIB, CalculateDIBInfoSize((LPBITMAPINFOHEADER)lpDIB));
if (!pInfo)
{
::free((void*)lpDIB);
return FALSE;
}
// 計算位數據首地址
LPSTR pBits = (LPSTR)FindDIBBits(lpDIB);
ASSERT(pBits);
// 制作DDB位圖
HBITMAP hBmp;
HWND hWnd = ::GetDesktopWindow();
ASSERT(hWnd);
HDC hDC = ::GetDC(hWnd);
hBmp = ::CreateDIBitmap(hDC, // 創建DDB位圖。(將DIB位數據
(BITMAPINFOHEADER *)pInfo, // 轉換為DDB位數據)
CBM_INIT, pBits,
(BITMAPINFO *)pInfo,
DIB_RGB_COLORS);
::ReleaseDC(hWnd, hDC);
// 創建完邏輯位圖后,從剪貼板中讀取的數據已無用,釋放
::free((void*)lpDIB);
if (hBmp) // 成功
{
// 刪除原來的圖像,并且設置新的位圖
if (!ClearAndSetData(IT_CLIP,0,(LPCTSTR)"",pInfo,hBmp))
{
::free((void*)pInfo);
::DeleteObject(hBmp);
return FALSE;
}
return TRUE;
}
else // 失敗
{
::free((void*)pInfo);
return FALSE;
}
}
return FALSE;
}
/*************************************************************************
*
* LoadFromFile()
*
* 參數說明:
*
* LPCTSTR lpszPathName - 待讀入的位圖文件名稱(路徑)
*
* 返回值:
*
* BOOL - 如果成功返回TRUE,否則返回FALSE
*
* 描述:
*
* 讀取指定位圖文件到類中
*
* 如果函數成功,則類中原來的位圖(如果有的話)將被刪除
* 如果入口參數指定的文件不存在或不是一個位圖文件,則函數返回FALSE
*
************************************************************************/
BOOL CBmpProc::LoadFromFile(LPCTSTR lpszPathName)
{
CFile file;
LPBITMAPINFO lpbi;
LPSTR pBits;
HBITMAP hBmp;
if (!file.Open(lpszPathName, CFile::modeRead | CFile::shareDenyWrite))
return FALSE;
// 判斷文件是否是有效的BMP文件
if (IsValidBmpFile(file) == FALSE)
{
file.Close();
return FALSE;
}
// 讀取BMP文件信息
{
file.Close();
return FALSE;
}
// 本類不支持壓縮位圖,所以如果是壓縮位圖則返回FALSE
if ((lpbi->bmiHeader.biCompression==BI_RLE4)||(lpbi->bmiHeader.biCompression==BI_RLE8))
{
::free((void*)lpbi);
file.Close();
return FALSE;
}
// 提取BMP位數據
if ((pBits=GetBmpFileBits(file)) == NULL)
{
::free((void*)lpbi);
file.Close();
return FALSE;
}
HWND hWnd = ::GetDesktopWindow();
ASSERT(hWnd);
HDC hDC = ::GetDC(hWnd);
hBmp = ::CreateDIBitmap(hDC, // 創建DDB位圖。(將DIB位數據
(BITMAPINFOHEADER *)lpbi, // 轉換為DDB位數據)
CBM_INIT, pBits,
(BITMAPINFO *)lpbi,
DIB_RGB_COLORS);
::ReleaseDC(hWnd, hDC);
// 創建完邏輯位圖后,從文件中讀取的位數據已無用,釋放
::free((void*)pBits);
file.Close();
if (hBmp) // 成功
{
// 刪除原來的圖像,并且設置新的位圖
if (!ClearAndSetData(IT_DISKFILE,0,lpszPathName,lpbi,hBmp))
{
::free((void*)lpbi);
::DeleteObject(hBmp);
return FALSE;
}
return TRUE;
}
else // 失敗
{
::free((void*)lpbi);
return FALSE;
}
}
/*************************************************************************
*
* LoadFromResourceID()
*
* 參數說明:
*
* UINT uID - 待讀入的位圖資源名稱(標識值)
* HINSTANCE hInstance - 位圖資源所在實例的句柄(如果它被設為NULL,則
* 函數將該值設為當前應用程序進程)
*
* 返回值:
*
* BOOL - 如果成功返回TRUE,否則返回FALSE
*
* 描述:
*
* 讀取指定位圖資源到類中
*
* 如果函數成功,則類中原來的位圖(如果有的話)將被刪除
*
************************************************************************/
BOOL CBmpProc::LoadFromResourceID(UINT uID, HINSTANCE hInst)
{
return LoadFromResourceName((LPCTSTR)MAKEINTRESOURCE(uID), hInst);
}
/*************************************************************************
*
* LoadFromResourceName()
*
* 參數說明:
*
* LPCTSTR lpResourceName - 待讀入的位圖資源名稱(字符串)
* HINSTANCE hInstance - 位圖資源所在實例的句柄(如果它被設為NULL,則
* 函數將該值設為當前應用程序進程)
*
* 返回值:
*
* BOOL - 如果成功返回TRUE,否則返回FALSE
*
* 描述:
*
* 讀取指定位圖資源到類中
*
* 如果函數成功,則類中原來的位圖(如果有的話)將被刪除
*
************************************************************************/
BOOL CBmpProc::LoadFromResourceName(LPCTSTR lpResourceName,
HINSTANCE hInstance)
{
HINSTANCE hInst = hInstance;
HBITMAP hBmp = NULL;
//如果入口參數hInstance是NULL,則函數將用當前應用程序進程的實例句柄
if (hInst == NULL)
hInst = ::AfxGetResourceHandle();
ASSERT(hInst);
HRSRC hSrc = ::FindResource(hInst, lpResourceName, RT_BITMAP);
BOOL bSuccess = FALSE;
if (!hSrc)
return bSuccess;
// 由LoadResource()函數讀入的資源目標不需要顯示的刪除它,Windows
// 系統會自動刪除。LockResource()鎖定的資源目標也不需要顯示的解鎖
HGLOBAL hResData = LoadResource(hInst, hSrc);
if (hResData)
{
LPVOID lpResData = LockResource(hResData);
if (lpResData)
{
// 如果是有效的DIB資源,則資源的首位應該是BITMAPINFOHEADER
// 結構
ASSERT(*((DWORD*)lpResData) == sizeof(BITMAPINFOHEADER));
LPSTR pBits = FindDIBBits((LPSTR)lpResData);
ASSERT(pBits > (LPSTR)lpResData);
HWND hWnd = ::GetDesktopWindow();
ASSERT(hWnd);
HDC hDC = ::GetDC(hWnd);
hBmp = CreateDIBitmap(hDC, // 創建DDB位圖。(將DIB位數據
(BITMAPINFOHEADER *)lpResData, // 轉換為DDB位數據)
CBM_INIT, pBits,
(BITMAPINFO *)lpResData,
DIB_RGB_COLORS);
::ReleaseDC(hWnd, hDC);
if (hBmp) // 成功
{
DWORD dwInfoSize = (DWORD)((LPSTR)pBits-(LPSTR)lpResData);
ASSERT(dwInfoSize > (DWORD)(sizeof(BITMAPFILEHEADER)));
LPBITMAPINFO lpbi = (LPBITMAPINFO)CreateMemoryBlockFromAddress(
(LPVOID)NULL, dwInfoSize);
if (lpbi)
{
// 復制位圖信息塊,因為lpResData所指的內存不是運行時態庫
// 函數分配的內存塊,所以未用CreateMemoryBlockFromAddress()
// 的復制功能
::memcpy((void*)lpbi, (const void*)lpResData, dwInfoSize);
}
else
{
::DeleteObject(hBmp);
return FALSE;
}
if ((((DWORD)lpResourceName)>>16) == 0)
{// 如果指定資源時使用的是標識,則串指針的高16位是0
// 刪除原來的圖像,并且設置新的位圖
if (!ClearAndSetData(IT_RESOURCE,(DWORD)lpResourceName,(LPCTSTR)"",lpbi,hBmp))
{
::free((void*)lpbi);
::DeleteObject(hBmp);
return FALSE;
}
}
else
{
// 刪除原來的圖像,并且設置新的位圖
if (!ClearAndSetData(IT_RESOURCE,0, lpResourceName,lpbi,hBmp))
{
::free((void*)lpbi);
::DeleteObject(hBmp);
return FALSE;
}
}
bSuccess = TRUE;
}
}
}
return bSuccess;
}
/*************************************************************************
*
* LoadFromObject()
*
* 參數說明:
*
* CBmpProc& souBmp - 源位圖目標
* CRect *pSouRect - 復制矩形
*
* 返回值:
*
* BOOL - 如果成功返回TRUE,否則返回FALSE
*
* 描述:
*
* 讀取源位圖目標中指定區域(矩形)的圖像到類中
*
* 如果入口參數pSouRect設為NULL,則復制源目標的整個位圖
* 入口參數pSouRect必須是一個正常的矩形坐標數據(即
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -