크기가 약 400X300 픽셀 인 계층화 된 창 (WS_EX_LAYERED 포함)을 만들었습니다.
UpdateLayeredWindow을 사용하여 창을 그릴 때 모든 것이 효과적입니다.계층화 된 창에서 HBITMAP 가져 오기 - 잘못된 데이터
문제는 드로잉 후 창 HBITMAP을 가져올 수 없다는 것입니다. 창 HDC를 통해 HBITMAP을 가져 오려고하면 전체 바탕 화면 크기 (1920X1080 px insted of 400X300 px) 인 빈 (검은 색) 비트 맵이 나타납니다.
계층화 된 창의 HDC \ HBITMAP을 가져 오는 것이 가능한지 아무도 알지 못합니까?
코드 샘플
여기에 내가 계층화 된 창을 그리는 방법에 대한 코드입니다 (다시는, 잘 작동) : 여기
void MyLayeredWindow::DrawLayered() const
{
RECT rcWindow;
GetWindowRect(rcWindow);
int nWidth = abs(rcWindow.right - rcWindow.left);
int nHeight = abs(rcWindow.bottom - rcWindow.top);
// Create 32Bit bitmap to apply transparency
// (have to set negative height because if not the (0,0) point would be the bottom left instead of top left)
VOID *ppvBits = NULL;
BITMAPINFO BitmapInfo = {0};
BitmapInfo.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
BitmapInfo.bmiHeader.biWidth = nWidth;
BitmapInfo.bmiHeader.biHeight = -nHeight;
BitmapInfo.bmiHeader.biPlanes = 1;
BitmapInfo.bmiHeader.biBitCount = 32;
BitmapInfo.bmiHeader.biCompression = BI_RGB;
// Copy view buffer to a temp DC and bitmap
HDC hDcTemp = ::CreateCompatibleDC(NULL);
assert(hDcTemp);
HBITMAP hBitmapTemp = ::CreateDIBSection(hDcTemp, &BitmapInfo, DIB_RGB_COLORS, &ppvBits, NULL, 0);
assert(hBitmapTemp && hBitmapTemp!=(HBITMAP)ERROR_INVALID_PARAMETER)
::SelectObject(hDcTemp, hBitmapTemp);
// Darwing the window's conent here
// ....
// ....
// Call UpdateLayeredWindow
BLENDFUNCTION blend = {0};
blend.BlendOp = AC_SRC_OVER;
blend.SourceConstantAlpha = 190;
blend.AlphaFormat = AC_SRC_ALPHA;
SIZE sizeWnd = {0};
sizeWnd.cx = nWidth;
sizeWnd.cy = nHeight;
POINT ptPos = {0};
ptPos.x = rcWindow.left;
ptPos.y = rcWindow.top;
POINT ptSrc = {0,0};
::UpdateLayeredWindow(m_hWnd, NULL, &ptPos, &sizeWnd, hDcTemp, &ptSrc, 0, &blend, ULW_ALPHA);
if(hDcTemp)
::DeleteDC(hDcTemp);
if(hBitmapTemp)
::DeleteObject(hBitmapTemp);
}
내가 윈도우의 비트 맵을 캡처에 저장하는 방법의 코드입니다 파일 : (
주의 사항 :이 같은 계산기와 같은 "정상"창, 작품)
bool MyLayeredWindow::SaveBitmapFile(__in const HWND& hWnd, __in const wstring& sFileName)
{
HDC hDC = ::GetDC(hWnd);
// get bitmap of DC
HBITMAP hBmp = (HBITMAP)::GetCurrentObject(hDC, OBJ_BITMAP);
// get info of bitmap
BITMAPINFO stBmpInfo;
stBmpInfo.bmiHeader.biSize = sizeof(stBmpInfo.bmiHeader);
stBmpInfo.bmiHeader.biBitCount = 0;
GetDIBits(hDC, hBmp, 0, 0, NULL, &stBmpInfo, DIB_RGB_COLORS);
// init info size
ULONG iBmpInfoSize;
switch(stBmpInfo.bmiHeader.biBitCount)
{
case 24:
iBmpInfoSize = sizeof(BITMAPINFOHEADER);
break;
case 16:
case 32:
iBmpInfoSize = sizeof(BITMAPINFOHEADER)+sizeof(DWORD)*3;
break;
default:
iBmpInfoSize = sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * (1 << stBmpInfo.bmiHeader.biBitCount);
break;
}
// copy header
PBITMAPINFO pstBmpInfo = NULL;
if(iBmpInfoSize != sizeof(BITMAPINFOHEADER))
{
pstBmpInfo = (PBITMAPINFO)GlobalAlloc(GMEM_FIXED | GMEM_ZEROINIT, iBmpInfoSize);
PBYTE pbtBmpInfoDest = (PBYTE)pstBmpInfo;
PBYTE pbtBmpInfoSrc = (PBYTE)&stBmpInfo;
ULONG iSizeTmp = sizeof(BITMAPINFOHEADER);
while(iSizeTmp--)
*((pbtBmpInfoDest)++) = *((pbtBmpInfoSrc)++);
}
// create file
HANDLE hFile = CreateFile(sFileName.c_str(), GENERIC_WRITE, 0 , NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_ARCHIVE, NULL);
// init bmp file header
BITMAPFILEHEADER stBmpFileHder = {0};
stBmpFileHder.bfType = 0x4D42; // 'BM'
stBmpFileHder.bfSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + iBmpInfoSize + pstBmpInfo->bmiHeader.biSizeImage;
stBmpFileHder.bfReserved1 = 0;
stBmpFileHder.bfReserved2 = 0;
stBmpFileHder.bfOffBits = sizeof(BITMAPFILEHEADER) + iBmpInfoSize;
// write header to file
DWORD dRet;
WriteFile(hFile, (LPCVOID)&stBmpFileHder, sizeof(BITMAPFILEHEADER), &dRet, NULL);
// allocate size for rest of bmp (body)
PBYTE pBits = (PBYTE)GlobalAlloc(GMEM_FIXED | GMEM_ZEROINIT, stBmpInfo.bmiHeader.biSizeImage);
// get bmp bits
HBITMAP hBmpOld;
HBITMAP hTmpBmp = CreateCompatibleBitmap(hDC, pstBmpInfo->bmiHeader.biWidth, pstBmpInfo->bmiHeader.biHeight);
hBmpOld = (HBITMAP)SelectObject(hDC, hTmpBmp);
GetDIBits(hDC, hBmp, 0, pstBmpInfo->bmiHeader.biHeight, (LPSTR)pBits, pstBmpInfo, DIB_RGB_COLORS);
// write bmp info
WriteFile(hFile, (LPCVOID)pstBmpInfo, iBmpInfoSize, &dRet, NULL);
// write bmp bits
WriteFile(hFile, (LPCVOID)pBits, pstBmpInfo->bmiHeader.biSizeImage, &dRet, NULL);
// release handles and free memory
SelectObject(hDC, hBmpOld);
DeleteObject(hTmpBmp);
CloseHandle(hFile);
GlobalFree(pstBmpInfo);
GlobalFree(pBits);
ReleaseDC(hWnd, hDC);
return true;
}
감사합니다.
접근 방법은 일반적으로 잘못되어 우연히 만 작동 할 수 있습니다. 윈도우에 비트 맵이 없으면 BitBlt 또는 PrintWindow를 사용해야합니다. 계층화 된 창에 CAPTURE_BLT 옵션을 사용하십시오. http://msdn.microsoft.com/en-us/library/windows/desktop/dd183402%28v=vs.85%29.aspx –
BitBlt 및 PrintWindow가 내 계층화 된 창에 적용되지 않는 것 같습니다. 빈 (검은 색/투명) DC를 반환합니다. –