用TWebBrowser 组件 POST 数据和预览 HTML 片段

 

相信 Delphi 中 TWebBrowser 组件大家都比较熟悉,用它自己进行制作浏览器非常简单,论坛中和文档中心中都谈了很多,我这里主要想谈两个两个问题:

如何用 TWebBrowser 组件 POST 数据?
如何用 TWebBrowser 组件预览 HTML 文档片段?
因为工作需要,需用用到 TWebBrowser 组件的 POST 功能,查了CSDN上的很多文档都没有介绍,只有一篇关于 C++ Builder 的使用示例,但是我相信很多用 Delphi 的朋友跟我一样都会觉太复杂,很难写成 Delphi 的语法。所以自己就动手做,终于最有实现了!这里就拿出来跟大家共享。我不能保证我的示例是优秀,但是确实是可以工作的,我用它在已经发了几万个POST请求,没有出错。

至于第二个问题,我这里只是对一个朋友网文的补充,看看如何轻松、准确预览 HTML 片段,相信跟我一样比较喜欢偷懒、完美的人会喜欢的!

先看看文中用到的几个 TWebBrowser 的关键属性、方法、事件:

OleObject.Document 属性:指向 TWebBrower 的文档接口,也可以用 Document 属性代替
DefaultInterface 属性:指向组件的默认接口,也就是 TWebBrower 本身
ReadyState 属性:指示 TWebBrower 组件的状态
Navigate 过程:本文用来 POST 数据调用的方法,与 Navigate2 相似,文中用了这个
OnBeforeNavigate2 事件:调用 Navigate 后,真正发送事件前发生,带来所有 POST 的参数
OnNewWindow2 事件:TWebBrower 组件需要打开新窗口时发生,可以屏蔽或重定位新窗口
OnDocumentComplete 事件:文档装载完毕时发生
下面就来开始我们的第一个例子:

1、所用组件:

wbMain: TWebBrowser;// 主的 TWebBrowser 组件
wbAssistant: TWebBrowser; // 辅助 TWebBrowser 组件,有些网站要求
memoSource: TMemo;// 存放 POST 回来的 HTML 文本
memoLog: TMemo;// 记录一些 Navigate 的数据
btnPrepare: TBitBtn;// 做些准备操作
btnPost:??? TBitBtn;// 真正 POST 数据出去

2、编写代码:

A、准备起始网页
根据各个网站,可能要求不用,有的网站不要求预先浏览网页就可以直接 POST 数据的,有些不行,还有些必须是重另一个网页跳转过来的(下面的例子就是,如果不是这种情况,可以不用 wbAssistant 组件)
procedure TformMain.btnPrepareClick(Sender: TObject);
begin
 // 如果网站不要求跳转可以直接用下面一句,如果不用预览,则完全不需要准备这个过程的?
 // wbMain.Navigate('http://www.imobile.com.cn/pconline2.php');
 wbAssistant.Navigate('http://www.hao123.com/haoserver/showjicc.htm');
end;

procedure TformMain.wbAssistantNewWindow2(Sender: TObject;
 var ppDisp: IDispatch; var Cancel: WordBool);
begin
 // 把新窗口指向 wbMain ,要不就会弹出新窗口,要求此时不能有浏览器已经打开目标页,要不还是定位在那个窗口(本例)
??? ppDisp := wbMain.DefaultInterface;??
end;

B、发送 POST 数据
????? 对本例需要现在 wbAssistant 输入一个手机号码,然后才跳转到 wbMain,本来可以只用一个浏览器,但考虑到本例网站本身要求跳转到新页面,就用两个浏览器(实际可以跳转会原来的)。
????? 下面是关键代码,注意每个参数是怎么定义的!

