Uploaded image for project: 'Qt'
  1. Qt
  2. QTBUG-83599

Signal parameter referenced in a JS closure is undefined while QML debugger is attached

    XMLWordPrintable

Details

    • Bug
    • Resolution: Done
    • P1: Critical
    • 6.0, 6.1.0 Alpha
    • 5.12, 5.13, 5.14.2, 5.15.1, 6.0.0 Beta5
    • QML: Tooling
    • Windows 10
    • All
    • bad85119bf35468292cfd80ecc934b66515f0c68 (qt/qtdeclarative/dev) 37c290c5b8659256ff574a06a3df2c363ae446b5 (qt/qtdeclarative/5.15)

    Description

      The following erroneous behavior mainfests only while the QML debugger is attached. Whether a C++ debugger is attached or not, does not affect this. As a result, code that works outside debugger, does not work while debugging. This hinders debugging of logic code in QML and workarounds are needed in certain situations.

      When a QML signal on a different item is handled using the Connections item, signal parameters that are captured in a JS closure within the signal handler are undefined.

      Under these conditions, when the closure is executed, the QML runtime reports the following error and execution stops at the line where the signal parameter is referenced.

      ReferenceError: 'signal_parameter_name' is not defined.

       

      The following code reproduces this behavior when the QML debugger is attached:

      Item {
          Item {
              id: logic
      
              signal doSomething(var text)
          }
      
          Item {
              id: handler
      
              Connections {
                  target: logic
      
                  onDoSomething: { // handles signal: logic.doSomething(var text)
                      handler.callCallback(function(){
                          console.log("Arg value captured in closure:", text) // ERROR: ReferenceError: text is not defined.
                          console.log("You will not see this line logged when QML debugger is attached")
                      })
                  }
              }
      
              function callCallback(callback) {
                  callback()
              }
          }
      }
      

       

      A workaround can be applied: reference the signal parameter outside / before the closure and store its value in a local variable, reference the local variable in the closure instead:

                  onDoSomething: { // handles signal: logic.doSomething(var text)
                      var v_text = text
                      handler.callCallback(function(){
                          console.log("Arg value captured in closure with workaround:", v_text)
                      })
                  }
      

       

       Steps to reproduce:

      1. Open the attached project in Qt Creator.
      2. In Project settings -> Build and Run -> Run Settings: make sure Enable QML debugging is checked.
      3. Build the project in debug mode.
      4. Start debuggin the project (press F5).
      5. Click the button in the QML example to fire the signal.
      6. Observe the error in the output window:
        ReferenceError: text is not defined.
        This error only manifests while using the QML debugger and should not happen, as this is a valid JS code.

      Attachments

        No reviews matched the request. Check your Options in the drop-down menu of this sections header.

        Activity

          People

            ulherman Ulf Hermann
            martin_ky Martin Kutny
            Votes:
            4 Vote for this issue
            Watchers:
            5 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved:

              Gerrit Reviews

                There are no open Gerrit changes