Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Qt6] Drawer element blocks mouseClick #54

Open
prototypicalpro opened this issue Mar 9, 2022 · 12 comments
Open

[Qt6] Drawer element blocks mouseClick #54

prototypicalpro opened this issue Mar 9, 2022 · 12 comments

Comments

@prototypicalpro
Copy link
Contributor

I have a strange bug that I'm trying to wrap my head around. When using spix (modified to print the mouse events) with a minimal QML application on Qt6 everything works as expected:

ApplicationWindow {
    id: window
    visible: true

    Button {
        id: clickMe
        onClicked: console.log("clicked");
        text: "A Special Button"
    }
}
s = xmlrpc.client.ServerProxy('http://localhost:9000')
s.mouseClick("window/clickMe")
print(s.getErrors())
# Qt
Starting minimalDrawerBug...
QML debugging is enabled. Only use this in a safe environment.
QMouseEvent(MouseButtonPress LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
QMouseEvent(MouseButtonRelease LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
qml: clicked

# python
[]

When I update the QML application to include a Drawer element, however, spix is unable to click on the element:

ApplicationWindow {
    id: window
    visible: true

    Button {
        id: clickMe
        onClicked: console.log("clicked");
        text: "A Special Button"
    }
    
    // I tested placing drawer both before and after button
    Drawer {
        id: drawer
    }
}
# Qt
Starting minimalDrawerBug...
QML debugging is enabled. Only use this in a safe environment.
QMouseEvent(MouseButtonPress LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
QMouseEvent(MouseButtonRelease LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))

# python
[]

I am still able to click the button with normal mouse interaction, but spix seems unable to replicate the same behavior using synthetic events. As far as I can tell spix is generating the same MouseEvent in both cases, so maybe it has something to do with how Drawer interacts with mouse events?

I'm on Ubuntu 20.04, Qt 6.2.3 and the latest spix from master (modified slightly to print mouse events). I'd be happy to post the full project that I test with if that's helpful.

@faaxm
Copy link
Owner

faaxm commented Mar 11, 2022

I have had some issues with the synthetic events in more complex cases, like drag&drop, where Qt seems to work directly with system events and not with the QEvents in its own queue. But that this would be caused by just adding a Drawer seems odd...

What happens if you use pyAutoGUI to create the events on the system level?
If you post the code, I can have a look...

@prototypicalpro
Copy link
Contributor Author

prototypicalpro commented Mar 14, 2022

Interaction with pyAutoGui seems to work. Test script:

import xmlrpc.client
import time
import pyautogui

def clickItem(path):
    # from https://github.com/faaxm/spix/blob/master/examples/RemoteCtrl/script/autogui.py
    # Query spix to get the location of the item
    bounds = s.getBoundingBox(path)
    # bounds = [x, y, width, height] as list
    center_x = bounds[0] + bounds[2] / 2
    center_y = bounds[1] + bounds[3] / 2

    # use pyautogui to move the cursor...
    pyautogui.moveTo(center_x, center_y, duration=1)
    # ...and click
    pyautogui.click()

s = xmlrpc.client.ServerProxy('http://localhost:9000')
print('Test synthetic click')
time.sleep(1)
s.mouseClick("window/clickMe")
print(s.getErrors())
time.sleep(1)

print('Test autogui click')
time.sleep(1)
clickItem("window/clickMe")
print(s.getErrors())
print('done')

Log without drawer:

Starting minimalDrawerBug...
QML debugging is enabled. Only use this in a safe environment.
QMouseEvent(MouseButtonPress LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=844,1400 dev=QPointingDevice("core pointer" Mouse id=1))
QMouseEvent(MouseButtonRelease LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=844,1400 dev=QPointingDevice("core pointer" Mouse id=1))
qml: clicked
qml: clicked

Log with drawer:

Starting minimalDrawerBug...
QML debugging is enabled. Only use this in a safe environment.
QMouseEvent(MouseButtonPress LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=1121,1226 dev=QPointingDevice("core pointer" Mouse id=1))
QMouseEvent(MouseButtonRelease LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=1121,1226 dev=QPointingDevice("core pointer" Mouse id=1))
qml: clicked

If you could take a look at the project that would be great, I am thoroughly stumped: minimalDrawerBug.zip. Let me know if you have any questions.

@faaxm
Copy link
Owner

faaxm commented Mar 24, 2022

Sorry for the long wait, I had less time to look into this than I had hoped...
For now, I only had a quick look and have tested this with Qt5 as that is still my default version. With that version, I found that it seems to work as expected.

The output I get is:

# Qt
$ ./examples/Basic/SpixBasicExample
qml: clicked
qml: clicked

# python
$ python3 test_click.py 
Test synthetic click
[]
Test autogui click
[]
done

The synthetic click also works when running the app with -platform minimal.

@prototypicalpro prototypicalpro changed the title Drawer element blocks mouseClick [Qt6] Drawer element blocks mouseClick Mar 29, 2022
@MelodicsPavol
Copy link
Contributor

MelodicsPavol commented Feb 27, 2023

Hi there, very similar (or maybe same) problem is happening with our app, using quite complex UI elements. Spix works great with Qt 5.15.10 but all generated QEvents have no effect in Qt 6.4.2.

Note that some of the constructors that Spix is using (e.g. QMouseEvent are deprecated since Qt 6.4) but they should still work. Any idea how to solve this problem? The generated events pass through installed event filter, but maybe are not delivered to the receiver.

Update:
The unit tests work with Qt 6.4.2 and if I use same QML contents from the tests in our app, it works as well.

@MelodicsPavol
Copy link
Contributor

I've found through debugging that the issue was caused by an inactive Popup item attached to an Overlay and thus blocking mouse events. Interestingly regular mouse clicks worked, so did the pyautogui solution.

@chruetli
Copy link

Hi there, I have the same problem. My UI has a drawer on it which seems to block the mouse events. As soon as i replace the drawer everything works. Disabling, or modifying any property doensn't help to have the mouse clicks come through. I'm using Qt 6.5.0.
Any ideas how to work with this?

@auxxos
Copy link

auxxos commented Jun 24, 2024

I think, it is related to how mouse events are simulated. In the current SPIX version, they are fired on windows level. I have changed this to component level in my SPIX version. You can then adress the target component directly and the events are working even underneath a drawer.

There is a corresponding pull request (#101), but it is still open.

@chruetli
Copy link

I think, it is related to how mouse events are simulated. In the current SPIX version, they are fired on windows level. I have changed this to component level in my SPIX version. You can then adress the target component directly and the events are working even underneath a drawer.

There is a corresponding pull request (#101), but it is still open.

Thanks for the hint. But for me it still doesn't work. Maybe I didn't something wrong using your commit. Anyway, did you try your changes it with the example given by @prototypicalpro in the first post?

@auxxos
Copy link

auxxos commented Jun 24, 2024

Just tried it, and it works with my version.

If I define WINDOW_MODE in QtEvents.cpp the code in the first post is not working. If I use my changes, it works as expected.

Check, if you have the changes in QtEvents.cpp to switch between the old and my new mode.

@chruetli
Copy link

Hmm, in my case undefining WINDOW_MODE is even worse. I have the following structure:
Window/Item/Rectangle/Item/TabBar/contentItem/TabButton
Clicking on a TabButton doesn't work, I don't get any click event. If i define WINDOW_MODE I get the click event as long as the Drawer is not present.

@auxxos
Copy link

auxxos commented Jun 25, 2024

In a TabBar you have to give unique ids or objectNames to the TabButtons to be able to address them.

Should not work properly in both event modes, I guess.

@chruetli
Copy link

Hmm, in my case undefining WINDOW_MODE is even worse. I have the following structure: Window/Item/Rectangle/Item/TabBar/contentItem/TabButton Clicking on a TabButton doesn't work, I don't get any click event. If i define WINDOW_MODE I get the click event as long as the Drawer is not present.

Sorry for the confusion, the path I mentioned was just the object path. The id/objectName path is mainWindow/controlBar/controlBackground/controlBarItem/tabBar/contentItem/controlButtonMenu. The drawer is at Window/Item/Drawer (mainWindow/statusIndicator/statusDrawer)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants