如何在 DotNetBrowser 中打印之前等待挖空页面完成加载?

How to wait for knockout page to finish loading before printing in DotNetBrowser?

我正在尝试使用 DotNetBrowser 使用如下代码进行打印:

    public void PrintUrl(string url)
    {
        using (var browser = BrowserFactory.Create())
        {
            browser.PrintHandler = this;
            _waitEvent = new ManualResetEvent(false);

            browser.FinishLoadingFrameEvent += (sender, e) => 
            {
                if (e.IsMainFrame)
                {
                    browser.Print();
                }
            };

            browser.LoadURL(url);
            _waitEvent.WaitOne();
        }
    }

    public PrintStatus OnPrint(PrintJob printJob)
    {
        printJob.PrintJobEvent += (sender, args) => _waitEvent.Set();
        return PrintStatus.CONTINUE;
    }

我尝试打印的页面是用 Knockout 呈现的。 HTML 元素绑定到 Javascript Knockout 模型。当执行 Javascript 并更新 HTML 时,模型被初始化。

我只得到一个空白页。

我假设发生的是主框架的 FinishLoadingFrameEvent 在执行 Javascript 之前被触发 - 要么 - 该事件在 Javascript 执行之后但在绑定的 HTML 元素更新之前触发。

我可以通过在打印调用之前添加以下代码来使打印工作:

        browser.FinishLoadingFrameEvent += (sender, e) => 
        {
            if (e.IsMainFrame)
            {
                // executing javascript seems to update the DOM
                browser.ExecuteJavaScriptAndReturnValue("window"); 
                browser.Print();
            }
        };

调用 ExecuteJavaScriptAndReturnValue 似乎有效,但我不知道这是否可靠。是否有可靠的方法让 DOM 根据底层 KO 模型进行更新?

该页面本身包含一个调用 ko.applyBindings() 的脚本块,如果我执行它而不是 "window",它似乎也可以工作。

这个靠谱吗?感觉像个黑客。

似乎 DOM 模型是在页面加载后生成的。在这种情况下,DotNetBrowser 报告页面已加载但内容尚未由 Knockout 库更新。

这种情况的选项很少。

选项 1:

如您所述执行'ko.ApplyBindings()'。执行该方法后,应加载网页内容并准备打印。

选项 2:

通知 .NET 端有关内容已使用 JS-.NET Bridge 加载。在这种情况下,您需要将 .NET 对象注入 Javascript。该对象应包含启动打印的方法。 DOM加载后,Knockout应该调用这个方法。