Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. QML and Qt Quick
  4. QML - signals for nested properties
Forum Updated to NodeBB v4.3 + New Features

QML - signals for nested properties

Scheduled Pinned Locked Moved Unsolved QML and Qt Quick
13 Posts 3 Posters 2.7k Views 2 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.
  • V Offline
    V Offline
    Vadi2
    wrote on last edited by
    #1

    If I have property var name; then I can use the onName signal to know when it's changed. But what about when a property is nested inside another object, what is the syntax for that?

    KroMignonK 1 Reply Last reply
    0
    • V Vadi2

      If I have property var name; then I can use the onName signal to know when it's changed. But what about when a property is nested inside another object, what is the syntax for that?

      KroMignonK Offline
      KroMignonK Offline
      KroMignon
      wrote on last edited by KroMignon
      #2

      @Vadi2 The right signal name is onNameChanged, but I don't really understand your question. Can you have a small QML code extract to show what you want to do?

      It is an old maxim of mine that when you have excluded the impossible, whatever remains, however improbable, must be the truth. (Sherlock Holmes)

      1 Reply Last reply
      0
      • V Offline
        V Offline
        Vadi2
        wrote on last edited by
        #3

        I have an object that I populate from the backend (in this case - I'm learning C# and QML at once, so the backend is in C#). What I have in QML is:

        AppModel {
            id: appmodel
        }
        

        (for the curious - it's populated from C# here)

        I can then use various properties such as appmodel.scopeDirectory, appmodel.resourceText, appmodel.dotnetResult.errorCount and so on.

        How can I trigger on appmodel.dotnetResult.errorCount changing is my exact question?

        KroMignonK 1 Reply Last reply
        0
        • V Vadi2

          I have an object that I populate from the backend (in this case - I'm learning C# and QML at once, so the backend is in C#). What I have in QML is:

          AppModel {
              id: appmodel
          }
          

          (for the curious - it's populated from C# here)

          I can then use various properties such as appmodel.scopeDirectory, appmodel.resourceText, appmodel.dotnetResult.errorCount and so on.

          How can I trigger on appmodel.dotnetResult.errorCount changing is my exact question?

          KroMignonK Offline
          KroMignonK Offline
          KroMignon
          wrote on last edited by
          #4

          @Vadi2 I still don't really understand what you want to achieve... Why do you have a C# part? do you use Qml.Net?

          What do you want to do? Is it inside AppModel component? What is AppModel?

          If you want to made public and internal state, you can do something like this, in AppModel.qml, I suppose AppModel is base on Item:

          import QtQuick 2.4
          
          Item {
          ...
              property alias errorCount: dotnetResult.errorCount
          
          }
          

          It is an old maxim of mine that when you have excluded the impossible, whatever remains, however improbable, must be the truth. (Sherlock Holmes)

          1 Reply Last reply
          0
          • V Offline
            V Offline
            Vadi2
            wrote on last edited by
            #5

            Yep, I'm using Qml.Net!

            AppModel is a component I register in C# (https://github.com/vadi2/Hammer/blob/master/Program.cs#L628), this is similar to how you register a custom component from C++ I think.

            I don't have an AppModel.qml, but I'll try the property aliases anyway...

            KroMignonK 1 Reply Last reply
            0
            • V Vadi2

              Yep, I'm using Qml.Net!

              AppModel is a component I register in C# (https://github.com/vadi2/Hammer/blob/master/Program.cs#L628), this is similar to how you register a custom component from C++ I think.

              I don't have an AppModel.qml, but I'll try the property aliases anyway...

              KroMignonK Offline
              KroMignonK Offline
              KroMignon
              wrote on last edited by
              #6

              @Vadi2 Sorry, I don't think I can help you. I never used Qml.Net and don't know what is the best way to achieve this.

              It is an old maxim of mine that when you have excluded the impossible, whatever remains, however improbable, must be the truth. (Sherlock Holmes)

              1 Reply Last reply
              0
              • GrecKoG Offline
                GrecKoG Offline
                GrecKo
                Qt Champions 2018
                wrote on last edited by GrecKo
                #7

                If your sub properties are correctly typed, you can do that:

                AppModel {
                    id: appmodel
                    dotNetResult.onErrorCountChanged: print("error count changed")
                }
                

                If the dotNetResult is a generic type (I assume it would be a QObject*, a QQmlPropertyMap* or a QVariantMap), this won't work because there is no errorCountChanged signal in the base type, even if the actual instance has one.

                A solution in this case would be to use Connections :

                Connections {
                    target: appmodel.dotNetResult
                    onErrorCountChanged: print("error count changed")
                }
                
                1 Reply Last reply
                3
                • V Offline
                  V Offline
                  Vadi2
                  wrote on last edited by
                  #8

                  @GrecKo said in QML - signals for nested properties:

                  If your sub properties are correctly typed

                  I guess they're not, it says Cannot assign to non-existent property "dotNetResult". I see that Connections doc says they're useful for Connecting to targets not defined in QML which is perhaps the case here.

                  It didn't work either unfortunately:

                  file:///home/vadi/Programs/Hammer/Main.qml:382:29: QML Connections: Cannot assign to non-existent property "onErrorCountChanged"
                  file:///home/vadi/Programs/Hammer/Main.qml:383:33: Unable to assign [undefined] to QObject*
                  

                  From reading the doc, I can put it anywhere, right?

                  GrecKoG 1 Reply Last reply
                  0
                  • V Vadi2

                    @GrecKo said in QML - signals for nested properties:

                    If your sub properties are correctly typed

                    I guess they're not, it says Cannot assign to non-existent property "dotNetResult". I see that Connections doc says they're useful for Connecting to targets not defined in QML which is perhaps the case here.

                    It didn't work either unfortunately:

                    file:///home/vadi/Programs/Hammer/Main.qml:382:29: QML Connections: Cannot assign to non-existent property "onErrorCountChanged"
                    file:///home/vadi/Programs/Hammer/Main.qml:383:33: Unable to assign [undefined] to QObject*
                    

                    From reading the doc, I can put it anywhere, right?

                    GrecKoG Offline
                    GrecKoG Offline
                    GrecKo
                    Qt Champions 2018
                    wrote on last edited by
                    #9

                    @Vadi2
                    is Main.qml:383:33: Unable to assign [undefined] to QObject* refering to the line with target: appmodel.dotNetResult?
                    Can you show us how you used Connections?

                    You should be able to use Connections anywhere yes.

                    1 Reply Last reply
                    0
                    • V Offline
                      V Offline
                      Vadi2
                      wrote on last edited by
                      #10

                      I did it both deep down in a component where I actually use appmodel.dotNetResult.errorCount successfully and at the root level:

                          AppModel {
                              id: appmodel
                          }
                      
                          Connections {
                              target: appmodel.dotNetResult
                              onErrorCountChanged: print("error count changed")
                      
                              Component.onCompleted: appmodel.testMe()
                          }
                      

                      Root level use says:

                      file:///home/vadi/Programs/Hammer/Main.qml:25:5: QML Connections: Cannot assign to non-existent property "onErrorCountChanged"
                      Writing test - errorcount is 0
                      file:///home/vadi/Programs/Hammer/Main.qml:26:9: Unable to assign [undefined] to QObject*
                      

                      I also defined a TestMe() method which prints this:

                          public void TestMe()
                          {
                            Console.WriteLine($"Writing test - errorcount is {DotnetResult.ErrorCount}");
                          }
                      

                      So we can be pretty certain the property does exist and is filled in...

                      1 Reply Last reply
                      0
                      • GrecKoG Offline
                        GrecKoG Offline
                        GrecKo
                        Qt Champions 2018
                        wrote on last edited by
                        #11

                        @Vadi2 said in QML - signals for nested properties:

                        Unable to assign [undefined] to QObject*

                        That errors means appmodel.dotNetResult is undefined, the property might incorrectly be exposed.

                        Your TestMe() test only shows that DotnetResult.ErrorCount is accessible from C#, not that it is properly exposed to QML.

                        1 Reply Last reply
                        0
                        • V Offline
                          V Offline
                          Vadi2
                          wrote on last edited by Vadi2
                          #12

                          Aha we had a typo, it should be dotnetResult and not dotNetResult. Fixing the typo so the code becomes:

                              AppModel {
                                  id: appmodel
                              }
                          
                              Connections {
                                  target: appmodel.dotnetResult
                                  onErrorCountChanged: print("error count changed")
                          
                                  Component.onCompleted: { appmodel.testMe(); console.log(`errors: ${appmodel.dotnetResult.errorCount}`) }
                              }
                          

                          I get the following output:

                          Writing test - errorcount is 0
                          qml: errors: 0
                          

                          But no notification of the change.

                          I _am_replacing DotnetResult in C# with another validation result when I get it - perhaps I shouldn't replace the object but copy/set the properties instead. I'll try it.

                          1 Reply Last reply
                          0
                          • V Offline
                            V Offline
                            Vadi2
                            wrote on last edited by
                            #13

                            No, the object replacing theory wasn't in. Before I do any validation, so appmodel.dotnetResult stays as-is, still don't get a notification with the following code:

                                AppModel {
                                    id: appmodel
                                }
                            
                                Connections {
                                    target: appmodel.dotnetResult
                                    onErrorCountChanged: print("error count changed")
                            
                                    Component.onCompleted: { appmodel.testMe(); console.log(`errors: ${appmodel.dotnetResult.errorCount}`) }
                                }
                            
                                Timer {
                                    interval: 1000; running: true;
                                    onTriggered: { appmodel.testMe(); console.log(`errors: ${appmodel.dotnetResult.errorCount}`) }
                                }
                            

                            Output:

                            Writing test - errorcount is 8
                            qml: errors: 8
                            Writing test - errorcount is 6
                            qml: errors: 6
                            

                            So the properties are accessible - but not able to be notified correctly. What techniques can I use to debug this?

                            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