nexus4 window mode mouse motion bounded incorrectly with external monitor

Bug #1488417 reported by kevin gunn
10
This bug affects 2 people
Affects Status Importance Assigned to Milestone
Canonical Pocket Desktop
Fix Released
Medium
kevin gunn
Mir
Fix Released
Medium
Unassigned
mir (Ubuntu)
Fix Released
Medium
Daniel d'Andrada
qtmir (Ubuntu)
Fix Released
Medium
Daniel d'Andrada

Bug Description

when connecting a monitor to the Nexus4 during windowed mode, the device is put into landscape mode. the mouse motion appears to not have followed the orientation and is bounded by roughly portrait width instead of landscape width

The problem is that when unity8 configures cloning, it picks the intersection of all displays. While the input subsystem uses the bounding rectangle of all displays. Thus it allows the cursor to move around in (1200x1920) while the only surface is 1080x1920. So there is a dead zone between the display extent and the surface extent. When the cursor hits that area the SurfaceInputDispatcher has no surface underneath, so it decides to not send any further mouse input to Unity8.

We can fix that by extending the behaviour of display_input_region.cpp to use the intersection of displays when necessary.

Related branches

kevin gunn (kgunn72)
tags: added: pd
Changed in qtmir (Ubuntu):
status: New → Opinion
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Might be bug 1313610, or closely related.

tags: added: cursor
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Yeah pretty sure it's the same as bug 1313610. We've never updated our cursor bounds correctly on rotation...

Revision history for this message
kevin gunn (kgunn72) wrote :

unduping for the moment, after some discussion with anpok, while this is similar we're not totally convinced it's the same

@duflu also, your are welcome please try this - specifically notice that if you move the mouse completely horizontal, the mouse will stick in a position that is inconsistent (e.g. sometimes sticks at a position further left or shorter left from the right edge than the previous time)
also, when the mouse "sticks" to a position while moving completely horizontal to the right, keep moving horizontal to the right, then move completely horizontal back to the left....the distance you travel back to the left is ~ the same before the mouse is "picked up" and "unstuck" giving it a feeling the position is changing for the mouse, however not rendering correctly.

note this is silo 0 where unity8 is doing the render - using the mir relative mouse events
to install
flash nexus4 with --channel=ubuntu-touch/rc-proposed/ubuntu
then install silo 0, unfortunately the silo is dirty holding back unity8 (atm i think) - so even if you install using ctrain tools you'll need to dist-upgrade
so....citrain device-upgrade 0 <device pin/password> , then apt-get update, apt-get dist-upgrade

Revision history for this message
kevin gunn (kgunn72) wrote :

more information i should add - this is not seen on nexus7, which in windowed mode is always in landscape and doesnt rotate
on nexus4, if a second monitor is not attached, this is not seen, even in windowed mode (which rotates to landscape, e.g. just connect a bt mouse will put into windowed mode)
but once a monitor is connected to the nexus 4, this can be seen

Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Yeah there may be some common things to fix with bug 1313610 but possibly some things different here.

Revision history for this message
Daniel van Vugt (vanvugt) wrote :

OK, I can see one problem already. While Unity8 does its own screen rotation without notifying Mir, Mir cannot do anything to help it update the cursor bounds. Because Unity8 is not telling Mir that the display has rotated, Mir will keep the old cursor bounds...

Portrait:

