实验室要每天签到,所以用webBrowser写了一个一键签到的小程序,期间遇到些很有价值的问题,最大的收获就是对navigated事件 和 DocumentCompleted事件的了解。
private void webBrowser1_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
{
if (webBrowser1.ReadyState < WebBrowserReadyState.Complete) return;
if (flag == true)
{
//HtmlElementCollection 是一个集合类型,Submit中保存了表单中所有元素
HtmlElementCollection Submit = webBrowser1.Document.All;
HtmlElement tbUserid = webBrowser1.Document.All["username"];
HtmlElement tbPasswd = webBrowser1.Document.All["password"];
if (tbUserid == null || tbPasswd == null)
return;
tbUserid.SetAttribute("value", "Dp");
tbPasswd.SetAttribute("value", "123456");
getSubmit(Submit);
}
else
{
HtmlElement signIn = webBrowser1.Document.GetElementById("signin");
if (signIn == null)
return;
signIn.InvokeMember("click");
}
}
//按元素类型获取,invokeMember方法模拟点击,GetAttribut方法检索已命名属性的值
private void getSubmit(HtmlElementCollection Submit)
{
foreach (HtmlElement e in Submit)
{
string str = e.GetAttribute("type");
if (str == "submit")
{
e.InvokeMember("click");
}
}
}
首先是Documentscompleted事件的代码,其中flag用来指定一级或二级页面,因为只有两个,bool型完全足够了,flag为true时检索登录页面,获取登录id、密码,登录button等元素,并自动填充表单。
对于表单元素中有id属性的,可以用document.All["value"] 或 document.GetElementById("value") 获取相应元素,要注意的是用这两种方法必须对检索结果是否为空进行判断,不然会报错。
而没有id属性的只用靠遍历所有元素获得,这里用的是“type”类型,一定要注意,选取检索的类型命名一定要是唯一的,不然会返回所有匹配项。
获得元素后,用SetAttribute()方法填写表单,用InvokeMember()方法模拟点击,实现自动填写表单并提交的功能。
private void webBrowser1_Navigated(object sender, WebBrowserNavigatedEventArgs e)
{
//label1.Text = webBrowser1.Document.Url.ToString();
flag = !flag;
}
接下来是Navigated事件,虽然很简单,却是关键所在,因为如果不对navigate事件进行处理,webBrowser.url会一直是一级页面,这样也就不能获取到跳转后页面的元素。
整个流程就是Navigated --> DocumentCompleted --> Navigated --> DocumentCompleted,也就是每次跳转后都会重新调用DocumentCompleted事件对网页进行处理,所以所有操作都该放在DocumentCompleted中,放在Navigated中的话不能获取所有元素,只是body之前的。