Delphi 如何对我的实际窗口进行屏幕截图
我定义了一个战术列表,其中包含显示/隐藏表单的所有操作。这可以是模态(showmodel)或非模态(visible:=true)。我发现一些代码可以通过以下方式捕捉屏幕截图:Delphi 如何对我的实际窗口进行屏幕截图,delphi,screenshot,delphi-2009,Delphi,Screenshot,Delphi 2009,我定义了一个战术列表,其中包含显示/隐藏表单的所有操作。这可以是模态(showmodel)或非模态(visible:=true)。我发现一些代码可以通过以下方式捕捉屏幕截图: procedure GetScreenShot(shotType: TScreenShotType; var img: TJpegImage); var w,h: integer; DC: HDC; hWin: Cardinal; r: TRect; tmpBmp: TBitmap; begin h
procedure GetScreenShot(shotType: TScreenShotType; var img: TJpegImage);
var
w,h: integer;
DC: HDC;
hWin: Cardinal;
r: TRect;
tmpBmp: TBitmap;
begin
hWin := 0;
case shotType of
sstActiveWindow:
begin //This is what I use
//only the active window
hWin := GetForegroundWindow;
dc := GetWindowDC(hWin);
GetWindowRect(hWin,r);
w := r.Right - r.Left;
h := r.Bottom - r.Top;
end; //sstActiveWindow
sstActiveClientArea:
begin
end; //sstActiveClientArea
sstPrimaryMonitor:
begin
end; //sstPrimaryMonitor
sstDesktop:
begin
end; //sstDesktop
else begin
Exit;
end; //case else
end; //case
//convert to jpg
tmpBmp := TBitmap.Create;
try
tmpBmp.Width := w;
tmpBmp.Height := h;
BitBlt(tmpBmp.Canvas.Handle,0,0,tmpBmp.Width,
tmpBmp.Height,DC,0,0,SRCCOPY);
img.Assign(tmpBmp);
finally
ReleaseDC(hWin,DC);
FreeAndNil(tmpBmp);
end; //try-finally
end;
我的“扫描”程序如下:
for ACnt := 0 to GenActions.ActionCount - 1 do
begin
try
LogBook.ML(Format('%d. Aktion %s gestartet',[ACnt,quotedstr(GenActions.Actions[ACnt].Name)]));
if GenActions.Actions[ACnt].Tag > 0 then
begin // Action is ready for test
TAction(GenActions.Actions[ACnt]).checked:=true;
if GenActions.Actions[ACnt].Execute then
begin
LogBook.ML(Format('%d. Aktion %s erfolgreich ausgeführt',[ACnt,quotedstr(GenActions.Actions[ACnt].Name)]));
if SaveScreens then // var boolean
begin
img:=TJPEGImage.Create;
try
GetScreenShot(sstActiveWindow,img);
img.SaveToFile(IncludeTrailingBackslash(Optionen.PictPfad.Text)+inttostr(ACnt)+'.jpg');
finally
img.Free;
end;
end;
repeat
sleep(100);
Application.ProcessMessages;
until not DM_Gen.TestTimer.Enabled ; //for modal windows a timer sends modalresult:=mrcancel
end;
end
else
begin
LogBook.ML(Format('%d Aktion %s nicht getestet',[ACnt,quotedstr(GenActions.Actions[ACnt].Name)]));
end;
except
on E: Exception do
LogBook.ML(Format('%d. Aktion hat Fehler %s gemeldet',[ACnt,E.Message]));
end;
end;
finally
LogBook.ML('Testlauf beendet');
end;
当我运行这段代码时,我得到大约前150个操作的主窗体,然后是一些其他窗体,如日志或浏览器或。。。几乎从来没有我想要的形式
我发现一些帖子建议使用“findwindow”。我的问题是,我不知道窗口的确切标题,因为在所有窗口中,为了显示实际信息,在onshow事件中修改了标题
你知道怎么才能抓住我真正打开的窗户吗
所以一个问题是要理解我的行为是如何运作的。这里有两个典型的例子:
procedure TDM_Gen.VALstVisActExecute(Sender: TObject);
begin
if Sender is TAction then
begin // set some properties
end;
ListeVeranst_2.Visible:=VALstVisAct.Checked;
end;
procedure TDM_Gen.NewVAActExecute(Sender: TObject);
var
NewVA : TNewVeranstaltung;
begin
if Sender <> nil then
begin
if Sender is TButton then
begin //do something depending on who fired
end;
end;
try
NewVA:=TNewVeranstaltung.Create(nil);
case NewVA.ShowModal of
mrOk:
begin // e.g. refresh some lists
end;
mrCancel:
begin // clean up
end;
end;
finally
NewVA.Free;
end;
end;
您面临的问题是由于阻止调用的
showmodel
方法造成的。这意味着该调用之后的所有后续代码都将在表单关闭后开始执行
以下简化示例中的代码流:
MyAction.Execute;
CaptureScreen;
procedure TSomeForm.MyActionExecute(Sender: TObject);
var frm: TForm;
begin
frm := TForm.Create(nil);
try
frm.ShowModal; // this call blocks execution of subsequent code in this method until form is closed
finally
frm.Free;
end;
end;
将是MyAction.Execute->frm.showmodel->frm.Close->frm.Free->CaptureScreen
您必须从模式表单中启动屏幕捕获以捕获其屏幕。您面临的问题是由于阻止调用的
showmodel
方法造成的。这意味着该调用之后的所有后续代码都将在表单关闭后开始执行
以下简化示例中的代码流:
MyAction.Execute;
CaptureScreen;
procedure TSomeForm.MyActionExecute(Sender: TObject);
var frm: TForm;
begin
frm := TForm.Create(nil);
try
frm.ShowModal; // this call blocks execution of subsequent code in this method until form is closed
finally
frm.Free;
end;
end;
将是MyAction.Execute->frm.showmodel->frm.Close->frm.Free->CaptureScreen
您必须从模式表单中启动屏幕捕获以捕获其屏幕。您面临的问题是由于阻止调用的
showmodel
方法造成的。这意味着该调用之后的所有后续代码都将在表单关闭后开始执行
以下简化示例中的代码流:
MyAction.Execute;
CaptureScreen;
procedure TSomeForm.MyActionExecute(Sender: TObject);
var frm: TForm;
begin
frm := TForm.Create(nil);
try
frm.ShowModal; // this call blocks execution of subsequent code in this method until form is closed
finally
frm.Free;
end;
end;
将是MyAction.Execute->frm.showmodel->frm.Close->frm.Free->CaptureScreen
您必须从模式表单中启动屏幕捕获以捕获其屏幕。您面临的问题是由于阻止调用的
showmodel
方法造成的。这意味着该调用之后的所有后续代码都将在表单关闭后开始执行
以下简化示例中的代码流:
MyAction.Execute;
CaptureScreen;
procedure TSomeForm.MyActionExecute(Sender: TObject);
var frm: TForm;
begin
frm := TForm.Create(nil);
try
frm.ShowModal; // this call blocks execution of subsequent code in this method until form is closed
finally
frm.Free;
end;
end;
将是MyAction.Execute->frm.showmodel->frm.Close->frm.Free->CaptureScreen
您必须从模式表单中启动屏幕捕获,才能捕获其屏幕。如果您不知道您想要哪个窗口,我们有什么机会?我知道我想要哪个窗口。一个由动作可见的动作,所以你有不知道他们在做什么的动作。。更改它们的代码,以便引用所创建的表单。ProcessMessages是错误的建议。@ChristineRoss您说您正在使用操作显示和隐藏您自己的表单,并且希望在执行操作时对这些表单进行截屏。通过从表单
handle
属性中读取if,可以轻松获得操作刚刚显示或创建的表单窗口的句柄。现在,在模态表单的情况下,您必须从模态表单代码中执行屏幕截图代码,否则在您尝试进行屏幕截图之前,表单可能会被销毁。为此,你可以创建自定义例程,它将以模式显示它们并立即截图。如果你不知道你想要哪个窗口,我们有什么机会?我知道我想要哪个窗口。一个由动作可见的动作,所以你有不知道他们在做什么的动作。。更改它们的代码,以便引用所创建的表单。ProcessMessages是错误的建议。@ChristineRoss您说您正在使用操作显示和隐藏您自己的表单,并且希望在执行操作时对这些表单进行截屏。通过从表单handle
属性中读取if,可以轻松获得操作刚刚显示或创建的表单窗口的句柄。现在,在模态表单的情况下,您必须从模态表单代码中执行屏幕截图代码,否则在您尝试进行屏幕截图之前,表单可能会被销毁。为此,你可以创建自定义例程,它将以模式显示它们并立即截图。如果你不知道你想要哪个窗口,我们有什么机会?我知道我想要哪个窗口。一个由动作可见的动作,所以你有不知道他们在做什么的动作。。更改它们的代码,以便引用所创建的表单。ProcessMessages是错误的建议。@ChristineRoss您说您正在使用操作显示和隐藏您自己的表单,并且希望在执行操作时对这些表单进行截屏。通过从表单handle
属性中读取if,可以轻松获得操作刚刚显示或创建的表单窗口的句柄。现在,在模态表单的情况下,您必须从模态表单代码中执行屏幕截图代码,否则在您尝试进行屏幕截图之前,表单可能会被销毁。为此,你可以创建自定义例程,它将以模式显示它们并立即截图。如果你不知道你想要哪个窗口,我们有什么机会?我知道我想要哪个窗口。一个由动作可见的动作,所以你有不知道他们在做什么的动作。。更改它们的代码,以便引用所创建的表单。ProcessMessages是错误的建议。@ChristineRoss您说您正在使用操作显示和隐藏您自己的表单,并且希望在执行操作时对这些表单进行截屏。通过从表单handle
属性中读取if,可以轻松获得操作刚刚显示或创建的表单窗口的句柄。现在,对于模态表单,您必须从模态表单代码或表单中执行屏幕截图代码