Как скопировать такой растр в DC?

Я пишу программу удаленного управления с графическим интерфейсом.
Вот часть кода сервера:

HDC desktopHdc = GetDC(NULL);
int bm_x = GetDeviceCaps(desktopHdc, HORZRES);
int bm_y = GetDeviceCaps(desktopHdc, VERTRES);
DWORD bmSize = ((bm_x * 32 + 31) / 32) * bm_y * 4;
HDC memHdc = CreateCompatibleDC(desktopHdc);
HBITMAP bitmap = CreateCompatibleBitmap(desktopHdc, bm_x, bm_y);

while(TRUE)
{
SelectObject(memHdc, (HGDIOBJ)bitmap);
HANDLE hDIB = GlobalAlloc(GHND, bmSize);
char* bmbits = (char*)GlobalLock(hDIB);
BitBlt(memHdc, 0, 0, bm_x, bm_y, desktopHdc, 0, 0, SRCCOPY);
GetBitmapBits(bitmap, bmSize, bmbits);

int bytes = send(secondarySocket, bmbits, bmSize, 0);
if(bytes == 0 || bytes == -1)
{
MessageBox(NULL, "disconnected", "", 0);
break;
}

GlobalUnlock(hDIB);
GlobalFree(hDIB);
Sleep(1000);
}

И вот некоторый клиентский код:

HDC windowHdc = GetDC(hwnd);
HDC memHdc = CreateCompatibleDC(windowHdc);
// bm_x and bm_y are sent by the server and received by the client
DWORD bmSize = ((bm_x * 32 + 31) / 32) * bm_y * 4;
while(TRUE)
{
HANDLE hDIB = GlobalAlloc(GHND, bmSize);
char* buf = (char*)GlobalLock(hDIB);
int bytes = recv(mainSocket, buf, bmSize, 0);
if(bytes == 0 || bytes == -1)
{
MessageBox(NULL, "disconnected", "", 0);
break;
}
else
{
buf[bytes] = '\0';

HBITMAP bmp = CreateCompatibleBitmap(memHdc, bm_x, bm_y);

SetBitmapBits(bmp, bmSize, buf);

SelectObject(memHdc, bmp);
BitBlt(windowHdc, 0, 0, bm_x, bm_y, memHdc, 0, 0, SRCCOPY); // should copy received bitmap to the window DC
}

GlobalUnlock(hDIB);
GlobalFree(hDIB);
}

Я получаю весь буфер в клиенте правильно. Я делаю растровое изображение из этого. И тогда я просто не могу скопировать его в окно DC — ничего не появляется. Как я могу это сделать?

РЕДАКТИРОВАТЬ

Вот мой новый код:

DWORD thServerSend(LPVOID param)
{
HDC memHdc = CreateCompatibleDC(desktopHdc);
HBITMAP bitmap;

while(TRUE)
{
BITMAPINFO bmi;
ZeroMemory(&bmi,sizeof(BITMAPINFO));
bmi.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
bmi.bmiHeader.biWidth=bm_x;
bmi.bmiHeader.biHeight=bm_y;
bmi.bmiHeader.biPlanes=1;
bmi.bmiHeader.biBitCount=32;

char* bmbits;
bitmap = CreateDIBSection(memHdc, &bmi, DIB_RGB_COLORS, (void**)&bmbits, NULL, 0);

HBITMAP restore = (HBITMAP)SelectObject(memHdc, (HGDIOBJ)bitmap);
BitBlt(memHdc, 0, 0, bm_x, bm_y, desktopHdc, 0, 0, SRCCOPY);

int bytes = send(secondarySocket, bmbits, bmSize, 0);
if(bytes == 0 || bytes == -1)
{
MessageBox(NULL, "disconnected", "", 0);
break;
}
std::cout << "bmsize: " << bmSize << " bytes: " << bytes << " bmbits: " << bmbits << std::endl; // for debugging

SelectObject(memHdc, restore);
DeleteObject(bitmap);
Sleep(1000);
}

DeleteDC(memHdc);
DeleteObject(bitmap);

shutdown(mainSocket, SD_BOTH);
shutdown(secondarySocket, SD_BOTH);

return 0;
}

DWORD thClient(LPVOID param) // window handle is passed through "param" parameter
{
HDC windowHdc = GetDC((HWND)param);
HDC memHdc = CreateCompatibleDC(windowHdc);
HBITMAP restore;
while(TRUE)
{
BITMAPINFO bmi;
ZeroMemory(&bmi,sizeof(BITMAPINFO));
bmi.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
bmi.bmiHeader.biWidth=bm_x;
bmi.bmiHeader.biHeight=bm_y;
bmi.bmiHeader.biPlanes=1;
bmi.bmiHeader.biBitCount=32;

char* buffer;
HBITMAP bitmap = CreateDIBSection(windowHdc, &bmi, DIB_RGB_COLORS, (void**)&buffer, NULL, 0);

int bytes = recv(mainSocket, buffer, bmSize, 0);
if(bytes == 0 || bytes == -1)
{
MessageBox(NULL, "Disconnected.", "", 0);
break;
}
else
{
restore = (HBITMAP)SelectObject(memHdc,bitmap);

BitBlt(windowHdc, 0, 0, bm_x, bm_y, memHdc, 0, 0, SRCCOPY);
std::cout << "bmsize: " << bmSize << " bytes: " << bytes << " bmbits: " << buffer << std::endl; // for debugging
SelectObject(memHdc, restore);
}
}

DeleteDC(memHdc);
return 0;
}

РЕДАКТИРОВАТЬ 2

Задача решена:

Вот как я назвал темы:

CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)thClient, (PVOID)&hwnd, 0, NULL);
CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)thServerSend, (PVOID)hwnd, 0, NULL);

Как видите, я использовал ссылку на дескриптор окна в аргументе функции, вызывающей поток. Это тайно вызвало глупые ошибки. Никто не мог решить это без полного кода.

2

Решение

Не создавайте совместимое растровое изображение.
Создайте раздел DIB: http://msdn.microsoft.com/en-us/library/windows/desktop/dd183494%28v=vs.85%29.aspx

BITMAPINFO bi;
ZeroMemory(&bi,sizeof(BITMAPINFO));
bi.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
bi.bmiHeader.biWidth=Width;
bi.bmiHeader.biHeight=Height;
bi.bmiHeader.biPlanes=1;
bi.bmiHeader.biBitCount=32;
char* buffer;
HBITMAP bitmap=CreateDIBSection(dc,&bi,DIB_RGB_COLORS,&buffer,NULL,0);
// copy pixels to buffer
SelectObject(dc,bitmap);
BitBlt(....
1

Другие решения


По вопросам рекламы [email protected]