You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用Microsoft WebView2将动态加载的PDF保存到本地文件

解决方案:通过execScriptAsync获取WebView2中的PDF并保存

核心思路

你的页面里<embed>标签初始src是about:blank,说明PDF大概率是后续通过JavaScript动态加载的(比如Blob URL、Data URI或者PDF.js渲染)。这种情况下,可以用ExecuteScriptAsync执行前端脚本获取PDF数据,再传递到宿主程序保存到本地。

具体步骤

1. 执行脚本获取PDF数据源

先确认<embed>标签实际加载的PDF地址或数据,执行以下脚本即可:

// 获取页面中的PDF embed元素
const embed = document.querySelector('embed[type="application/pdf"]');
if (embed) {
    // 若为Blob URL,直接获取Blob内容并转为Base64传递给宿主
    if (embed.src.startsWith('blob:')) {
        fetch(embed.src)
            .then(res => res.blob())
            .then(blob => {
                const reader = new FileReader();
                reader.onloadend = () => {
                    // 通过WebView2的消息机制传递数据
                    window.chrome.webview.postMessage(reader.result);
                };
                reader.readAsDataURL(blob);
            });
    } else {
        // 若为普通URL,直接返回地址(需注意跨域限制)
        window.chrome.webview.postMessage(embed.src);
    }
}

2. 宿主程序接收数据并保存(以C#为例)

先注册WebView2的消息接收事件,再执行脚本,最后处理数据保存:

// 注册消息接收回调
webView.CoreWebView2.WebMessageReceived += CoreWebView2_WebMessageReceived;

// 执行前端脚本
await webView.CoreWebView2.ExecuteScriptAsync(@"
const embed = document.querySelector('embed[type=""application/pdf""]');
if (embed) {
    if (embed.src.startsWith('blob:')) {
        fetch(embed.src)
            .then(res => res.blob())
            .then(blob => {
                const reader = new FileReader();
                reader.onloadend = () => {
                    window.chrome.webview.postMessage(reader.result);
                };
                reader.readAsDataURL(blob);
            });
    } else {
        window.chrome.webview.postMessage(embed.src);
    }
}
");

// 处理接收到的PDF数据
private void CoreWebView2_WebMessageReceived(object sender, CoreWebView2WebMessageReceivedEventArgs e)
{
    string receivedData = e.WebMessageAsString;
    if (receivedData.StartsWith("data:application/pdf;base64,"))
    {
        // 移除Base64前缀并转为字节数组
        string pdfBase64 = receivedData.Replace("data:application/pdf;base64,", "");
        byte[] pdfBytes = Convert.FromBase64String(pdfBase64);
        // 保存到本地文件
        File.WriteAllBytes(@"C:\your\save\path\file.pdf", pdfBytes);
    }
    else
    {
        // 若收到的是普通URL,可根据需求进一步处理(但你提到WebClient受限,此分支可能暂用不上)
        Console.WriteLine($"PDF URL: {receivedData}");
    }
}

3. 关键注意事项

  • 执行时机:必须确保PDF加载完成后再执行脚本,可通过监听WebView2的NavigationCompleted事件,或前端监听<embed>的load事件后再触发数据传递。
  • 跨域限制:如果Blob URL来自跨域资源,fetch可能失败,需检查WebView2的跨域配置,或通过前端其他方式获取渲染后的PDF数据。
  • PDF.js场景:若页面用PDF.js渲染PDF,需直接从PDF.js的文档实例中提取数据,而非从<embed>标签获取。

内容的提问来源于stack exchange,提问作者Gabriel-Joy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.17 02:18:19