Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Мультимедиа в Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 25.11.2009, 14:19   #1
rekrow
Пользователь
 
Регистрация: 08.10.2009
Сообщений: 16
По умолчанию Проблема с GetDC

делаю:

bmp:=TBitmap.Create;
bmp.Height:=500;
bmp.Width:=500;
DC:=GetDC(findwindow('Notepad','fai l.info - Блокнот'));
bitblt(bmp.Canvas.Handle, 0, 0, bmp.Width, bmp.Height,DC, 0, 0, SRCCOPY);

если окно развернуто,то захват изображения делает корректно,а если нет,то просто белое изображение.Как сделать чтобы изображение захватывалось по указанному хэндлу,даже если окно свернуто?
Thanx.

захват изображения активного окна прекрасно работает если GetDC(0),но мне нужно чтобы захват изображения происходил для другого окна(неактивного,а указанного хэндла) GetDC(findwindow('Notepad','1.txt - Блокнот')).вот.

Последний раз редактировалось mihali4; 26.11.2009 в 22:26.
rekrow вне форума Ответить с цитированием
Старый 25.11.2009, 17:12   #2
raxp
Старожил
 
Регистрация: 29.09.2009
Сообщений: 9,713
По умолчанию

Цитата:
но мне нужно чтобы захват изображения происходил для другого окна(неактивного,а указанного хэндла)
изучайте... работает хорошо если окно перекрыто другими или неактивно, если свернуто... увы... как вариант разворачивать на момент фотографирования
Код:
var fl: boolean;

//1 - способ
procedure CaptureClientImage(h: hwnd; b: tbitmap);
var DC,hSrcDC: hDC;
    Rect : TRect;
    wX,wY: integer;
begin
 GetWindowRect(h,Rect);
 wX:= Rect.Right - Rect.Left;
 wY:= Rect.Bottom - Rect.Top;
 DC:= GetWindowDC(h);
 //
 b.Handle:= CreateCompatibleBitmap(dc,wX,wY);
 //
 hSrcDC:= CreateCompatibleDC(0);
 SelectObject(hSrcDC, b.Handle);
 PrintWindow(h, hSrcDC, 0);
 //
 BitBlt(b.Handle,0,0,wX,wY,dc,0,0,SRCCOPY);
 //b.Palette:= GetSystemPalette;

 ReleaseDC(h,DC);
 DeleteDC(hSrcDC);
end;


//2 - способ
function WindowSnap(windowHandle: HWND; bmp: TBitmap): boolean;
var
  r: TRect;
  user32DLLHandle: THandle;
  printWindowAPI: function(sourceHandle: HWND; destinationHandle: HDC; nFlags: UINT): BOOL; stdcall;
begin
  result := False;
  user32DLLHandle := GetModuleHandle(user32) ;
  if user32DLLHandle <> 0 then
  begin
    @printWindowAPI := GetProcAddress(user32DLLHandle, 'PrintWindow') ;
    if @printWindowAPI <> nil then
    begin
      GetWindowRect(windowHandle, r) ;
      bmp.Width := r.Right - r.Left;
      bmp.Height := r.Bottom - r.Top;
      bmp.Canvas.Lock;
      try
        result := printWindowAPI(windowHandle, bmp.Canvas.Handle, 0) ;
      finally
        bmp.Canvas.Unlock;
      end;
    end;
  end;
end;


procedure TForm1.SpeedButton1Click(Sender: TObject);
var b: tbitmap;
    h: hwnd;
begin
  b:= tbitmap.Create;
  h:= findwindow('Notepad',nil);
  {if IsWindowVisible(h) then begin
   fl:= true;
   showwindow(h,sw_restore)
  end;
  }//
  WindowSnap(h, b);
  CaptureClientImage(h, b);
  //if fl then begin fl:= false; showwindow(h,SW_MINIMIZE) end;
  b.SaveToFile('1.bmp');
  b.Free
end;
зы: кстати обсуждалось 1 2
Разработки и научно-технические публикации :: Видеоблог :: Твиттер
Radar systems engineer & Software developer of industrial automation

Последний раз редактировалось raxp; 25.11.2009 в 17:17.
raxp вне форума Ответить с цитированием
Старый 26.11.2009, 15:23   #3
rekrow
Пользователь
 
Регистрация: 08.10.2009
Сообщений: 16
По умолчанию

Всем спасибо,вся инфа очень полезна

У меня остался один вопрос:

Как сделать частичное копирование чужого окна?
Если для активного окна работает такой код:

bmp:=TBitmap.Create;
bmp.Height:=500;
bmp.Width:=500;
DC:=GetDC(0);
bitblt(bmp.Canvas.Handle, 0, 0, bmp.Width, bmp.Height,DC, 350, 120, SRCCOPY);

т.е. 350,120 дает мне смещение отсчета координат,то при копировании чужого окна такого не получается,уже все значения поменял,ну никак не смещается точка-начала копирования....

Вот код,который прекрасно работает с копированием чужого окна:

var DC,hSrcDC: hDC;
Rect : TRect;
wX,wY: integer;
b: tbitmap;
h: hwnd;
begin
b:= tbitmap.Create;
h:= findwindow(nil,'Сube Info');
GetWindowRect(h,Rect);
wX:= Rect.Right - Rect.Left;
wY:= Rect.Bottom - Rect.Top;
DC:= GetWindowDC(h);
b.Handle:= CreateCompatibleBitmap(dc,wX,wY);
hSrcDC:= CreateCompatibleDC(0);
SelectObject(hSrcDC, b.Handle);
PrintWindow(h, hSrcDC, 0);
BitBlt(b.Handle,0,0,wX,wY,DC,0,0,SR CCOPY);
b.SaveToFile('C:\1.bmp');
ReleaseDC(h,DC); DeleteDC(hSrcDC);
b.Free

