How can I use a function from an external/custom .js file with QWebEngineView?



  • Hello guys,

    I am sure this is something simple, but I just can't figure out how to use the "w3IncludeHTML()" function from the "w3data.js" file. It works in a normal browser page though.

    EDIT: this is my NEW index.html, to match with my "marked as solved" post

    //<!DOCTYPE html>
    <html lang="en" dir="ltr">
      <head>
        <meta charset="utf-8">
        <link rel="stylesheet" type="text/css" href="styles.css">
        <!--
        <script type="text/javascript" src="qrc:/scripts/script/w3data.js"></script>
        -->
        <script src="qrc:///qtwebchannel/qwebchannel.js"></script>
      </head>
      <body>
        <div class="page">
          <div id="first_page">
    
          </div>
    
        </div>
    
        <div class="page">
          <div id="last_page">
    
          </div>
          <div class="text" id="attrid">
          </div>
        </div>
    
    
        <script type="text/javascript">
          var updateattribute=function(text)
          {
            var string = document.getElementById("attrid").innerHTML;
            string = string + text;
            document.getElementById("attrid").innerHTML = string;
            //$("#attrid").val(text);
          }
          new QWebChannel(qt.webChannelTransport, function(channel){
            var webobj = channel.objects.webobj;
            window.webobj = webobj;
            webobj.sendText.connect(updateattribute);
          });
        </script>
      </body>
    </html>
    
    

    In the w3data.js is the function:

    function w3IncludeHTML(cb) {
      var z, i, elmnt, file, xhttp;
      z = document.getElementsByTagName("*");
      for (i = 0; i < z.length; i++) {
        elmnt = z[i];
        file = elmnt.getAttribute("w3-include-html");
        if (file) {
          xhttp = new XMLHttpRequest();
          xhttp.onreadystatechange = function() {
            if (this.readyState == 4 && this.status == 200) {
              elmnt.innerHTML = this.responseText;
              elmnt.removeAttribute("w3-include-html");
              w3IncludeHTML(cb);
            }
          }
          xhttp.open("GET", file, true);
          xhttp.send();
          return;
        }
      }
      if (cb) cb();
    

    If I use an incorrect path, QT complains about "Uncaught ReferenceError: w3IncludeHTML is not defined". So it does find the definition of "w3IncludeHTML()" with the right path but does not execute it.

    I tried:

    QFile script_file(":/scripts/script/w3data.js");
    script_file.open(QIODevice::ReadOnly);
    QString script = QString::fromLatin1(script_file.readAll());
    script_file.close();
    view->page()->runJavaScript(script);       // QWebEngineView *view is in my header file;
    view->page()->runJavaScript("w3IncludeHTML();");
    

    I also tried to figure out this tutorial: https://doc.qt.io/qt-5/qtwebengine-webenginewidgets-contentmanipulation-example.html

    But I don't understand the relationship between their jQuery file and functions like:

    QString code = QStringLiteral("qt.jQuery('a').each( function () { qt.jQuery(this).css('background-color', 'yellow') } )");
    view->page()->runJavaScript(code);
    

    I think it definitely has something to do with the append here:

     QFile file;
     file.setFileName(":/jquery.min.js");
     file.open(QIODevice::ReadOnly);
     jQuery = file.readAll();
     jQuery.append("\nvar qt = { 'jQuery': jQuery.noConflict(true) };");   // what does this mean?
     file.close();
    

    But I cannot figure out what this does, unfortunately the jQuery file itself is very unreadable.

    Thank you for your time :)



  • Ok so I managed to import the html by modeling my code similar to the example with:

    QString code = QStringLiteral("qt.jQuery('#first_page').load('html/first_page.html');");
    
    //you can even nest it with:
    QString code = QStringLiteral(
                    "qt.jQuery('#first_page').load('html/first_page.html', ()=>{"
                        "qt.jQuery('#border_content').load('html/border_content.html', ()=>{"   //some other html
                            "qt.jQuery('#last_page').load('html/last_page.html');"
                            "});"
                        "});"
                    );
    

    unfortunately I now cannot use the qwebchannel.js script anymore and my css gets screwed :(
    even loading it with:

    QFile script_file(":/qtwebchannel/qwebchannel.js");
    if(!script_file.open(QIODevice::ReadOnly))
         qDebug()<<"Couldn't load Qt's QWebChannel API!";
    QString qt_script = QString::fromLatin1(script_file.readAll());
    script_file.close();
    view->page()->runJavaScript(qt_script);
    

    did not help. Since it is a small project and I am on a short deadline right now I will put everything in one html file and mark this question als solved.



  • Hi,

    jQuery.append("\nvar qt = { 'jQuery': jQuery.noConflict(true) };");
    

    it says that jQuery will use jQuery instead of $ for refrence it to jquery framework stuff,
    this line it appends at the end of the file content readed

    for have a jquery readeable you can download the jquery.js not the jquery.min.js



  • Hey,

    thanks for the reply ;)

    Ok I will look into the jQuery API and JavaScript tutorials to understand the "WebEngine Content Manipulation Example" better.



  • Ok so I managed to import the html by modeling my code similar to the example with:

    QString code = QStringLiteral("qt.jQuery('#first_page').load('html/first_page.html');");
    
    //you can even nest it with:
    QString code = QStringLiteral(
                    "qt.jQuery('#first_page').load('html/first_page.html', ()=>{"
                        "qt.jQuery('#border_content').load('html/border_content.html', ()=>{"   //some other html
                            "qt.jQuery('#last_page').load('html/last_page.html');"
                            "});"
                        "});"
                    );
    

    unfortunately I now cannot use the qwebchannel.js script anymore and my css gets screwed :(
    even loading it with:

    QFile script_file(":/qtwebchannel/qwebchannel.js");
    if(!script_file.open(QIODevice::ReadOnly))
         qDebug()<<"Couldn't load Qt's QWebChannel API!";
    QString qt_script = QString::fromLatin1(script_file.readAll());
    script_file.close();
    view->page()->runJavaScript(qt_script);
    

    did not help. Since it is a small project and I am on a short deadline right now I will put everything in one html file and mark this question als solved.