$ mirout /var/run/mir_socket
Connected to server: /var/run/mir_socket
Card 0: Max 2 simultaneous outputs
Output 0: Card 0, LVDS, connected, 768x1280+0+0, used, on, 61mm x 102mm (4.7"), normal
     768x1280 60.00*+
Output 1: Card 0, DisplayPort, disconnected

Landscape (incorrectly shows orientation still "normal"):

$ mirout /var/run/mir_socket
Connected to server: /var/run/mir_socket
Card 0: Max 2 simultaneous outputs
Output 0: Card 0, LVDS, connected, 768x1280+0+0, used, on, 61mm x 102mm (4.7"), normal
     768x1280 60.00*+
Output 1: Card 0, DisplayPort, disconnected

So if Unity8 is going to keep doing rotation independently of Mir, it either needs to find a way to update the Mir display config without making Mir actually apply that display config, or Unity8 do mouse movement entirely within itself using relative motion.

Changed in mir (Ubuntu):
status: New → Invalid
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Oh... is there another Mir bug too? Is Mir failing to provide continuous relative motion data without hitting invisible bounds?

Changed in mir (Ubuntu):
status: Invalid → Incomplete
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Aha! Confirmed on arale with a USB mouse and mir-demos.

Relative motion events usually work continuously, and come in even after the cursor hits the screen boundary. However Mir stops sending relative motion events if you've rotated the screen (touch+volume key in mir_proving_server) and the cursor happens to be outside of the original non-rotated dimensions. That's a Mir bug.

Changed in mir (Ubuntu):
status: Incomplete → Confirmed
Changed in mir:
status: New → Confirmed
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

My mistake. Not a Mir bug. I was looking at MIR_CLIENT_INPUT_RECEIVER_REPORT=log and expecting the client to receive motion events after the cursor had left the window, which was wrong.

Using a more correct test where the gesture starts in the app window (click but don't release), then you can see the client continues to receive relative motion data even after hitting the edge of the screen:

[1440559624.200713] <DEBUG> input-receiver: Received event:pointer_event(when=1440559624199932000 (0.685269 ms ago), from=6, motion, button_state=1, x=1919, y=1151, dx=1, dy=1, vscroll=0, hscroll=0, modifiers=1)

[1440559624.208718] <DEBUG> input-receiver: Received event:pointer_event(when=1440559624207936000 (0.687115 ms ago), from=6, motion, button_state=1, x=1919, y=1151, dx=0, dy=1, vscroll=0, hscroll=0, modifiers=1)

[1440559624.377396] <DEBUG> input-receiver: Received event:pointer_event(when=1440559624376062000 (1.160346 ms ago), from=6, motion, button_state=1, x=1919, y=1151, dx=0, dy=1, vscroll=0, hscroll=0, modifiers=1)

So Mir seems to be working properly. It even keeps sending relative motion events after the cursor has hit the edge.

Changed in mir:
status: Confirmed → Incomplete
Changed in mir (Ubuntu):
status: Confirmed → Incomplete
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Please try this:

   restart unity8 MIR_CLIENT_INPUT_RECEIVER_REPORT=log
   tail -f ~/.cache/upstart/unity8.log

and see if Unity8 actually is still receiving input events with relative data (dx, dy) when the problem occurs.

kevin gunn (kgunn72)
Changed in qtmir:
status: New → Opinion
no longer affects: qtmir
no longer affects: qtmir (Ubuntu)
kevin gunn (kgunn72)
Changed in canonical-pocket-desktop:
importance: Undecided → Critical
Changed in unity8 (Ubuntu):
importance: Undecided → Critical
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Please try comment #10 as that should help us to identify if the problem is on the Mir side or Unity8.

Changed in canonical-pocket-desktop:
status: New → Incomplete
Changed in unity8 (Ubuntu):
status: New → Incomplete
Revision history for this message
Daniel d'Andrada (dandrader) wrote :

I will investigate the claim that qtmir is still receiving relative mouse movement even when you see the cursor hitting an invisible boundary

no longer affects: unity8 (Ubuntu)
Changed in qtmir (Ubuntu):
assignee: nobody → Daniel d'Andrada (dandrader)
status: New → In Progress
Revision history for this message
Daniel d'Andrada (dandrader) wrote :

Mir keeps sending pointer events after it hits a boundary only if you're using the primary display. If you connect and external monitor, it doesn't work like that anymore.

Steps to reproduce:
- Flash an N7 and install silo0 in it.
- Add "initctl set-env --global QT_LOGGING_RULES=qtmir.mir.input.debug=true" to /usr/share/upstart/sessions/unity8.conf
- sudo restart lightdm
- in a phablet terminal: tail -f ~/.cache/upstart/unity8.log
- connect a bluetooth mouse and check the output, you should see a lot of entries like "qtmir.mir.input: Received MirPointerEvent(x=971,y=573,relative_x=-1,relative_y=0)"
- see that the mouse goes through the entire screen and you always get mouse events even when the pointer reaches a boundary
- now conenct an external monitor and see what happens

expected outcome:
mouse events keep coming like before

actual outcome:
you have invisible boundaries since mouse events stop coming when the pointer reaches some width and height boundary.

Note that the cursor you see on the screen is drawn by unity8 and it's driven solely by the relative movement in MirPointerEvents.

Revision history for this message
Daniel d'Andrada (dandrader) wrote :

To get the debug output you've to make sure your qtmir is at least lp:~unity-team/qtmir/silo0 revision 369 ("QtEventFeeder: log the pointer events it gets from Mir")

Changed in qtmir (Ubuntu):
status: In Progress → Invalid
Changed in mir:
status: Incomplete → Confirmed
Changed in mir (Ubuntu):
status: Incomplete → New
Changed in mir:
status: Confirmed → New
Changed in canonical-pocket-desktop:
status: Incomplete → New
Changed in mir (Ubuntu):
assignee: nobody → Daniel van Vugt (vanvugt)
Changed in mir:
assignee: nobody → Daniel van Vugt (vanvugt)
Changed in mir (Ubuntu):
importance: Undecided → Critical
Changed in mir:
importance: Undecided → Critical
Changed in qtmir (Ubuntu):
importance: Undecided → Critical
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Can you double check using the report in comment #10? It's still theoretically a small possibility that the bug lies in unity8 till that's confirmed.

Changed in mir:
status: New → Incomplete
Changed in mir (Ubuntu):
status: New → Incomplete
Changed in mir:
importance: Critical → High
assignee: Daniel van Vugt (vanvugt) → nobody
Changed in mir (Ubuntu):
importance: Critical → High
assignee: Daniel van Vugt (vanvugt) → nobody
Revision history for this message
Daniel van Vugt (vanvugt) wrote :
summary: - nexus4 window mode mouse motion bounded incorrectly
+ nexus4 window mode mouse motion bounded incorrectly with external
+ monitor
tags: added: android multimonitor
Revision history for this message
Daniel d'Andrada (dandrader) wrote :

@duflu

There you go:
http://paste.ubuntu.com/12213056/

When you hit the invisible boundary on the external monitor nothing comes up in the log. Neither from mir nor qtmir. Happy now? :)

Changed in mir (Ubuntu):
status: Incomplete → New
Changed in mir:
status: Incomplete → New
Changed in mir (Ubuntu):
assignee: nobody → Daniel d'Andrada (dandrader)
status: New → In Progress
description: updated
Revision history for this message
Daniel d'Andrada (dandrader) wrote :

Now we know what the problem is, and it will be gone once qtmir+unity8 start using one surface per display instead of cloning displays as it's currently happening.

Changed in mir (Ubuntu):
status: In Progress → New
Changed in qtmir (Ubuntu):
status: Invalid → New
Revision history for this message
kevin gunn (kgunn72) wrote :

yep, like daniel said we'll lower priority on this since qtmir multimonitor branch is getting cleaned up and landed.

Changed in canonical-pocket-desktop:
importance: Critical → Medium
Changed in mir:
importance: High → Medium
Changed in mir (Ubuntu):
importance: High → Medium
Changed in qtmir (Ubuntu):
importance: Critical → Medium
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Comment #18 kind of makes sense.

In trying to replicate the bug using just Mir demos I found one way to do it: Have a client (which in our case is Unity8 itself) that fails to resize to cover all displays. As it fails to resize to cover all displays, the client (Unity8 shell) will fail to get motion events that are outside of its window.

So this problem can be solved in Unity8 by resizing the Unity8 Mir surface to cover all displays, or it can be solved more reliably with a Mir enhancement (which we plan on already) --> implement pointer grabs so that the cursor location does not ever stop the owning surface from receiving pointer events.

Either way, seems like Mir is working correctly. In the absence of pointer grab support, clients (including Unity8) stop getting pointer events when the cursor leaves their window.

Changed in mir:
status: New → Invalid
Changed in mir (Ubuntu):
status: New → Invalid
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

Actually there might still be a related bug in Mir. Seems unlikely, but not really sure yet.

Changed in mir:
status: Invalid → New
Changed in mir (Ubuntu):
status: Invalid → New
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

I'm fairly sure this bug is invalid for Mir per comment #20. Although pointer grabs in Mir would help to solve the problem, that's really an enhancement for later. In comment #21 I was just being cautious in case anyone can correct me.

Revision history for this message
Launchpad Janitor (janitor) wrote :

Status changed to 'Confirmed' because the bug affects multiple users.

Changed in mir (Ubuntu):
status: New → Confirmed
Changed in qtmir (Ubuntu):
status: New → Confirmed
Revision history for this message
Daniel van Vugt (vanvugt) wrote :

I've found the same kind of bug, but no external monitor required --> bug 1502805.

Revision history for this message
kevin gunn (kgunn72) wrote :

this is fixed in silo 22 which should land soon

Changed in qtmir (Ubuntu):
status: Confirmed → In Progress
Changed in canonical-pocket-desktop:
status: New → In Progress
assignee: nobody → kevin gunn (kgunn72)
Revision history for this message
Daniel d'Andrada (dandrader) wrote :

Actually input still gets in a pretty sorry state when an external monitor is connected.
But waiting for silo 22 to land before raising the issue to mir guys. Will make for easier debugging and communication.

Revision history for this message
kevin gunn (kgunn72) wrote :

seems corrected in latest image
channel: ubuntu-touch/rc-proposed/ubuntu-pd
version version: 54
version ubuntu: 20151026
version device: 20150911
version custom: 20150929-2-vivid

Changed in canonical-pocket-desktop:
status: In Progress → Fix Released
Changed in mir (Ubuntu):
status: Confirmed → Fix Released
Changed in qtmir (Ubuntu):
status: In Progress → Fix Released
Changed in qtmir:
status: New → Fix Released
Changed in mir:
status: New → Fix Released
Michał Sawicz (saviq)
no longer affects: qtmir
To post a comment you must log in.
This report contains Public information  
Everyone can see this information.

Other bug subscribers

Remote bug watches

Bug watches keep track of this bug in other bug trackers.