Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. QtWebEngine
  4. QWebChannel - js: Uncaught ReferenceError: qt is not defined
Forum Updated to NodeBB v4.3 + New Features

QWebChannel - js: Uncaught ReferenceError: qt is not defined

Scheduled Pinned Locked Moved Solved QtWebEngine
15 Posts 8 Posters 23.7k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • M Offline
    M Offline
    maximus
    wrote on last edited by maximus
    #1

    I am trying to migrate to QtWebEngine all my code that is using QWebKit.

    in my .cpp code:

    QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
    ui->webView_workouts->page()->setWebChannel(channel);
    channel->registerObject(QString("workoutObject"), this);
    

    In my webpage: (qwebchannel.js is loaded the header of the page)

    var workoutObject;
    new QWebChannel(qt.webChannelTransport, function (channel) {
      // now you retrieve your object
      workoutObject = channel.objects.workoutObject;
    });
    

    I am getting this error :
    js: Uncaught ReferenceError: qt is not defined
    When I try to use "workoutObject" in the js, since it is not loaded correctly I get:
    js: Uncaught TypeError: Cannot read property 'filterChanged' of undefined

    Any help appreciated, currently stuck to migrate with QWebEngine..


    Free Indoor Cycling Software - https://maximumtrainer.com

    1 Reply Last reply
    0
    • M Offline
      M Offline
      maximus
      wrote on last edited by
      #2

      I tried to debug in the webpage and qt is always undefined for some reason?

      I am using latest Qt 5.7.0 on MSVC 2015

      var workoutObject;
      
      if (typeof qt != 'undefined') {
      	alert("Qt is OK!!");
      	new QWebChannel(qt.webChannelTransport, function (channel) {
              // now you retrieve your object
              workoutObject = channel.objects.workoutObject;
          });
      }
      else {
      	alert("Qt is not defined!");
      }
      

      Free Indoor Cycling Software - https://maximumtrainer.com

      1 Reply Last reply
      0
      • M Offline
        M Offline
        maximus
        wrote on last edited by
        #3

        I copied the whole content of qwebchannel.js inside my page just before "new QWebChannel..." and I do not get the error on the Qtcreator console, but still qt is undefined (get the alert message on my webpage).

        Also to note that I try to set my channel after the page is loaded, and it get triggered 2 times? I only load the URL once. I read on other forums that reloading the page could stop the channel from working, but I am unable to make it work in the first place.

        ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
        connect(ui->webView_workouts->page(), SIGNAL(loadFinished(bool)), this, SLOT(connectToJs(bool)));
        
        void Main_WorkoutPage::connectToJs(bool result) {
        
            qDebug() << "connectToJs!" << result;
            if (result) {
                QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
                ui->webView_workouts->page()->setWebChannel(channel);
                channel->registerObject(QString("workoutObject"), this);
            }
        }
        

        Free Indoor Cycling Software - https://maximumtrainer.com

        raven-worxR U 3 Replies Last reply
        0
        • SGaistS Offline
          SGaistS Offline
          SGaist
          Lifetime Qt Champion
          wrote on last edited by
          #4

          Hi,

          I haven't played with QtWebChannel yet but did you get the QtWebChannel Standalone Example to run ? That might give you some hints to go further.

          Hope it helps

          Interested in AI ? www.idiap.ch
          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

          1 Reply Last reply
          0
          • M maximus

            I copied the whole content of qwebchannel.js inside my page just before "new QWebChannel..." and I do not get the error on the Qtcreator console, but still qt is undefined (get the alert message on my webpage).

            Also to note that I try to set my channel after the page is loaded, and it get triggered 2 times? I only load the URL once. I read on other forums that reloading the page could stop the channel from working, but I am unable to make it work in the first place.

            ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
            connect(ui->webView_workouts->page(), SIGNAL(loadFinished(bool)), this, SLOT(connectToJs(bool)));
            
            void Main_WorkoutPage::connectToJs(bool result) {
            
                qDebug() << "connectToJs!" << result;
                if (result) {
                    QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
                    ui->webView_workouts->page()->setWebChannel(channel);
                    channel->registerObject(QString("workoutObject"), this);
                }
            }
            
            raven-worxR Offline
            raven-worxR Offline
            raven-worx
            Moderators
            wrote on last edited by
            #5

            @maximus
            can you show how you include the qwebchannel.js into your page.
            Are you using a custom HTML page? or are you loading a page?

            --- SUPPORT REQUESTS VIA CHAT WILL BE IGNORED ---
            If you have a question please use the forum so others can benefit from the solution in the future

            1 Reply Last reply
            0
            • M maximus

              I copied the whole content of qwebchannel.js inside my page just before "new QWebChannel..." and I do not get the error on the Qtcreator console, but still qt is undefined (get the alert message on my webpage).

              Also to note that I try to set my channel after the page is loaded, and it get triggered 2 times? I only load the URL once. I read on other forums that reloading the page could stop the channel from working, but I am unable to make it work in the first place.

              ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
              connect(ui->webView_workouts->page(), SIGNAL(loadFinished(bool)), this, SLOT(connectToJs(bool)));
              
              void Main_WorkoutPage::connectToJs(bool result) {
              
                  qDebug() << "connectToJs!" << result;
                  if (result) {
                      QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
                      ui->webView_workouts->page()->setWebChannel(channel);
                      channel->registerObject(QString("workoutObject"), this);
                  }
              }
              
              raven-worxR Offline
              raven-worxR Offline
              raven-worx
              Moderators
              wrote on last edited by
              #6

              @maximus
              Here is a way to include the webchannel stuff without worrying anymore:

              QWebEngineProfile* profile = new QWebEngineProfile("MyWebChannelProfile", parent);
              
              QFile webChannelJsFile(":/qtwebchannel/qwebchannel.js");
              if(  !webChannelJsFile.open(QIODevice::ReadOnly) )
              {
                    qFatal( QString("Couldn't open qwebchannel.js file: %1").arg(webChannelJsFile.errorString()) );
              }
              else
              {
                      QByteArray webChannelJs = webChannelJsFile.readAll();
                      webChannelJs.append( 
                               "\n"
                               "new QWebChannel(qt.webChannelTransport, function(channel) {"
                               "     workoutObject = channel.objects.workoutObject;"
                               "});"
                      );
              
                      QWebEngineScript script;
                          script.setSourceCode(webChannelJs);
                          script.setName("qwebchannel.js");
                          script.setWorldId(QWebEngineScript::MainWorld);
                          script.setInjectionPoint(QWebEngineScript::DocumentCreation);
                          script.setRunsOnSubFrames(false);
                      profile->scripts()->insert(script);
                  }
              

              Then make sure you create a QWebEnginePage with the profile on your view: new QWebEnginePage(profile,view)

              --- SUPPORT REQUESTS VIA CHAT WILL BE IGNORED ---
              If you have a question please use the forum so others can benefit from the solution in the future

              1 Reply Last reply
              1
              • M Offline
                M Offline
                maximus
                wrote on last edited by maximus
                #7

                hey @raven-worx, thanks for the reply

                I am using a custom html page that I control.
                The .js file is loaded this way:
                <script type="text/javascript" src="http://localhost/assets/js/qwebchannel.js"></script>
                I then have another <script> section at the end of my page that is creating a QWebChannel
                I can access the page source and click on the link fine to see the js file.

                Also note that I am using Designer to create my QWebEngineView so object is already instantiated in my .cpp

                I'll try loading it your way and post my result soon.
                Thanks


                Free Indoor Cycling Software - https://maximumtrainer.com

                1 Reply Last reply
                0
                • M Offline
                  M Offline
                  maximus
                  wrote on last edited by
                  #8

                  You are a lifesaver, it worked this way! Now to figure out how to strip and put this code generic because I use around 10 QWebEngineView :)

                  QWebEngineProfile *profile = new QWebEngineProfile("MyWebChannelProfile", this);
                  
                      QFile webChannelJsFile(":/qtwebchannel/qwebchannel.js");
                      if(  !webChannelJsFile.open(QIODevice::ReadOnly) ) {
                          qDebug() << QString("Couldn't open qwebchannel.js file: %1").arg(webChannelJsFile.errorString());
                      }
                      else {
                          qDebug() << "OK webEngineProfile";
                          QByteArray webChannelJs = webChannelJsFile.readAll();
                          webChannelJs.append(
                                      "\n"
                                      "var workoutobject"
                                      "\n"
                                      "new QWebChannel(qt.webChannelTransport, function(channel) {"
                                      "     workoutobject = channel.objects.workoutobject;"
                                      "});"
                                      );
                  
                          QWebEngineScript script;
                          script.setSourceCode(webChannelJs);
                          script.setName("qwebchannel.js");
                          script.setWorldId(QWebEngineScript::MainWorld);
                          script.setInjectionPoint(QWebEngineScript::DocumentCreation);
                          script.setRunsOnSubFrames(false);
                          profile->scripts()->insert(script);
                      }
                  
                      QWebEnginePage *myPage = new QWebEnginePage(profile, ui->webView_workouts);
                      ui->webView_workouts->setPage(myPage);
                  
                      QWebChannel *channel = new QWebChannel(myPage);
                      ui->webView_workouts->page()->setWebChannel(channel);
                      channel->registerObject("workoutobject", this);
                  
                      ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
                  

                  And now my .js page doesn't have anything related to Qt, really clean result.
                  Thanks a lot
                  Max


                  Free Indoor Cycling Software - https://maximumtrainer.com

                  1 Reply Last reply
                  0
                  • M Offline
                    M Offline
                    maximus
                    wrote on last edited by
                    #9

                    I am running into problem using profile->scripts()->insert(script);
                    There is conflict with multiple scripts that I insert in my shared QWebEngineProfile.
                    I use the same QWebEngineProfile on all my webpage in my application in order to keep cookie data, etc.

                    So when I insert a new script, it overwrite the last one inserted and screw up my QWebChannel initialization
                    Resulting in warning like "js: Uncaught ReferenceError: zoneObject is not defined"
                    Trying to find a solution..
                    script.setWorldId(QWebEngineScript::MainWorld); maybe set a unique worldID for each page but that doesnt seem to work now


                    Free Indoor Cycling Software - https://maximumtrainer.com

                    1 Reply Last reply
                    0
                    • M Offline
                      M Offline
                      maximus
                      wrote on last edited by
                      #10

                      Solution found, insert the script to the page instead of the profile

                      void WorkoutCreator::createWebChannel() {
                      
                          QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
                      
                          QFile webChannelJsFile(":/qtwebchannel/qwebchannel.js");
                          if(  !webChannelJsFile.open(QIODevice::ReadOnly) ) {
                              qDebug() << QString("Couldn't open qwebchannel.js file: %1").arg(webChannelJsFile.errorString());
                          }
                          else {
                              qDebug() << "OK webEngineProfile";
                              QByteArray webChannelJs = webChannelJsFile.readAll();
                              webChannelJs.append(
                                          "\n"
                                          "var workoutCreator"
                                          "\n"
                                          "new QWebChannel(qt.webChannelTransport, function(channel) {"
                                          "     workoutCreator = channel.objects.workoutCreator;"
                                          "});"
                                          "\n"
                                          "function enableSaveButton(forceOff) {"
                                          "if (forceOff) {$('#btn-save-workout').prop('disabled', true);return;}"
                                          "var nameValue = $('#name-workout').val();"
                                          "var planValue =   $('#plan-workout').val();"
                                          "var creatorValue = $('#creator-workout').val();"
                                          "if (nameValue.length > 0 && creatorValue.length > 0 && planValue.length > 0) {$('#btn-save-workout').prop('disabled', false);}"
                                          "else {$('#btn-save-workout').prop('disabled', true);}"
                                          "}"
                                          );
                      
                              QWebEngineScript script;
                              script.setSourceCode(webChannelJs);
                              script.setName("qwebchannel.js");
                              script.setWorldId(QWebEngineScript::MainWorld);
                              script.setInjectionPoint(QWebEngineScript::DocumentCreation);
                              script.setRunsOnSubFrames(false);
                              //        profile->scripts()->insert(script);
                      
                              QWebEnginePage *myPage = new QWebEnginePage(profile, ui->webView_createWorkout);
                              ui->webView_createWorkout->setPage(myPage);
                              myPage->scripts().insert(script);
                      
                              QWebChannel *channel = new QWebChannel(myPage);
                              ui->webView_createWorkout->page()->setWebChannel(channel);
                              channel->registerObject("workoutCreator", this);
                          }
                      }
                      

                      Free Indoor Cycling Software - https://maximumtrainer.com

                      M 1 Reply Last reply
                      0
                      • M maximus

                        Solution found, insert the script to the page instead of the profile

                        void WorkoutCreator::createWebChannel() {
                        
                            QWebEngineProfile *profile = QWebEngineProfile::defaultProfile();
                        
                            QFile webChannelJsFile(":/qtwebchannel/qwebchannel.js");
                            if(  !webChannelJsFile.open(QIODevice::ReadOnly) ) {
                                qDebug() << QString("Couldn't open qwebchannel.js file: %1").arg(webChannelJsFile.errorString());
                            }
                            else {
                                qDebug() << "OK webEngineProfile";
                                QByteArray webChannelJs = webChannelJsFile.readAll();
                                webChannelJs.append(
                                            "\n"
                                            "var workoutCreator"
                                            "\n"
                                            "new QWebChannel(qt.webChannelTransport, function(channel) {"
                                            "     workoutCreator = channel.objects.workoutCreator;"
                                            "});"
                                            "\n"
                                            "function enableSaveButton(forceOff) {"
                                            "if (forceOff) {$('#btn-save-workout').prop('disabled', true);return;}"
                                            "var nameValue = $('#name-workout').val();"
                                            "var planValue =   $('#plan-workout').val();"
                                            "var creatorValue = $('#creator-workout').val();"
                                            "if (nameValue.length > 0 && creatorValue.length > 0 && planValue.length > 0) {$('#btn-save-workout').prop('disabled', false);}"
                                            "else {$('#btn-save-workout').prop('disabled', true);}"
                                            "}"
                                            );
                        
                                QWebEngineScript script;
                                script.setSourceCode(webChannelJs);
                                script.setName("qwebchannel.js");
                                script.setWorldId(QWebEngineScript::MainWorld);
                                script.setInjectionPoint(QWebEngineScript::DocumentCreation);
                                script.setRunsOnSubFrames(false);
                                //        profile->scripts()->insert(script);
                        
                                QWebEnginePage *myPage = new QWebEnginePage(profile, ui->webView_createWorkout);
                                ui->webView_createWorkout->setPage(myPage);
                                myPage->scripts().insert(script);
                        
                                QWebChannel *channel = new QWebChannel(myPage);
                                ui->webView_createWorkout->page()->setWebChannel(channel);
                                channel->registerObject("workoutCreator", this);
                            }
                        }
                        
                        M Offline
                        M Offline
                        Munish
                        wrote on last edited by
                        #11

                        @maximus
                        Just wanted to know, will c++ objects (workoutCreator) available to other javascript also?
                        I am getting "undefined" error while accessing c++ object slots/function from script other than qwebchannel.js

                        S 1 Reply Last reply
                        0
                        • M Munish

                          @maximus
                          Just wanted to know, will c++ objects (workoutCreator) available to other javascript also?
                          I am getting "undefined" error while accessing c++ object slots/function from script other than qwebchannel.js

                          S Offline
                          S Offline
                          SherifOmran
                          wrote on last edited by
                          #12

                          @Munish if you checked the "enable Qt Quick compiler" in the build setting, you may get this error. I got it also.

                          1 Reply Last reply
                          0
                          • K Offline
                            K Offline
                            KWanH
                            wrote on last edited by
                            #13

                            when page finish,Run this!

                            	QString js;
                            	QFile jsFile(":/ServiceNumber/Resource/ServiceNumber/qwebchannel.js");
                            	jsFile.open(QIODevice::ReadOnly);
                            	js = jsFile.readAll();
                            	webView->page()->runJavaScript(js);
                            
                            1 Reply Last reply
                            0
                            • M maximus

                              I copied the whole content of qwebchannel.js inside my page just before "new QWebChannel..." and I do not get the error on the Qtcreator console, but still qt is undefined (get the alert message on my webpage).

                              Also to note that I try to set my channel after the page is loaded, and it get triggered 2 times? I only load the URL once. I read on other forums that reloading the page could stop the channel from working, but I am unable to make it work in the first place.

                              ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
                              connect(ui->webView_workouts->page(), SIGNAL(loadFinished(bool)), this, SLOT(connectToJs(bool)));
                              
                              void Main_WorkoutPage::connectToJs(bool result) {
                              
                                  qDebug() << "connectToJs!" << result;
                                  if (result) {
                                      QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
                                      ui->webView_workouts->page()->setWebChannel(channel);
                                      channel->registerObject(QString("workoutObject"), this);
                                  }
                              }
                              
                              U Offline
                              U Offline
                              Unicode
                              wrote on last edited by
                              #14

                              call page()->setWebChannel() before QWebEngineView::load()

                              ==>
                              .......
                              QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
                              ui->webView_workouts->page()->setWebChannel(channel);
                              channel->registerObject(QString("workoutObject"), this);
                              ......
                              ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
                              .......

                              H 1 Reply Last reply
                              1
                              • U Unicode

                                call page()->setWebChannel() before QWebEngineView::load()

                                ==>
                                .......
                                QWebChannel *channel = new QWebChannel(ui->webView_workouts->page());
                                ui->webView_workouts->page()->setWebChannel(channel);
                                channel->registerObject(QString("workoutObject"), this);
                                ......
                                ui->webView_workouts->load(QUrl(Environnement::getUrlWorkout()));
                                .......

                                H Offline
                                H Offline
                                hank_yu
                                wrote on last edited by
                                #15

                                @Unicode this way works! thank you!

                                1 Reply Last reply
                                0

                                • Login

                                • Login or register to search.
                                • First post
                                  Last post
                                0
                                • Categories
                                • Recent
                                • Tags
                                • Popular
                                • Users
                                • Groups
                                • Search
                                • Get Qt Extensions
                                • Unsolved