简体   繁体   中英

QWebEngineView show page only upon javascript script finish

I'm developing a C++ Qt application with a web view. This is what I'm trying to do: I want to show a webpage (I don't have control on it, so I cannot modify it but I'm sure on what this page do, so don't worry for unexpected behavior) to the user, but only after running some javascript on it. The problem is I'm not able to wait for the javascript. I use Qt, QWebEngineView to load the page and to inject javascript file on it using:

void MainWindow::pageloaded(bool ok)
{
    ui->webView->page()->runJavaScript(jQuery);
    ui->webView->page()->runJavaScript(waitForKeyElement,[this](const QVariant &v) { qDebug() << v.toString();ui->webView->show();});
}

jquery is just the file jquery.min.js and waitForKeyElement is this and basically wait for elements of the page to appear in the DOM. At the end of the latter file I appended my function:

waitForKeyElements (".x-live-elements", scrollpage);
function scrollpage (jNode) {
    window.scrollTo(0, 80);
    tables = document.getElementsByClassName("x-content");
    table = tables[0];
    table.style.backgroundColor="transparent";
    document.body.style.backgroundColor = "transparent";
}

Basically when an element of the class .x-live-elements appears in the DOM, using the callback it scroll down the page and set background of a table and entire body to transparent. This is working, but I'd like to keep the page hidden until this is complete, now the user see the job running for a moment. At the beginning I call the method hide() for the webview, but how to call show() when the javascript is done ? My idea was to add this at the end of waitForKeyElement.js file:

(function (){
    while(true){
        var bodyStyle = window.getComputedStyle(document.body, null);
        var bgcolor = bodyStyle.backgroundColor;
        var transparent = 'rgba(0, 0, 0, 0)';
        if (bgcolor === transparent){
            break;
        }
    } 
    a = "done";
    return a; 
})();

When the background of the page become transparent (this is basically the last javascript instruction I need) it means that the job is done, so the function should return and callback of runJavascript invoked.. but it doesn't work. It get stuck in the while loop forever and never return, the if condition is never met. I know runJavascript is not synchronous, and the callback is fired soon as the javascript file reach the end, but with the while loop I should overcome this.. Any help ?

The best I was able to do was this:

Before running jquery and waitForKeyElement I hide the entire body

ui->webView->page()->runJavaScript("$('body').hide();");
ui->webView->page()->runJavaScript(jQuery);
ui->webView->page()->runJavaScript(waitForKeyElement);

Then in the waitForKeyElement.js my scrollpage function became:

function scrollpage (jNode) {
  tables = document.getElementsByClassName("x-content");
  table = tables[0];
  table.style.backgroundColor="transparent";
  document.body.style.backgroundColor = "transparent";
  $('body').show();
  window.scrollTo(0, 80);
}

This is of curse not the best solution, but is acceptable for my purpose.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM