| vazzzzz 
 
 | Редактировать | Цитировать | Сообщить модератору Zloy_Gelud
 
 Спасибо вам за информацию, только что приехал и попробовал наваять чего-нить. Но как-то не вышло сходу (хотя все до функции SetDIBitsToDevice "заработало" сразу и выдало уведомление об "успехе"). Но в итоге функция вернула "0" (( Что-то я не так делаю, прошу еще раз пендаль волшебный (взгляните на мои "труды" если не сложно).
 
 
 Код:
 | local disp = {};
 disp.Width = 800;
 disp.Height = 600;
 disp.Handle = Application.GetWndHandle();
 disp.DevCH = DLL.CallFunction("User32.dll", "GetDC", disp.Handle, DLL_RETURN_TYPE_INTEGER, DLL_CALL_STDCALL);
 --создание структуры, описывающей bitmap изображение (BITMAPINFO)
 local BITMAPINFO = MemoryEx.DefineStruct {
 DWORD    ("biSize", disp.Width * disp.Height * 3);
 INT        ("biWidth", disp.Width);
 INT        ("biHeight", disp.Height);
 WORD    ("biPlanes", 1);
 WORD    ("biBitCount", 24);
 DWORD    ("biCompression", 0);
 DWORD    ("biSizeImage", 0);
 INT        ("XPelsPerMeter"); --что это?
 INT        ("YPelsPerMeter"); --что это?
 DWORD    ("biClrUsed", 0);
 DWORD    ("biClrImportant", 0);
 DWORD    ("biRGBQuad", 0); --что это?
 };
 apper1 = Application.GetLastError();
 --получение указателя на структуру BITMAPINFO
 local hBITMAPINFO = BITMAPINFO:New();
 apper2 = Application.GetLastError();
 local pBITMAPINFO = hBITMAPINFO:GetPointer();
 apper3 = Application.GetLastError();
 --создание массива из disp.Width * disp.Height * 3 байт для указания цветов каждого пикселя
 disp.BMHandle = MemoryEx.Allocate(disp.Width * disp.Height * 3);
 apper4 = Application.GetLastError();
 --
 if (disp.Handle > -1 and disp.DevCH ~= "") then
 if (apper1 == 0 and apper2 == 0 and apper3 == 0 and apper4 == 0) then
 --если все OK
 disp.args = disp.DevCH .. ",0,0," .. tostring(disp.Width) .. "," .. tostring(disp.Height) .. ",0,0,0," .. tostring(disp.Height) .. "," .. disp.BMHandle .. "," .. pBITMAPINFO .. ",0";
 -- в функции StretchDIBits использовать pBITMAPINFO в качестве указателя на структуру BITMAPINFO
 dispIsOK = DLL.CallFunction("gdi32.dll", "SetDIBitsToDevice", disp.args, DLL_RETURN_TYPE_INTEGER, DLL_CALL_STDCALL);
 apper1 = Application.GetLastError();
 hBITMAPINFO:Free();
 apper2 = Application.GetLastError();
 if (dispIsOK ~= "") then
 if (apper1 == 0 and apper2 == 0) then
 message = "Успешно!\n\n";
 message = message .. "Структура: " .. disp.DevCH .. "\n";
 message = message .. "BitmapInfo: " .. pBITMAPINFO .. "\n";
 message = message .. "Bitmap: " .. disp.BMHandle .. "\n";
 message = message .. "Результат: " .. dispIsOK;
 Dialog.Message("Уведомление", message, MB_OK, MB_ICONINFORMATION, MB_DEFBUTTON1);
 else
 Dialog.Message("Ошибка", "Не удалось удалить структуру BITMAPINFO!", MB_OK, MB_ICONSTOP, MB_DEFBUTTON1);
 end
 else
 Dialog.Message("Ошибка", "Не удалось вывести bitmap!", MB_OK, MB_ICONSTOP, MB_DEFBUTTON1);
 end
 else
 Dialog.Message("Ошибка", "Не удалось выделить память!", MB_OK, MB_ICONSTOP, MB_DEFBUTTON1);
 end
 if (DLL.CallFunction("User32.dll", "ReleaseDC", disp.Handle .. "," .. disp.DevCH, DLL_RETURN_TYPE_INTEGER, DLL_CALL_STDCALL) == "") then
 Dialog.Message("Ошибка", "Не удалось удалить контекст устройства!", MB_OK, MB_ICONSTOP, MB_DEFBUTTON1);
 end
 else
 Dialog.Message("Ошибка", "Не удалось создать контекст устройства!", MB_OK, MB_ICONSTOP, MB_DEFBUTTON1);
 end
 
 
 | 
 
 Пояснения: я выделяю массив по 3 байта на пиксель и ничего туда не пишу, потому как мне б "хоть что-то" для начала вывести на экран (хоть все черное, хоть все белое, да хоть пурпурное - лишь бы пощупать функцию для начала). Как я понимаю в изначально выделенных байтах будет либо 0x000000 либо 0xFFFFFF (на каждый пиксель)? Или я ошибаюсь? С NULLом не оч дружу (в плане осознания), может это и губит?
 
 Добавлено:
 Zloy_Gelud
 
 Еще наблюдаю периодически странное пока для меня явление: иногда функция GetDC возвращает отрицательный хэндл для контекста окна. Совершенно не предсказуемо. И еще одна странность - если я устанавливаю в настройках проекта "запускать от имени администратора", то эффект выдачи отрицательного хэндла проявляется чаще, чем при обычном запуске (As invoker). И это меня слегка пугает, т.к. сейчас я вызываю функцию однократно, а что будет когда я буду кадры отрисовывать 100 раз в секунду?.. Отрицательный хэндл имеется в виду не "-1", а "-179832749238" (ну или типа того). Пробовал устанавливать и DLL_RETURN_TYPE_LONG (первая мысль возникла, что причина в изменении старшего бита переменной и из-за этого число становится отрицательным) - не помогло, все равно иногда проскакивает отрицательное число.
 |