Bug 406520 - Qt's WinTab impl may map wrong screen geometry on some devices
Summary: Qt's WinTab impl may map wrong screen geometry on some devices
Status: RESOLVED FIXED
Alias: None
Product: krita
Classification: Applications
Component: Tablets (tablet issues are only very rarely bugs in Krita!) (show other bugs)
Version: git master (please specify the git hash!)
Platform: Microsoft Windows Microsoft Windows
: NOR normal
Target Milestone: ---
Assignee: Dmitry Kazakov
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2019-04-14 06:34 UTC by Alvin Wong
Modified: 2019-04-16 10:23 UTC (History)
0 users

See Also:
Latest Commit:
Version Fixed In:
Sentry Crash Report:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Alvin Wong 2019-04-14 06:34:36 UTC
This issue is specific to Qt's WinTab implementation with the mouse mode hack disabled in Qt (from 6806b44ec2122eb6b8ff531d5bf94e89d0dc31cc).

Qt assumes the WinTab coordinates are mapped to the whole virtual screen, but this is not true for all WinTab driver implementations, and thus will cause tablet offset for some users.

Tested on a SP5 with Microsoft's WinTab driver, with a secondary monitor attached:

This setup works fine on Krita 4.1.7. The following is the debug output from the WinTab code:

[8300] krita.tabletlog: # Getting current context data:
[8300] krita.tabletlog: lc.lcName = 0x5fbf30
[8300] krita.tabletlog: lc.lcDevice = 0
[8300] krita.tabletlog: lc.lcInOrgX = 0
[8300] krita.tabletlog: lc.lcInOrgY = 0
[8300] krita.tabletlog: lc.lcInExtX = 9600
[8300] krita.tabletlog: lc.lcInExtY = 7200
[8300] krita.tabletlog: lc.lcOutOrgX = 0
[8300] krita.tabletlog: lc.lcOutOrgY = 0
[8300] krita.tabletlog: lc.lcOutExtX = 9600
[8300] krita.tabletlog: lc.lcOutExtY = -7200
[8300] krita.tabletlog: lc.lcSysOrgX = 0
[8300] krita.tabletlog: lc.lcSysOrgY = 0
[8300] krita.tabletlog: lc.lcSysExtX = 2736
[8300] krita.tabletlog: lc.lcSysExtY = 1824
[8300] krita.tabletlog: Qt Desktop Geometry QRect(0,0 4656x1815)
[8300] qtDesktopRect = QRect(0,0 4656x1815)
[8300] wintabDesktopRect = QRect(0,0 2736x1824)

You can see that the WinTab driver maps the tablet input only to the primary screen, which voids Qt's assumption.

