RFR: 8314906: [testbug] Create behavior tests for text input controls [v5]

Andy Goryachev angorya at openjdk.org
Mon Sep 18 20:24:48 UTC 2023


On Mon, 18 Sep 2023 19:59:30 GMT, Martin Fox <duke at openjdk.org> wrote:

>> Merci, Monsieur Fox!
>> 
>> We seem to have quite a few tickets in this area (who created the first one in the list?):
>> 
>> * [JDK-8278924](https://bugs.openjdk.org/browse/JDK-8278924) [Linux] Robot key test can fail if multiple keyboard layouts are installed
>> * [JDK-8022079](https://bugs.openjdk.org/browse/JDK-8022079) [macosx] swing shortcuts are counterintuitive with non-english keyboard layouts
>> * [JDK-8087915](https://bugs.openjdk.org/browse/JDK-8087915) Mac: accelerator doesn't take into account azerty keyboard layout
>> * [JDK-4760902](https://bugs.openjdk.org/browse/JDK-4760902) java.awt.Robot can't generate % character on FRENCH keyboard
>> 
>> Not only we get key events for wrong characters, but also shortcut(A) generates `character = q, text = , code = UNDEFINED, metaDown, shortcutDown]` which closes the test app :-(
>> 
>> I have no idea how to fix this test...  We could try to introduce a translation layer to emit the right sequences (for each keyboard layout), or, alternatively, we could skip the tests altogether for non-US keyboard, except ... there seems to be no easy way to determine the keyboard layout?  (There are some suggestions involving InputContext or JNI on stackoverflow).  We could also try to skip the test if Locale.getDefault is other than Locale.US, not sure if that would solve the issue.
>> 
>> What do you think?
>
> The problem you're running into here isn't due to any bug in JavaFX. The way KeyCodes identify keys works well for defining accelerators but not for using a Robot to generate a specific printable character. As an extreme example, if you're using a Greek keyboard there will be a key that has KeyCode.Z assigned to it so you can use Shortcut+Z to invoke Undo. But that key will generate a Greek letter when pressed by a human or a Robot.
> 
> You can probably assume that anyone running these tests is using a Latin/Roman keyboard that can generate the lower-case letters a-z so one approach is to just stick to those characters in the typing tests. The other is to try to identify the layout using a Robot. For example, send KeyCode.DIGIT1 and see if that generates a '1'. If not you're probably on a French layout.
> 
> Punctation and symbols are hopeless, there's just too much variation in the keyboard layouts.
> 
>> Not only we get key events for wrong characters, but also shortcut(A) generates `character = q, text = , code = UNDEFINED, metaDown, shortcutDown]` which closes the test app :-(
> 
> Could you provide more details (platform, keyboard, keyboard layout, etc.)? On the Mac PR #425 cleaned all this up in jfx21.

I am running this on macOS 13.5.1 with several keyboard layouts enabled.

A test that does keyPress(KecCode.A) followed by a keyRelease(KeyCode.A) generates the following sequence of events:

With the US layout:


KeyEvent [source = TextArea at 7da926e[styleClass=text-input text-area], target = TextArea at 7da926e[styleClass=text-input text-area], eventType = KEY_PRESSED, consumed = false, character = , text = a, code = A]
KeyEvent [source = TextArea at 7da926e[styleClass=text-input text-area], target = TextArea at 7da926e[styleClass=text-input text-area], eventType = KEY_TYPED, consumed = false, character = a, text = , code = UNDEFINED]
KeyEvent [source = TextArea at 7da926e[styleClass=text-input text-area], target = TextArea at 7da926e[styleClass=text-input text-area], eventType = KEY_RELEASED, consumed = false, character = , text = a, code = A]


With the French layout:


KeyEvent [source = TextArea at 75ffb50a[styleClass=text-input text-area], target = TextArea at 75ffb50a[styleClass=text-input text-area], eventType = KEY_PRESSED, consumed = false, character = , text = q, code = A]
KeyEvent [source = TextArea at 75ffb50a[styleClass=text-input text-area], target = TextArea at 75ffb50a[styleClass=text-input text-area], eventType = KEY_TYPED, consumed = false, character = q, text = , code = UNDEFINED]
KeyEvent [source = TextArea at 75ffb50a[styleClass=text-input text-area], target = TextArea at 75ffb50a[styleClass=text-input text-area], eventType = KEY_RELEASED, consumed = false, character = , text = q, code = A]


And with a cyrillic layout it generates whatever cyrillic letter is mapped to the key.  So, basically, KeyCode is more like a scan code, which means there is no reliable way to test key bindings using Robot, unless we limit ourselves (and the test) to the US layout.  Or is there another way?

<img width="612" alt="Screenshot 2023-09-18 at 13 19 51" src="https://github.com/openjdk/jfx/assets/107069028/8bd8745c-8973-449f-bf17-0473f5c0e0b6">

-------------

PR Review Comment: https://git.openjdk.org/jfx/pull/1221#discussion_r1329233409


More information about the openjfx-dev mailing list