Bug 46059 - Can't use focus listener to select all text
Summary: Can't use focus listener to select all text
Status: RESOLVED WORKSFORME
Alias: None
Product: Platform
Classification: Eclipse Project
Component: SWT (show other bugs)
Version: 3.0   Edit
Hardware: PC Linux-GTK
: P3 normal (vote)
Target Milestone: ---   Edit
Assignee: Grant Gayed CLA
QA Contact:
URL:
Whiteboard:
Keywords:
Depends on:
Blocks: 46380 185693
  Show dependency tree
 
Reported: 2003-11-04 15:21 EST by Douglas Pollock CLA
Modified: 2020-12-02 04:21 EST (History)
2 users (show)

See Also:


Attachments
Snippet showing problem (1.31 KB, text/plain)
2003-11-04 15:23 EST, Douglas Pollock CLA
no flags Details

Note You need to log in before you can comment on or make changes to this bug.
Description Douglas Pollock CLA 2003-11-04 15:21:56 EST
I would like a text widget that selects all of its text when it gains focus. 
This doesn't appear to be currently supported by SWT.
Comment 1 Douglas Pollock CLA 2003-11-04 15:23:43 EST
Created attachment 6654 [details]
Snippet showing problem

1.) Run snippet
2.) Select left text box with the mouse.


OBSERVED RESULTS:
Selection expands to all of the text, and then reduces to just the cursor.


DESIRED RESULTS:
Selection expands to all of the text, and stays that way.
Comment 2 Douglas Pollock CLA 2003-11-04 15:25:41 EST
On Windows XP, the text isn't visibly selected at all.
Comment 3 Douglas Pollock CLA 2003-11-05 18:23:54 EST
This is a complicated problem (from my perspective), and it may be that there is
a way to do it with the existing framework.

Sometimes I want focus to arrive at the widget and have all the text selected. 
This would happen if the user clicks in the widget, or tabs into the widget
themselves.  However, if I programmatically set the focus into the widget, then
I don't want the text selected.  (While in my case I don't ever want the text
selected when focus is set programmatically, I could see a case where a
developer may want to chose one or the other.)

Comment 4 Grant Gayed CLA 2003-11-10 14:52:39 EST
I think the following addresses all cases well...

public static final void main(final String[] args) {
	final Display display = new Display();
	final Shell shell = new Shell(display);
	shell.setLayout(new RowLayout());
	final Text text1 = new Text(shell, SWT.NULL);
	text1.setText("Set focus, but select all fails."); //$NON-NLS-1$
	Listener listener = new Listener() {
		public void handleEvent(Event event) {
			text1.selectAll();
		}
	};
	text1.addListener(SWT.FocusIn, listener);
	text1.addListener(SWT.MouseUp, listener);
	final Text text2 = new Text(shell, SWT.NULL);
	text2.setText("Use me to change focus."); //$NON-NLS-1$
	text2.setFocus();
	shell.pack();
	shell.open();
	while (!shell.isDisposed()) {
		if (!display.readAndDispatch()) display.sleep();
	}
	display.dispose();
}
Comment 5 Douglas Pollock CLA 2003-11-10 17:00:00 EST
Close, but no cigar.  It's my fault for not specifying all the scenarios.

1.) User tabs into widget -> SELECT ALL
2.) User bring focus to widget by clicking on it -> SELECT ALL
3.) User clicks in widget after focus is already on widget -> POSITION CURSOR
4.) User brings focus to widget by clicking on it and dragging to select text 
(all in one action) -> SELECT TEXT
5.) Program sets focus to the widget -> DO NOT MODIFY SELECTION

The snippet provided I know fails on #3, and it might fail on #4 and #5 as 
well.
Comment 6 Douglas Pollock CLA 2003-12-02 15:13:45 EST
What is the status of this bug?
Comment 7 Douglas Pollock CLA 2003-12-09 15:18:02 EST
Grant: this is blocking a bug that I'd like to wrap up for M6.  It causes
accessibility problems on the keys preference page.  Any chance this will be
looked at before M6?
Comment 8 Grant Gayed CLA 2003-12-09 15:32:22 EST
I'll look at it with SN after the OS X ctrl+space bug.
Comment 9 Grant Gayed CLA 2003-12-10 12:46:54 EST
I don't know how I didn't think of this before.  You need to asyncExec 
text1.setSelection(...) so that it's done last.

The only place that this doesn't work is occasionally on gtk (~25% of time) 
when the MouseUp is execut after the async'd text.setSelection(...) for some 
reason.  So I still need to look into this event ordering problem.
Comment 10 Douglas Pollock CLA 2003-12-10 12:52:41 EST
So, same as comment #4, but with:

    text1.selectAll();

changed to ...

    display.asyncExec(new Runnable() {
        public void run() {
            text1.selectAll()
        }
    });


But this doesn't work on GTK due to an event ordering problem.  So, will Bug 
46380 have to wait until post-M6?
Comment 11 Grant Gayed CLA 2003-12-10 13:15:01 EST
The snippet that I used was the one that you originally attached, with the 
asyncExec added, so:

text1.addFocusListener(new FocusAdapter() {
	public void focusGained(FocusEvent e) {
		display.asyncExec(new Runnable() {
			public void run() {
				text1.setSelection(0, text1.getText().length());
			}
		});
	}
});