Testing with a fresh build of 70ac5d1466cc286273e17186f91a13fa515c3e51 with the same setup, there is a huge offset with pen input.
If I run this build with the env var `QT_WINTAB_DESKTOP_RECT=0;0;2736;1824", the WinTab input works.

This doesn't necessarily mean that `lcSys*` will always give the correct mapping, but IMO it does show the need for some users to conveniently set the screen mapping if it goes wrong.
Comment 1 Dmitry Kazakov 2019-04-15 09:55:16 UTC
Hi, Alvin!

Could you please generate me an output of lc.lcSysOrgX and lc.lcSysOrgY, when your mapped screen is set *at the right* from the external display?

Therefore it's origin should be somewhere at QPoint(1920, 0). I'm wondering if your wintab driver will report that correctly.
Comment 2 Dmitry Kazakov 2019-04-15 11:01:01 UTC
Git commit 31c48ac7bf2a4831ade764fc7eba4776e0e56f7b by Dmitry Kazakov.
Committed on 15/04/2019 at 11:00.
Pushed by dkazakov into branch 'master'.

Fetch tablet mapping from Wintab instead virtual screen geometry

Some devices, like Microsoft Surface Pro 5, don't map tablet's
input range to the entire virtual screen area, but map it to
the primary display that has actual built-in tablet sensor.

In such cases we should fetch actualy mapped aread from Wintab's
lcSys{Org,Ext}{X,Y} fields and use it for cursor mapping.

The patch also introduces an environment variable switch that
falls back to the old method of mapping:

QT_IGNORE_WINTAB_MAPPING=1

When the variable is set, the scaling is done via virtual desktop
area only.

A  +171  -0    3rdparty/ext_qt/0027-Fetch-tablet-mapping-from-Wintab-instead-virtual-scr.patch
M  +1    -0    3rdparty/ext_qt/CMakeLists.txt

https://commits.kde.org/krita/31c48ac7bf2a4831ade764fc7eba4776e0e56f7b
Comment 3 Alvin Wong 2019-04-15 14:43:53 UTC
Output from 4.1.7 with external monitor as secondary and put to the left of the SP5 display:

[15112] krita.tabletlog: # Getting current context data:
[15112] krita.tabletlog: lc.lcName = 0x5fbf30
[15112] krita.tabletlog: lc.lcDevice = 0
[15112] krita.tabletlog: lc.lcInOrgX = 0
[15112] krita.tabletlog: lc.lcInOrgY = 0
[15112] krita.tabletlog: lc.lcInExtX = 9600
[15112] krita.tabletlog: lc.lcInExtY = 7200
[15112] krita.tabletlog: lc.lcOutOrgX = 0
[15112] krita.tabletlog: lc.lcOutOrgY = 0
[15112] krita.tabletlog: lc.lcOutExtX = 9600
[15112] krita.tabletlog: lc.lcOutExtY = -7200
[15112] krita.tabletlog: lc.lcSysOrgX = 0
[15112] krita.tabletlog: lc.lcSysOrgY = 0
[15112] krita.tabletlog: lc.lcSysExtX = 2736
[15112] krita.tabletlog: lc.lcSysExtY = 1824
[15112] krita.tabletlog: Qt Desktop Geometry QRect(-1920,0 3288x1815)
[15112] qtDesktopRect = QRect(-1920,0 3288x1815)
[15112] wintabDesktopRect = QRect(0,0 2736x1824)

Note that in this case the external monitor has a negative offset, so the SP5 display is still at (0,0).

---

Output from 4.1.7 with external monitor set as *primary* and SP5 display as secondary:

[4680] krita.tabletlog: # Getting current context data:
[4680] krita.tabletlog: lc.lcName = 0x5fbf30
[4680] krita.tabletlog: lc.lcDevice = 0
[4680] krita.tabletlog: lc.lcInOrgX = 0
[4680] krita.tabletlog: lc.lcInOrgY = 0
[4680] krita.tabletlog: lc.lcInExtX = 9600
[4680] krita.tabletlog: lc.lcInExtY = 7200
[4680] krita.tabletlog: lc.lcOutOrgX = 0
[4680] krita.tabletlog: lc.lcOutOrgY = 0
[4680] krita.tabletlog: lc.lcOutExtX = 9600
[4680] krita.tabletlog: lc.lcOutExtY = -7200
[4680] krita.tabletlog: lc.lcSysOrgX = 0
[4680] krita.tabletlog: lc.lcSysOrgY = 0
[4680] krita.tabletlog: lc.lcSysExtX = 1920
[4680] krita.tabletlog: lc.lcSysExtY = 1080
[4680] krita.tabletlog: Qt Desktop Geometry QRect(0,-735 3288x1815)
[4680] qtDesktopRect = QRect(0,-735 3288x1815)
[4680] wintabDesktopRect = QRect(0,0 1920x1080)

The WinTab driver erroneously report the primary monitor (i.e. the external monitor) as the tablet screen mapping.
Comment 4 Dmitry Kazakov 2019-04-16 10:23:22 UTC
Should be fixed in (there is a custom settings for such cases)
https://phabricator.kde.org/R37:71371bbc48f5251af326a6fae70ec3fe2247c60c