要如何透過WebBrowser去設定iframe內TextBox的值呢?
有朋友詢問如何透過WebBrowser元件設定「百度网站登录」裡面TextBox的值,如下圖,
透過 IE 開發者工具發現,要 Access 的 Textbox 是在 iframe 之中,如下,
所以就透過 webBrowser1.Document.Window.Frames[0].Document.All.GetElementsByName("url") 去取得 Textbox。
但卻發生「System.UnauthorizedAccessException was unhandled」的錯誤,如下,
System.UnauthorizedAccessException was unhandled
HResult=-2147024891
Message=存取被拒。 (發生例外狀況於 HRESULT: 0x80070005 (E_ACCESSDENIED))
Source=System.Windows.Forms
StackTrace:
於 System.Windows.Forms.UnsafeNativeMethods.IHTMLWindow2.GetDocument()
於 System.Windows.Forms.HtmlWindow.get_Document()
因為主頁面跟iframe是不同domain(www.baidu.com VS. utility.baidu.com),所以會有那個錯誤。
後來找到「c# webbrowser跨域存取iframe的方法」這篇,
可以到「IE Automation Library and Web Macro Recorder」,下載它的範例程式,
Copy CrossFrameIE.cs 加入專案,並加入 Interop.SHDocVw.dll(可以從它的範例中Copy) 及 Microsoft.mshtml 參考。
再來就是透過 CrossFrameIE.GetDocumentFromWindow 取回 Document,
因為我還要取得裡面的物件,所以將 IHTMLDocument2 轉型成 IHTMLDocument3 ,
所以完整的程式碼如下,
HtmlDocument main_formDoc = webBrowser1.Document;
IHTMLDocument2 main_mshtmlIHTMLDoc = (IHTMLDocument2)main_formDoc.DomDocument;
//取第1個frame,由0開始
Object frame_index = 0;
IHTMLWindow2 target_mshtmlIHTMLWindow = (IHTMLWindow2)main_mshtmlIHTMLDoc.frames.item(ref frame_index);
var target_mshtmlIHTMLDoc = (IHTMLDocument3)CodecentrixSample.CrossFrameIE.GetDocumentFromWindow(target_mshtmlIHTMLWindow);
var url = target_mshtmlIHTMLDoc.getElementsByName("url")
.OfType<IHTMLElement>()
.FirstOrDefault();
var code = target_mshtmlIHTMLDoc.getElementsByName("code")
.OfType<IHTMLElement>()
.FirstOrDefault();
if(url!=null && code != null)
{
url.setAttribute("value", "@@@网址@@@");
code.setAttribute("value", "@@@验证码@@@");
}
Demo程式:WebBrowseriFrame.zip
參考資料
IE Automation Library and Web Macro Recorder
Hi,
亂馬客Blog已移到了 「亂馬客 : Re:從零開始的軟體開發生活」
請大家繼續支持 ^_^