TWebBrowser:如何知道 OnNewWindow2 事件中的 URL?
TWebBrowser: How to know the URL in a OnNewWindow2 event?
我们 HTML 有:
<A target="_blank" href="http://blabla.com">
单击 link 时,触发 OnNewWindow2
:
procedure TForm1.WebBrowser1NewWindow2(Sender: TObject;
var ppDisp: IDispatch; var Cancel: WordBool);
begin
Cancel := True;
// open in default browser
end;
我想在默认浏览器中打开link:
Opening TWebBrowser link in default browser
但在我的案例中没有 BeforeNavigate2
被解雇。
我如何知道 TWebBrowser
OnNewWindow2
事件中预期的 URL?
编辑:在较新版本的 Delphi 中,有一个 OnNewWindow3
事件提供了我需要的 URL。目前我真的很难开始理解如何将这个事件实现到现有的 TWebBrowser
.
如果有人这样做过,那么得到一些帮助会很棒。
How can I know the intended URL in a TWebBrowser OnNewWindow2 event?
您可以使用 DOM 的 getAttribute method。但是在你应该加载所需的页面之前,完成之后用你自己的替换特定的事件。请参阅下面的代码:
uses
...
SHDocVw, MSHTML;
type
TForm1 = class(TForm)
...
// Your auto-generated event handler
procedure WebBrowser1DocumentComplete(ASender: TObject;
const pDisp: IDispatch; const URL: OleVariant);
private
// Your self-written event handlers
procedure New_BeforeNavigate2(ASender: TObject;
const pDisp: IDispatch; const URL, Flags, TargetFrameName, PostData, Headers: OleVariant;
var Cancel: WordBool);
procedure New_NewWindow2(ASender: TObject; var ppDisp: IDispatch; var Cancel: WordBool);
end;
...
// Assign event handler in design-time
procedure TForm1.WebBrowser1DocumentComplete(ASender: TObject; const pDisp: IDispatch;
const URL: OleVariant);
begin
(ASender as TWebBrowser).OnBeforeNavigate2 := New_BeforeNavigate2;
(ASender as TWebBrowser).OnNewWindow2 := New_NewWindow2;
end;
procedure TForm1.New_BeforeNavigate2(ASender: TObject; const pDisp: IDispatch;
const URL, Flags, TargetFrameName, PostData, Headers: OleVariant;
var Cancel: WordBool);
begin
ShowMessage('New URL will be: ' + URL);
Cancel := true;
end;
procedure TForm1.New_NewWindow2(ASender: TObject; var ppDisp: IDispatch; var Cancel: WordBool);
var
S: String;
begin
S := ((TWebBrowser(ASender).Document as IHTMLDocument2).ActiveElement as IHTMLElement).GetAttribute('href', 0);
ShowMessage('New window''s URL is: ' + S);
Cancel := true;
end;
现在即使有 OnNewWindow2
活动也可以获得 URL。对于案例 target="_self"
,还有 OnBeforeNavigate2
事件处理程序。如果我正确回答了你的问题,它应该可以工作。
您可以覆盖 InvokeEvent
method of the browser and wait there for the DISPID_NEWWINDOW3
dispatch identifier. For an interposer class such OnNewWindow3
事件,可以这样实现:
uses
ActiveX, OleCtrls, SHDocVw;
const
DISPID_NEWWINDOW3 = 273;
type
TWebBrowserNewWindow3 = procedure(ASender: TObject; var ppDisp: IDispatch; var Cancel: WordBool;
dwFlags: Longint; const bstrUrlContext: WideString; const bstrUrl: WideString) of object;
TWebBrowser = class(SHDocVw.TWebBrowser)
private
FOnNewWindow3: TWebBrowserNewWindow3;
protected
procedure InvokeEvent(ADispID: TDispID; var AParams: TDispParams); override;
public
property OnNewWindow3: TWebBrowserNewWindow3 read FOnNewWindow3 write FOnNewWindow3;
end;
implementation
procedure TWebBrowser.InvokeEvent(ADispID: TDispID; var AParams: TDispParams);
begin
if (ADispID = DISPID_NEWWINDOW3) and Assigned(FOnNewWindow3) then
begin
FOnNewWindow3(Self, AParams.rgvarg^[4].pdispVal^, AParams.rgvarg^[3].pbool^,
AParams.rgvarg^[2].lVal, WideString(AParams.rgvarg^[1].bstrVal), WideString(AParams.rgvarg^[0].bstrVal));
end
else
inherited;
end;
我们 HTML 有:
<A target="_blank" href="http://blabla.com">
单击 link 时,触发 OnNewWindow2
:
procedure TForm1.WebBrowser1NewWindow2(Sender: TObject;
var ppDisp: IDispatch; var Cancel: WordBool);
begin
Cancel := True;
// open in default browser
end;
我想在默认浏览器中打开link: Opening TWebBrowser link in default browser
但在我的案例中没有 BeforeNavigate2
被解雇。
我如何知道 TWebBrowser
OnNewWindow2
事件中预期的 URL?
编辑:在较新版本的 Delphi 中,有一个 OnNewWindow3
事件提供了我需要的 URL。目前我真的很难开始理解如何将这个事件实现到现有的 TWebBrowser
.
如果有人这样做过,那么得到一些帮助会很棒。
How can I know the intended URL in a TWebBrowser OnNewWindow2 event?
您可以使用 DOM 的 getAttribute method。但是在你应该加载所需的页面之前,完成之后用你自己的替换特定的事件。请参阅下面的代码:
uses
...
SHDocVw, MSHTML;
type
TForm1 = class(TForm)
...
// Your auto-generated event handler
procedure WebBrowser1DocumentComplete(ASender: TObject;
const pDisp: IDispatch; const URL: OleVariant);
private
// Your self-written event handlers
procedure New_BeforeNavigate2(ASender: TObject;
const pDisp: IDispatch; const URL, Flags, TargetFrameName, PostData, Headers: OleVariant;
var Cancel: WordBool);
procedure New_NewWindow2(ASender: TObject; var ppDisp: IDispatch; var Cancel: WordBool);
end;
...
// Assign event handler in design-time
procedure TForm1.WebBrowser1DocumentComplete(ASender: TObject; const pDisp: IDispatch;
const URL: OleVariant);
begin
(ASender as TWebBrowser).OnBeforeNavigate2 := New_BeforeNavigate2;
(ASender as TWebBrowser).OnNewWindow2 := New_NewWindow2;
end;
procedure TForm1.New_BeforeNavigate2(ASender: TObject; const pDisp: IDispatch;
const URL, Flags, TargetFrameName, PostData, Headers: OleVariant;
var Cancel: WordBool);
begin
ShowMessage('New URL will be: ' + URL);
Cancel := true;
end;
procedure TForm1.New_NewWindow2(ASender: TObject; var ppDisp: IDispatch; var Cancel: WordBool);
var
S: String;
begin
S := ((TWebBrowser(ASender).Document as IHTMLDocument2).ActiveElement as IHTMLElement).GetAttribute('href', 0);
ShowMessage('New window''s URL is: ' + S);
Cancel := true;
end;
现在即使有 OnNewWindow2
活动也可以获得 URL。对于案例 target="_self"
,还有 OnBeforeNavigate2
事件处理程序。如果我正确回答了你的问题,它应该可以工作。
您可以覆盖 InvokeEvent
method of the browser and wait there for the DISPID_NEWWINDOW3
dispatch identifier. For an interposer class such OnNewWindow3
事件,可以这样实现:
uses
ActiveX, OleCtrls, SHDocVw;
const
DISPID_NEWWINDOW3 = 273;
type
TWebBrowserNewWindow3 = procedure(ASender: TObject; var ppDisp: IDispatch; var Cancel: WordBool;
dwFlags: Longint; const bstrUrlContext: WideString; const bstrUrl: WideString) of object;
TWebBrowser = class(SHDocVw.TWebBrowser)
private
FOnNewWindow3: TWebBrowserNewWindow3;
protected
procedure InvokeEvent(ADispID: TDispID; var AParams: TDispParams); override;
public
property OnNewWindow3: TWebBrowserNewWindow3 read FOnNewWindow3 write FOnNewWindow3;
end;
implementation
procedure TWebBrowser.InvokeEvent(ADispID: TDispID; var AParams: TDispParams);
begin
if (ADispID = DISPID_NEWWINDOW3) and Assigned(FOnNewWindow3) then
begin
FOnNewWindow3(Self, AParams.rgvarg^[4].pdispVal^, AParams.rgvarg^[3].pbool^,
AParams.rgvarg^[2].lVal, WideString(AParams.rgvarg^[1].bstrVal), WideString(AParams.rgvarg^[0].bstrVal));
end
else
inherited;
end;