Community
Participate
Working Groups
This is lost (degraded) functionality, starting in 3.4.1, the following keystrokes have non-deterministic behavior: In the CU Editor: CTRL+O,g,e,t,F,o,o Sometimes, the popup outline appears and the prefix "getFoo" is recognized, but often, especially the first time invoking, such as when browsing around classes, any number of characters will be lost, which causes the search to fail (search for "tFoo", for example).
Yes, I've seen that too but also with other dialogs. Can you confirm that?
Tracked the issue down: if - for whatever reason - an asyncExec happens while the dialog is opened and the key is pressed, then that keyDown event is lost. Looks somewhat similar to bug 222281.
Test Case: 1. start the snippet 2. in the shell quickly type two numbers, e.g. 9 9 ==> dialog opens but first item instead of item starting with 9 is selected ==> second 9 is lost Now, set BUG to 'false' and repeat above steps ==> event not lost, correct item selected. /******************************************************************************* * Copyright (c) 2008 IBM Corporation and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * IBM Corporation - initial API and implementation *******************************************************************************/ package org.eclipse.swt.snippets; import org.eclipse.swt.SWT; import org.eclipse.swt.events.KeyEvent; import org.eclipse.swt.events.KeyListener; import org.eclipse.swt.widgets.Display; import org.eclipse.swt.widgets.Event; import org.eclipse.swt.widgets.Listener; import org.eclipse.swt.widgets.Shell; import org.eclipse.swt.widgets.Text; import org.eclipse.swt.widgets.Tree; import org.eclipse.swt.widgets.TreeItem; public class TreeEventsScrewedBug { private static final boolean BUG= true; public static void main(String[] args) { final Display display= new Display(); display.addFilter(SWT.KeyDown, new Listener() { public void handleEvent(Event event) { System.out.println(event); } }); final Shell shell= new Shell(display); shell.setSize(100, 100); Text b= new Text(shell, SWT.SINGLE); b.setSize(90, 90); b.addKeyListener(new KeyListener() { public void keyPressed(KeyEvent e) { Shell shell2= new Shell(shell, SWT.TOOL); Tree tree= new Tree(shell2, SWT.SINGLE); for (int i= 0; i < 2000; i++) { TreeItem item= new TreeItem(tree, 0); item.setText("" + i + " aItem " + i); } tree.setSize(100, 100); shell2.setSize(200, 200); shell2.setVisible(true); shell2.setFocus(); // FIXME: this screws the event notification if (BUG) display.asyncExec(new Runnable() { public void run() { } }); } public void keyReleased(KeyEvent e) { // TODO Auto-generated method stub } }); shell.open(); while (!shell.isDisposed()) { if (!display.readAndDispatch()) display.sleep(); } display.dispose(); } }
The problem happens because we post a message to the OS queue in asyncExec() in order to wake up the UI thread. I tried implementing wake() by signaling an event (CreateEvent()) and changing sleep() to call MsgWaitForMultipleObjectsEx() instead of WaitMessage() (adding that event as an wait object). Key events are not ignored with this implementation, but it only works for the SWT event loop. Any modal loop in the OS (i.e MessageBox, etc) would not wake properly since they do not wait on our event.
This means sync/asycnExec() would be broken when ever Window runs a modal operating system loop (message box, window resize/drag, drag detect etc.) We can't implement this solution until we have a fix for these cases.
Stopping the UI thread is not the issues for me as long as the stopped events are fired afterwards.
Silenio, is this asyncExec behavior new? We use asyncExecs in a rich text editor to queue layouts, and keystrokes don't get lost there. Daniel, has JDT always used asyncExec, or is this new in 3.4.1? Just wondering what changed between 3.4.0 and 3.4.1. What does the async do here?
>Daniel, has JDT always used asyncExec, or is this new in 3.4.1? It's not just JDT and it's not new. Same issue is in older builds too.
The following hack to the snippet flushes the events caused by constructing the Shell and assigning focus: ... shell2.setVisible(true); shell2.setFocus(); + while (display.readAndDispatch()); ...
(In reply to comment #8) > >Daniel, has JDT always used asyncExec, or is this new in 3.4.1? > It's not just JDT and it's not new. Same issue is in older builds too. > I just tried to reproduce this problem in 3.4.0 and couldn't, even when invoking CTRL+O on OS.java, keystrokes don't get lost.
>I just tried to reproduce this problem in 3.4.0 and couldn't, even when >invoking CTRL+O on OS.java, keystrokes don't get lost. It does here. Might depend on how fast you and your machine really are ;-)
RE: comment #19. I assume this "fixes" the problem too by running the key events before the asyncExec() is added? I had tried touching the event queue way down deep in the operating system to see if this helped and it didn't. Of course, running an event loop like this is a bad idea.
Any update on this one?
The fix that Silenio describes in comment #4 is not complete (won't work for operating system modal loops) and very dangerous. I'll discuss it with him but I think we are out of options.
Since the problem happens when wakeThread() is called (my interpretation of comment 4), what if you simply stop calling wakeThread()? My guess is that works unless the OS is running the event loop?
It's not that simple. Even if you are in the UI thread, you might be running from a deferred event. We are zeroing in on a fix ... stand by.
Fixed > 20090204. Please try the latest.
Verified in N20090205-2000. Thanks!
(In reply to comment #16) > It's not that simple. Even if you are in the UI thread, you might be running > from a deferred event. We are zeroing in on a fix ... stand by. You know, reading this bug reminds me that I've seen this pattern a lot in SWT: Problem is identified, discussed, then magically a "FIXED >xxx" comment gets added, but no details about the nature of the fix. This makes it hard for someone looking at the bug later (particularly, when it is discovered that the fix causes other issues ;-) ) to understand what was done. If you added a sentence that pointed us in the right direction, it would make it easier for us to know where to look when trying to understand the other interactions.