I'm looking into the gtk event ordering case, and will update here this 
afternoon.
Comment 12 Douglas Pollock CLA 2003-12-10 15:54:41 EST
My last bug for M6.  I wait with bated breath....  ;)
Comment 13 Grant Gayed CLA 2003-12-10 16:07:37 EST
I've been looking at this with SN, and it's a timing-related problem: gtk is 
sometimes deferring processing the mouse events for too long.  If 
text1.setSelection(...) is async'd, it shouldn't be possible for it to be 
performed before MouseUp, since these don't run until the event queue is 
empty.  Seeing it sometimes run before MouseUp is received shows the delay 
that's happening in the widget, which is removing the selection that was just 
made.  There isn't anything we can do here.

So I'm looking into ways to make the snippet work, and the only one I've found 
so far is to Thread.sleep(100) in the FocusIn callback before doing the 
asyncExec, which is a pretty bad thing...
Comment 14 Douglas Pollock CLA 2003-12-10 16:12:44 EST
Okay, fair enough.  I would have liked to have this fixed for M6, but it can 
wait until M7.  From the sounds of things, we wouldn't be able to get 
something reliable by M6 anyway.
Comment 15 Douglas Pollock CLA 2004-01-12 15:03:19 EST
Just looking at my own bug list, and making a peep to make sure this is still
being looked at.
Comment 16 Douglas Pollock CLA 2004-01-30 11:13:35 EST
Just looking at my own bug list, and making a peep to make sure this is still
being looked at.
Comment 17 Grant Gayed CLA 2004-01-30 14:04:25 EST
I've revisited this, and here's what's new:

1. After playing on gtk more, it appears that when the mouseUp comes in late 
it's not from being deferred in gtk, but is a direct response to the length of 
the user's click (the margin is pretty small here).  So SWT is actually 
behaving correctly here, though this wasn't my previous thought.

2. SSQ pointed out something interesting, that the FocusIn/MouseUp order only 
makes a difference on gtk if the text at the click point is already selected, 
otherwise it matches the other platforms.  It's not clear if this is a gtk bug 
or expected behaviour.  Anyways, I was able to make the snippet consistently 
work, irrespective of the length of the user click, by doing a clearSelection() 
on the field when it lost focus.  In some contexts this would be odd, but if 
the field is going to have its selection set to its full text on its next 
FocusIn anyways then it doesn't make a difference visually.

Since I don't know your full context for this, can you try this on your end and 
report here whether this is an acceptable solution?
Comment 18 Douglas Pollock CLA 2004-01-30 15:19:20 EST
The context is the keys preference page.  The user needs to be able to tab
traverse from a Text field on to a Button, do some work, and then tab back to
the Text field.  If you play around a bit, you can probably see how a person
using only the keyboard cannot enter a sequence like: "Esc Backspace 0".

From the sounds of things, clearSelection() might be a workable solution.  I'll
play around with it now.
Comment 19 Douglas Pollock CLA 2004-01-30 15:50:28 EST
Okay, I can't seem to get this to work.  Can you show me a simple working
snippet?  The set up should be a Text and Button widget -- using only the
keyboard to navigate.  Type some text in the widget, tab traverse out, tab
traverse back.  In a more complex variant of this, I'm getting all of the text
in the widget selected.  If I could see a simple working case, then I might be
able to do something.
Comment 20 Grant Gayed CLA 2004-01-30 16:01:11 EST
Sure, it's the previous snippet but with the focusOut listener added, and the 
second text changed to a button to more closely reflect your case.

public static final void main(final String[] args) {
	final Display display = new Display();
	final Shell shell = new Shell(display);
	shell.setLayout(new RowLayout());
	final Text text1 = new Text(shell, SWT.NULL);
	text1.setText("Set focus, but select all fails."); //$NON-NLS-1$
	text1.addFocusListener(new FocusAdapter() {
		public void focusGained(FocusEvent e) {
			display.asyncExec(new Runnable() {
				public void run() {
					text1.setSelection(0, text1.getText
().length());
				}
			});
		}
		public void focusLost(FocusEvent e) {
			text1.clearSelection();
		}
	});
	final Button button = new Button(shell, SWT.PUSH);
	button.setText("Use me to change focus."); //$NON-NLS-1$
	button.setFocus();
	shell.pack();
	shell.open();
	while (!shell.isDisposed()) {
		if (!display.readAndDispatch()) display.sleep();
	}
	display.dispose();
}
Comment 21 Douglas Pollock CLA 2004-02-11 10:32:24 EST
With your comments, work and some fiddling, I got something workable for my
situation.  Thanks.
Comment 22 Grant Gayed CLA 2004-02-13 16:26:07 EST
Nothing for swt to do here, so closing report.
Comment 23 Kim Horne CLA 2007-05-07 12:44:54 EDT
Is there an adequate workaround for OS X?  This is currently breaking our filtered tree implementation.
Comment 24 Eric Williams CLA 2016-08-17 14:06:12 EDT
(In reply to Kim Horne from comment #23)
> Is there an adequate workaround for OS X?  This is currently breaking our
> filtered tree implementation.

If this bug is still an issue, please file a separate bug against SWT-OSX/Cocoa for this issue. Marking this bug as fixed, see comments for the solution.