procedure TformMain.btnPostClick(Sender: TObject);
var
?  Index: Integer;
?  URL: WideString;
?  Flags, TargetFrameName, PostData, Headers: ?  OleVariant;
?  PostStr: AnsiString;
?  PostLen: Integer;
begin
?   //  先等待文章装载好了再进行
?   while  wbMain.ReadyState  <>  READYSTATE_COMPLETE ???????   do
???  Application.ProcessMessages;
?   // ========================================================
?   //  准备参数
?  URL : =   ' http://www.ip138.com:8080/search.asp ' ; ?   //  本例
?  Flags : =   0 ; ????????????????????????   //  VarType: varInteger
?  TargetFrameName : =   ' mobilewindow ' ; ?   //  VarType: varOleStr
?   //  构建 PostData 数据??????????????  //  VarType: 16396? (Variant array of Variant)
?   //  PostStr 采用 URL 的编码方式,具体如何变换大家查考相关文档,这里假定大家已经清楚
?  PostStr : =   ' mobile= '   +  editData.Text  +   ' &action=mobile&B1=%B2%E9+%D1%AF ' ;
?  PostLen : =  Length(PostStr);
?   //  用构建 varByte 类型的 Variant array
?  PostData : =  VarArrayCreate([ 0 , (PostLen  -   1 )], varByte);
?   //  填充数据
?   for  Index : =   0  to PostLen  -   1   do
???  PostData[Index] : =  Ord(PostStr[Index  +   1 ]);
?   //  填补头部数据注意:application
?  Headers : =   ' Content-Type: application/x-www-form-urlencoded ' ; ?   //  varOleStr
?   // ========================================================
?   //  用 Navigate 方法 POST 数据(如果 PostData 为空,TWebBrowser 用 GET 方法)
?  wbMain.Navigate(URL, Flags,TargetFrameName, PostData, Headers);
?   // ========================================================
?   //  等待接收结果 HTML
?   while  wbMain.ReadyState  <>  READYSTATE_COMPLETE ???????   do
???  Application.ProcessMessages;
?   //  提取数据,可以根据需要用其他方式
?  memoSource.Text : =  wbMain.OleObject.Document.all.tags( ' HTML ' ).Item( 0 ).outerHTML;
end;

C、可以在事件 OnBeforeNavigate2 检查数据(可选)
我觉得这个事件很有用,可以用来检测 TWebBrowser 实际上发送了什么数据到网络上,如 URL、PostData,我就是通过这个事件才搞清楚到底怎样构建 PostData 的数据的。

procedure TformMain.wbMainBeforeNavigate2(Sender: TObject;
?   const  pDisp: IDispatch; var URL, Flags, TargetFrameName, PostData,
?  Headers: OleVariant; var Cancel: WordBool);
var
?  Index: ?  Integer;
?  PostStr: AnsiString;
begin
 
//  加入时间标签
 memoLog.Lines.Add(FormatDateTime( ' ==== yyyy-mm-dd hh:nn:ss ==== ' , Now()));
 memoLog.Lines.Add(
' URL:  '   +  URL);
 memoLog.Lines.Add(
' Flags:  '   +  IntToStr(Flags));
 memoLog.Lines.Add(
' TargetFrameName:  '   +  TargetFrameName);
 
//  注意如何处理 PostData
  if  Length(PostData)  >   0  then
 begin
 PostStr :
=   ' PostData( '   +  IntToStr(Length(PostData))  +   ' ):  ' ;
 
for  Index : =   0  to VarArrayHighBound(PostData,  1 do
 begin
   PostStr :
=  PostStr  +  Chr(Byte(PostData[Index]));
 end;
 memoLog.Lines.Add(PostStr);
 end;
 memoLog.Lines.Add(
' Headers:  '   +  Headers);
end;

上面就是完整代码,在 Delphi 7(Window 2000/XP)调试通过!

对于第二问题,我这里就不详细介绍,只提两个关键点:

1、用 TWebBrowser 预览 HTML 片段的方式:

?? HTMLText := '

测试 HTML 片段

 // HTMLText 就是要预览的 HTML 片段
wbMain.Navigate('about:blank');
while wbMain.ReadyState <> READYSTATE_COMPLETE do
 Application.ProcessMessages;
wbMain.OleObject.Document.body.innerHTML := HTMLText;?
显示图片和Style:

 采用上面方式预览时有个问题,就是相对路径的图片、采用Style的格式没办法准确显示。可以这样处理,例如想分析“www.163.com”主页的一些片段,可以这样实现,解决这个问题:
 HTMLText := '

测试 HTML 片段

 // HTMLText 就是要预览的 HTML 片段
wbMain.Navigate('www.163.com');
while wbMain.ReadyState <> READYSTATE_COMPLETE do
 Application.ProcessMessages;
wbMain.OleObject.Document.body.innerHTML := HTMLText;?

上面就是完整代码,在 Delphi 7(Window 2000/XP)调试通过!

-----------------------------------------------------------------------------

希望本文章能让你更好的使用 TWebBrowser!需要例子可以跟我联系。
联系方式:
 QQ:4263383
 EM:zhengcg@163.com

 


Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=65883

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值