aardio 文档

web.view 自动化操作网页

web.view 操作网页应当是最优选,如无必要应优先使用 web.view 而不是 chrome.driver 。

请参考:

等待网页文档对象 #

在浏览器组件打开的网页加载完成以后,仍有可能会动态创建或加载其他内容。 根据需要等待的目标不同,web.view 提供了不同的方法。

web.view 网页加载事件按触发先后顺序列举如下:

web.view 还提供了 3 个函数用于判断网页文档对象的加载状态,并等待网页的文档对象准备就绪

示例:

import win.ui;
var winform = win.form(text="WebView2");

import web.view;
var wb = web.view(winform);

//网页文档对象已初始化。
wb.onDocumentInit = function(url){
    // url 为 当前打开的网址
}

//打开网页
wb.go("http://www.example.com?q=word")

//仅等待文档对象
wb.waitDoc();

//等待指定的 URL 打开并且网页文档对象准备就绪。 
wb.wait("example.com");

//等待指定的 URL 的指定参数,并返回该参数的值。 
var qValue = wb.waitUrlParam("example.com","q");

//查看 q 参数的值
winform.msgbox(qValue);

winform.show();
win.loopMessage();

等待并自动化操作网页元素 #

我们可以使用 wb.waitEle 或 wb.waitEle2 等待指定的网页创建指定的元素。 这两个函数的参数用法是相同的,但 wb.waitEle 仅等待单个网址,如果网页中途发生跳转,则 wb.waitEle 会返回 null,但 wb.waitEle2 在等待过程中允许网址跳转,它会继续等待直到成功,除非网页窗口关闭。

wb.waitEle 函数用法:

/*
同步等待网页创建指定节点。
网页关闭或当前网址变更也会退出等待。

@selector 参数指定CSS选择器。
可选用参数 @timeout 指定超时,单位毫秒。 

成功返回 CSS 选择器,失败返回 null,错误对象(表对象或字符串)。
*/
wb.waitEle(selector,timeout) 

/*
异步等待网页创建指定节点。

@selector 参数指定CSS选择器。
找到节点则执行参数 @2 指定的 JavaScript 代码。
执行 JS 代码时自动绑定 this 对象为找到的节点对象。 

可选用参数 @timeout 指定超时,单位毫秒。 
*/
wb.waitEle(selector,js,timeout) 

/*
异步等待网页创建指定节点。

@selector 参数指定CSS选择器。
找到节点后异步回调参数 @2 指定的 aardio 函数,参数@1为 CSS选择器。
可选用参数 @timeout 指定超时,单位毫秒。 
*/
wb.waitEle(selector,callback,timeout)

wb.wait 函数支持模式匹配语法

wb.waitEle2 函数用法:

/*
同步等待网页创建指定节点。
不同于 waitEle 仅在当前网页有效,
waitEle2 支持跨网页等待,网址变更也不会退出等待。
除非关闭窗口,此函数会一直等待直到指定选择器的对象创建成功。

@selector 参数指定CSS选择器。
可选用参数 @timeout 指定超时,单位毫秒。 

成功返回 CSS 选择器,失败返回 null,错误对象(表对象或字符串)。
*/
wb.waitEle2(selector,timeout) 

/*
同步等待网页创建指定节点。

@selector 参数指定CSS选择器。
找到节点则异步执行参数 @2 指定的 JavaScript 代码。
执行 JS 代码时自动绑定 this 对象为找到的节点对象。 

可选用参数 @timeout 指定超时,单位毫秒。 
*/
wb.waitEle2(selector,js,timeout) 

/*
同步等待网页创建指定节点。

@selector 参数指定CSS选择器。
找到节点后异步回调参数 @2 指定的 aardio 函数,参数@1为 CSS选择器。
可选用参数 @timeout 指定超时,单位毫秒。 
*/
wb.waitEle2(selector,callback,timeout)

wb.waitEle 与 wb.waitEle2 的区别在于::

如果等待时网页可能发生跳转,务必使用 wb.waitEle2 函数。

示例:

import win.ui;
var winform = win.form(text="web.view 等待并操作网页元素")

import web.view;
var wb = web.view(winform);

