Priority: P2: Important
Affects Version/s: 5.15, 6.2
Component/s: QPA: X11/XCB
Environment:ubuntu 19.04 deepin 20
xorg-server 1.20.4 libxkbcommon 0.8.2-1
Commits:ef94aeef649f832bb201cb752407ce3ea5e66562(dev) 379198828c (qt/qtbase/6.4) 379198828c (qt/tqtc-qtbase/6.4)
I have a scanner, When using a Qt program to input, if the second character is uppercase, the first lowercase character will be converted to a character with shift during the first scan.
On my computer, using xdotool I can also reproduce this phenomenon. see error.mp4 and xdotool.sh
the video show the reproduce step:
- open a Qt program and type some character to make sure the keyboard is master device;
- then run xdotool.sh and active Qt window, select QLineEdit all text, wait xdotool input;
- you will see the first character is error.
a. reproduce this bug to make sure the second character is uppercase;
b. xdotool sometime maybe can't reproduce,but scanner always exist.
- when use xdotool or scanner input, first of all, xorg-server will call CopyKeyClass and send XkbSendNewKeyboardNotify event to Qt program;
- when Qt program recvice this event, Qt will call updateKeymap, see Qt code: qtbase/src/plugins/platforms/xcb/qxcbkeyboard.cpp updateKeymap function;
- in the updateKeymap function, Qt will call libxkbcommon to reset xkbState, and this time, libxkbcommon will return Qt a new xkbState, but the value base_mods of xkbState's is not right;
If you switch input between the keyboard and the scanner, this bug will reappear immediately
- When xorg-server send XkbSendNewKeyboardNotify event, Qt and libxkbcommon communicate will spend some time;
- If Qt didn't initialized yet, and shift if pressed, and this time xorg-server will give libxkbcommon a error base_mods value of xkbState's.
a. If you increase the scanner input delay between characters, the probability of recurrence will decrease；
b. If xorg-server not send XkbSendNewKeyboardNotify event, this bug don't reproduce;
c. if xorg-server send XkbSendNewKeyboardNotify event, but Qt do nothing, this bug don't reproduce too;