2

I have a QML component with buttons, ... in it. I put a MouseArea which covers this entire component because I need to execute an action wherever I click on the component. However, I also want to execute the action behind the MouseArea.

For example, if I click on a button in the component, I want to execute the MouseArea action and then the button action.

Item {

  Button{
    anchors: ...
    onClicked: console.info("Button clicked")
  }

  MouseArea{
    anchors.fill: parent
    propagateComposedEvents: true
    onClicked: console.info("MouseArea clicked")
  }
}

If propagateComposedEvents: true, then MouseArea onClicked is not executed, but Button onClicked is. If false, MouseArea is executed but not Button onClicked.

I want to have both MouseArea (first) and Button (second) signal onClicked to be executed.

3
  • I think you can just call buttonId.clicked() in reaction to the clicked-signal of the MouseArea
    – derM
    Commented Oct 30, 2019 at 11:40
  • Indeed, it could be the solution but I don't have only one button. I have much more components behind the MouseArea and I can't put each action inside the MouseArea clicked signal.
    – SteveTJS
    Commented Oct 30, 2019 at 13:27
  • Then, maybe, describe what you actually want to achieve. Because maybe, the MouseArea is not your solution
    – derM
    Commented Oct 30, 2019 at 15:14

1 Answer 1

4

You just need to set the accepted property of the mouse to false.

Item {

  Button{
    anchors: ...
    onClicked: console.info("Button clicked")
  }

  MouseArea{
    anchors.fill: parent
    propagateComposedEvents: true
    onClicked: {
        console.info("MouseArea clicked");
        mouse.accepted =false;
  }
}

From MouseArea documentation:

If propagateComposedEvents is set to true, then composed events will be automatically propagated to other MouseAreas in the same location in the scene. Each event is propagated to the next enabled MouseArea beneath it in the stacking order, propagating down this visual hierarchy until a MouseArea accepts the event. Unlike pressed events, composed events will not be automatically accepted if no handler is present.

If you want to exclusively catch mouse click on one of them, just move the MouseArea under Button regarding its z level. Or, just move its definition before the Button.

Item {
  MouseArea{
    anchors.fill: parent
    onClicked: console.info("MouseArea clicked")
  }

  Button{
    anchors: ...
    onClicked: console.info("Button clicked")
  }
}

OR:

Item {
  Button{
    anchors: ...
    onClicked: console.info("Button clicked")
    z: 1
  }

  MouseArea{
    anchors.fill: parent
    onClicked: console.info("MouseArea clicked")
    z: 0
  }
}
0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.