//打开网址
wb.go("https://www.aardio.com/zh-cn/doc/");

//用法 1. 异步等待参数@1指定 CSS 选择器的节点,回调 aardio 函数
wb.waitEle("#search-input",function(ok,err){
    wb.doScript("
        var searchInput = document.querySelector('#search-input');
        searchInput.value='多线程'; 
        searchInput.dispatchEvent(new Event('input', { bubbles: true, }));
    ")
})

//用法 2. 不指定回调函数或回调 JS 脚本则同步等待参数 @1 指定CSS选择器的节点
wb.waitEle("#search-input");

wb.doScript("
var searchInput = document.querySelector('#search-input');
searchInput.value='多线程'; 
searchInput.dispatchEvent(new Event('input', { bubbles: true, }));
")

winform.show(3/*_SW_SHOWMAXIMIZED*/);
win.loopMessage();

网页动注入 JavaScript 代码 #

wb.preloadScript 函数可在网页初始化时注入 JS 代码,这是做网页自动化非常有用的函数,在这个函数里可以修改很多 JS 默认函数实现有趣的功能,下面是一个 禁止刷新缩放的例子:

import win.ui;
var winform = win.form(text="禁止按 F5,Ctrl + R 刷新")

import web.view;
var wb = web.view(winform);

//定义字符串 initScript,赋值为需要执行的 JavaScript
var initScript = /****

//禁止页面刷新
document.onkeydown = function (e) {
    if (e.key == "F5" || (e.ctrlKey && e.key == "r") ) {
        e.preventDefault(); 
    }
} 

//禁止滚轮缩放
document.addEventListener('wheel', function(e) {
    if(e.ctrlKey) {
        e.preventDefault();
    }
}, { passive: false });

****/

//添加网页默认加载执行的 JavaScript
wb.preloadScript(initScript)

wb.html = /**
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<script >alert("网页每加载一次,显示一次弹框")</script>
</head>
<body>已禁止刷新,禁止 Ctrl + 鼠标滚轮缩放。</body>
</html>
**/

winform.show();
win.loopMessage();

拦截弹窗:

import win.ui;
var winform = win.form(text="web.view - 拦截网页弹窗")

import web.view; 
var wb = web.view(winform);

//弹出新窗口触发
wb.onNewWindow = function(url){

//耗时操作应返回异步自动执行的函数(提前结束 onNewWindow )
return function(){ 
    //如果打开的是 file: 前缀网址,例如拖放文件到网页上。
    var filePath = inet.url.getFilePath(url)
    if(filePath){
        winform.msgbox(filePath,"本地文件");    
    }
    else {
        //用 wb.location 代替 wb.go 跳转网页则当前页面设为 HTTP referrer 请求头。 
        wb.location = url;
    } 
}
}

wb.html = /**
<!doctype html>
<html><head>
<base target="_blank" />
</head>

<body style="margin:50px">
<a href="http://www.aardio.com">aardio.com</a>
<button onclick="window.open('http://www.aardio.com')" >aardio.com</button>
**/

winform.show();
win.loopMessage();

4. 使用 CDP 命令 #

web.view 提供以下 CDP 有关函数调用 WebView2 内置 CDP 接口:

更多函数请参考:

web.view 自动关闭弹框示例:

import win.ui;
var winform = win.form(text="CDP 事件 - 自动关闭网页上弹出信息框")

import web.view; 
var wb = web.view(winform);
winform.show();

//允许监听页面事件
wb.cdp("Page.enable");

//订阅 CDP 事件
//https://chromedevtools.github.io/devtools-protocol/tot/Page/#event-javascriptDialogOpening
wb.cdpSubscribe("Page.javascriptDialogOpening",function(dlg){
/*
dlg.message 是对话框文本。
dlg.type 是对话框类型
dlg.url 对话框所在页面网址
*/

//为避免阻塞导致某些网页出现异常,应返回异步执行的函数关闭弹框。
return function(){
    //自动关闭弹框
    wb.cdp("Page.handleJavaScriptDialog",{accept=true})
} 
})

wb.html = /**
<script type="text/javascript">alert("测试弹框")</script>
**/
win.loopMessage();

Markdown 格式