Как его модифицировать,чтобы копировалась часть чужого экрана?

Последний раз редактировалось rekrow; 26.11.2009 в 15:43.
rekrow вне форума Ответить с цитированием
Старый 26.11.2009, 16:41   #4
raxp
Старожил
 
Регистрация: 29.09.2009
Сообщений: 9,713
По умолчанию

есть help, очень полезная вещь... а если еще потратить время, то можно найти - copyrect:
Код:
procedure CaptureScreen(ABitmap: TBitmap);
const CAPTUREBLT = $40000000;
var
  hdcScreen: HDC;
  hdcCompatible: HDC;
  hbmScreen: HBITMAP;
begin
  hdcScreen := CreateDC('DISPLAY', nil, nil, nil);
  hdcCompatible := CreateCompatibleDC(hdcScreen);

  hbmScreen := CreateCompatibleBitmap(hdcScreen,
    GetDeviceCaps(hdcScreen, HORZRES),
    GetDeviceCaps(hdcScreen, VERTRES));

  SelectObject(hdcCompatible, hbmScreen);
  ABitmap.Handle := hbmScreen;
  BitBlt(hdcCompatible,
    0, 0,
    ABitmap.Width, ABitmap.Height,
    hdcScreen,
    0, 0,
    SRCCOPY or CAPTUREBLT);

  DeleteDC(hdcScreen);
  DeleteDC(hdcCompatible)
end;

procedure getobl(filename: STRING; l,r,w,h: integer);
var b,b2: tbitmap;
begin
 b := tbitmap.Create;
 b2:= tbitmap.Create;

 b2.Width := w;
 b2.Height:= h;

 CaptureScreen(b);
 b2.Canvas.CopyRect(Rect(0,0,w,h),
                    b.canvas,
                    Rect(l,r,l+w,r+h));

 b2.SaveToFile(filename);
 b.Free; b2.Free
end;

procedure TForm1.SpeedButton2Click(Sender: TObject);
begin
 getobl('1.bmp', 874,618, 150,150)
end;
смысл ясен?
Разработки и научно-технические публикации :: Видеоблог :: Твиттер
Radar systems engineer & Software developer of industrial automation
raxp вне форума Ответить с цитированием
Старый 26.11.2009, 18:41   #5
rekrow
Пользователь
 
Регистрация: 08.10.2009
Сообщений: 16
По умолчанию

Да,смысл мне понятен!Дело в том,что я уже пробовал через CopyRect,но он не вырезает ничего,просто создает пустой bmp.Вот код,который я пользовал:
var DC,hSrcDC: hDC;
RRect : TRect;
wX,wY: integer;
b,b2: tbitmap;
h: hwnd;
begin
b:= tbitmap.Create;
b2:= tbitmap.Create;
h:= findwindow(nil,'Сube Info');
GetWindowRect(h,RRect);
wX:= RRect.Right - RRect.Left;
wY:= RRect.Bottom - RRect.Top;
DC:= GetWindowDC(h);
b.Handle:= CreateCompatibleBitmap(dc,wX,wY);
hSrcDC:= CreateCompatibleDC(0);
SelectObject(hSrcDC, b.Handle);
PrintWindow(h, hSrcDC, 0);
BitBlt(b.Handle,0,0,wX,wY,DC,0,0,SR CCOPY);
b.SaveToFile('C:\1.bmp');
b2.Canvas.CopyRect(Rect(0,0,860,635 ),b.canvas,Rect(10,10,10,10));
b2.SaveToFile('C:\2.bmp');
ReleaseDC(h,DC); DeleteDC(hSrcDC);
b.Free;
b2.Free;

Bmp1 хранит нормально,чужое окошко прекрасно копируется,а вот из него уже ничего не вырезается,просто создается файл с невозможностью прочитать его.Может я НУБлю жестко?!
rekrow вне форума Ответить с цитированием
Старый 26.11.2009, 22:13   #6
raxp
Старожил
 
Регистрация: 29.09.2009
Сообщений: 9,713
По умолчанию

ваш (этот) код мне знаком... у него есть еще недостаток, он не копирует полупрозрачные окна... используйте тот что дал и все будет ок.

...кроме того, при такой записи у вас
Код:
Rect(0,0,860,635 ),b.canvas,Rect(10,10,10,10)
размер выходной области будет 860x635, а копируете вы туда лишь 10х10px, да и размеры b2 вы не определили, тем паче 0 будет.
Разработки и научно-технические публикации :: Видеоблог :: Твиттер
Radar systems engineer & Software developer of industrial automation
raxp вне форума Ответить с цитированием
Старый 27.11.2009, 09:38   #7
BOBAH13
Android Developer
Старожил Подтвердите свой е-майл
 
Аватар для BOBAH13
 
Регистрация: 19.02.2007
Сообщений: 3,708
По умолчанию

Ну либо через DISPLAY + CreateDC как было выше указано либо через BitBlt но SRC_COPY +
Код:
#define CAPTUREBLT          (DWORD)0x40000000 /* Include layered windows */
BOBAH13 вне форума Ответить с цитированием
Старый 27.11.2009, 14:14   #8
rekrow
Пользователь
 
Регистрация: 08.10.2009
Сообщений: 16
По умолчанию

Всем огромное спасибо.Маленько пришлось по-другому обмозговать код,но в целом работает как мне надо

P.S.:отдельное спасибо raxp,сопровождал все мои топики ценными советами!!!
rekrow вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Аналог GetDC() Василий Win Api 3 14.01.2009 09:32
Проблема с рамами/Проблема с ЖД DRAGGER Компьютерное железо 6 04.01.2009 23:37