Java Solaris Communities Sun Store Join SDN My Profile Why Join?
 
Bug Database
Bug Detail
Quick Lists
Top 25 Bugs
Top 25 RFE's
Recently Closed Bugs
Printable Page Printable Page


Bug Database
Bug ID: 4199374
Votes 206
Synopsis Component.requestFocus() fails for components on JWindow.
Category java:classes_awt
Reported Against 1.2.2 , 1.2fcs
Release Fixed 1.3.0_02
State 10-Fix Delivered, Verified, bug
Priority: 2-High
Related Bugs 4232086 , 4662240 , 4851685
Submit Date 22-DEC-1998
Description




Focus management appears to be handled differently in JWindow and JFrame as the following example shows.  The sample code attempts to
create a JFrame with a JButton that, when pressed, creates a JWindow with a JTextField.  It then attempts to give the JTextField focus immediately
after it is displayed.

In practice, the field never receives focus.  Trying to set focus to the window yields interesting, but unhelpful results (the field gets and loses focus
before the window does.)  Setting focus on a timer doesn't do the trick.  I also have a nasty workaround that works on Win32 but not Solaris, but that
really isn't any better.

The attempt to transfer focus works flawlessly if the field is placed in a JFrame as implemented using the commented out code in the sample below,
so it seems clear that JWindow is somehow failing to provide proper focus management.

  import java.awt.event.*;
  import javax.swing.*;
  public class Test {
    public static void main(String args[]) {
      JFrame frame = new JFrame();
      JButton button = new JButton("Test");
      frame.getContentPane().add(button);
      frame.pack();

      frame.addFocusListener(new NoisyFocusListener("Frame"));
      button.addFocusListener(new NoisyFocusListener("Button"));

      button.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
          JWindow window = new JWindow();
  //        JFrame window = new JFrame();
          JTextField field = new JTextField("Edit Me!");
          window.getContentPane().add(field);
          window.pack();

          field.addFocusListener(new NoisyFocusListener("Field"));
          window.addFocusListener(new NoisyFocusListener("Window"));

          window.setVisible(true);
          field.requestFocus();
        }
      });
      frame.setVisible(true);
    }

    static class NoisyFocusListener implements FocusListener {
      private String name;
      public NoisyFocusListener(String name) {
        this.name = name;
      }
      public void focusGained(FocusEvent e) {
        System.out.println(name + (e.isTemporary() ? " got temporary focus." : " got focus."));
      }
      public void focusLost(FocusEvent e) {
        System.out.println(name + (e.isTemporary() ? " lost temporary focus." : " lost focus."));
      }
    }
  }
(Review ID: 48582)
======================================================================

This bug turns out to be a show stopper for a shipping SAP application.
They worked around it by shipping their application on 1.1.6.
They run in  xxxxx  problems now which are fixed in higher releases!
This bug is now a show stopper for a shipping, revenue generating 
commercial Java application (Hotel management).

Merlin beta is far out and unacceaptable

Regards

Stefan Schneider


 xxxxx@xxxxx  1999-11-12

This is also causing an accessibility problem for JavaHelp V1.1 popups in the ContentViewer. We cannot adequately test the code to verify a correct fix for setting focus to the popup.
Work Around
N/A
Evaluation
First, note that this is a different problem than the corresponding (solaris) problem that involves only heavyweight components. A fix for the heavyweight problem will not automatically fix this one, I don't think. The lightweight problem occurs on both platforms; the heavyweight one (for which there are other bug reports filed) occurs only on Solaris.

I think that the problem here is the following code in Container.java's proxyRequestFocus method:

	    if (dispatcher.setFocusRequest(c)) {
                Component window = this;
                while (!(window instanceof Window))
                    window = window.getParent();

                if (((Window)window).isActive()) {
                    peer.requestFocus();
		    }

The problem here is that if the lightweight requesting focus is placed inside a Window that's not a Frame or Dialog, then dipatcher.setFocusRequest will return true (because the Window never actually should have focus -- instead, the Frame or Dialog that owns it should get the key events and dispatch them to the Window when appropriate). Then the first loop will find the containing Window, but it will never be active, since Windows are never active, only the Frames that own them are. So the requestFocus will never happen, which is okay, because Windows aren't supposed to get keyboard events directly. But what needs to then happen instead is that keyboard events that go to the owning Frame need to be passed to the lightweight in the owned Window -- for that, I think that the owning Frame's setFocusRequest needs to be called to set the "focus" field to the appropriate lightweight in the owned Window. Or some such.

 xxxxx@xxxxx  1999-02-09

We have been unable to track down the bug. We will have to revisit this for
kestrel.
 xxxxx@xxxxx  1999-04-05

06/24/1999  xxxxx@xxxxx : This bug is reproducible with JDK 1.2.2 under solaris 2.6. This does not have a lot of votes (count : 18) in bug parade. This could be fixed in kestrel, but does not seem important at least from customer/user perspective.

Not true. It has 66 votes and is on the top 25. We will definitely target it
for kestrel.
 xxxxx@xxxxx  1999-07-30

CTE is developing a 1.2.2 patch for this bug, but the patch will not be put into 
an actual SDK release. As with all CTE patches, it will be available only to
specific customers through the escalation process.

The focus rewrite in merlin will address this bug in a more elegant and robust
fashion.
 xxxxx@xxxxx  2000-02-29

This bug is not fixed. The CTE patch which fixes this bug is available only on Windows, and is not generally available even on that platform. In addition,
the patch is only a temporary fix. As I stated above, a complete fix for this
bug will not be available until merlin.

In the future, please contact a bug's responsible engineer before closing it.
 xxxxx@xxxxx  2000-05-10
Comments
  
  Include a link with my name & email   

Submitted On 22-FEB-1999
flaggg
Forgot to mention in my previous note:
Focus works just as expected in JDK1.1.6.


Submitted On 22-FEB-1999
flaggg
I am experiencing the same problem.  
Here is some very simple sample code that can demonstrate the issue:
import javax.swing.*;
//
//
// Main
//
//
public class Main {
   public static void main(String[] args) {
      JWindow container = new JWindow();
      container.setSize(640, 480);
      container.getContentPane().setLayout(null);
      JTextField t1 = new JTextField("name");
      t1.setBounds(100, 100, 100, 25);
      container.getContentPane().add(t1);
      JTextField t2 = new JTextField("password");
      t2.setBounds(100, 200, 100, 25);
      container.getContentPane().add(t2);
      container.setVisible(true);
   }
}
When you click on either of the textfields no cursor appears, but the textfield
will receive keyboard events.
I can reproduce this with JDK1.2 and JDK1.1.7b
Please fix this ASAP.  We would really like to be able to take advantage of 1.2,
 but can't if focus doesn't transfer properly within a JWindow.


Submitted On 26-MAY-1999
smithaj
We have found a reasonable work around to this:
Extend JTextField and override requestFocus and grabFocus as follows...
public void requestFocus()
{
  super.requestFocus();
  if (fJTextField != null)
    fJTextField.getCaret().setVisible(false);
  fJTextField = this;
  getCaret().setVisible(true);
}
public void grabFocus()
{
  super.grabFocus();
  if (fJTextField != null)
    fJTextField.getCaret().setVisible(false);
  fJTextField = this;
  getCaret().setVisible(true);
}
fJTextField in this case is a class member in a containing class (our extension
is an inner class), basically something to track which component has focus.
Hope this helps people until a proper fix arrives.


Submitted On 22-JUN-1999
chrisburkey
This work around is not a good one. Because the focus
events are not run. All you this does is turn on the caret.


Submitted On 07-JUL-1999
chrisburkey
This bug is important. This focus problem in JWindows means that
You can't create a product such as WinAmp or any borderless popup 
with data entry on them.
It looks like a top 25 bug!


Submitted On 11-JUL-1999
sequel
I encourage everyone that needs this bug fixed to <strong>cast your vote
on Bug Id 4150988</strong>.
SUN, I hope that before anyone tries to rewrite code to get around the problem
you fix the REAL bug in the AWT.
There are now three bug reports for the same problem. Bug Id 4128659, 4150988,
and 4150988.


Submitted On 16-JUL-1999
torelli
I have found other strange behaviors of JWindow. 
If you add a FocusListener on a JWindow, the 
listener don't receive any FocusEvent, but if you
add the FocusLister on a component in the JWindow 
too, the listener receive the event on the 
JWindow! 

If you execute JWindow.requestFocus(), it happens 
this sequence of events on JWindow:
1)permanent focus gained
2)permanent focus lost
3)permanent focus gained
Why I get three events instead of only one event 
(focus gained)?  


Submitted On 31-JUL-1999
rootss
I run into the same problem and I saw this workaround:
http://www.codeguru.com/java/articles/446.shtml
It works great for me.


Submitted On 06-AUG-1999
chrisburkey
That work around does not solve this problem. Because if there is more than one
JTextField you can't even tab between them. In fact, even if you use your mouse
to click inside one it still does not take focus!


Submitted On 06-OCT-1999
chrisburkey
In reading the review from 1999-02-09 it indicates that all JWindows need to
have an owning JFrame. Then how can we use a JWindow as a top level container?
For example, I need to create an initial login screen with no Frame.


Submitted On 23-NOV-1999
Roland1753
I have the same problem as chris above.It would be nice if JWindow were a top
level component.


Submitted On 24-NOV-1999
JROSEN
I think the main problem of this bug is that the VM doesn't send the message
"WindowEvent.WINDOW_ACTIVATED" to JWindow. So JWindow doesn't
"know" that it is active and it cannot handle the focus correctly.
I have tried out this workaround and it worked fine in my application (insert
these lines into the constructor of the JWindow-Class):
setVisible(true);   // make it visible first
requestFocus();     // the window is active now
dispatchEvent(new WindowEvent(
  this, WindowEvent.WINDOW_ACTIVATED));


Submitted On 05-FEB-2000
DanielMichalik
In jdk1.3 RC1 still persists. I cant place textfield into JWindow


Submitted On 17-FEB-2000
bst5qi
"because the Window never actually should have focus -- 
 instead, the Frame or Dialog that owns it should get the key
 events and dispatch them to the Window when appropriate"

This seems the idea/spec of Window activation aso.
I don't agree; why should a Window behave differently from
Frame or Dialog concerning activation, focussing aso!!!???

On Windows at least if you click on a Window with the mouse
the parent Frame's title bar is deactivated (see background color),
so my intuition says that the Window should get activated.
But in the current implementation neither Window or Frame
is activated which is surely an invalid AWT state.


Submitted On 29-FEB-2000
fordmi
As of this writing, bug 4199374 has 178 votes, 4254005 has 27, 4186928 has 39, and who knows how many other 
bugs are duplicates! This makes it the 3rd most reqested bug fix. 

The cleanest and easiest workaround is to subclass JWindow and add the following code in the constructor. It took 
me days to figure this out!


addFocusListener(new FocusListener() {
  public void focusLost(FocusEvent e) { }
  public void focusGained(FocusEvent e) {
    dispatchEvent(new WindowEvent(this, WindowEvent.WINDOW_ACTIVATED));
  }
});


In bug #4186928, jhtpenttech arrived at the same conclusion and gives a detailed explaination why.


Submitted On 09-MAY-2000
chrisburkey
According to this press release: http://java.sun.com/products/jdk/1.2/CHANGES-1.2.2_005.html#5
this bug is fixed. Then why is it still labeled "In progress, bug"?


Submitted On 12-SEP-2000
a_petkov
:))))
Hi all i don't know if the bug is fixed but here is my solution.
You all call JWindows method setVisible(true)
this metod is supposed to replace the metod show()
but some how he could not fully replace it so 
you shold when use JWindow's method setVisible(true) to call after him show()
here is an example :
public class Blq {
  public JWindow window;
  ...
  ...
  
  window.setVisible(true);
  window.show();
  ...
  ...
  
}

after this when you call requestFocus() method of some of window's componets it wil work properly


Submitted On 19-APR-2001
cornwellsb
This works

private void setTextFocus(){
	    SwingUtilities.invokeLater(new Runnable(){
	        public void run(){
	              txtBox.requestFocus();
	        }
	    });
	}


Submitted On 18-MAY-2001
langles
Apparently this bug was fixed ... for a while. In the
release notes for the newly released JDK1.3.1,
http://java.sun.com/j2se/1.3/relnotes.html#awt

Bug 4199374 concerns a focus management problem with JWindow
objects. In particular, this bug prevents
Component.requestFocus() from giving focus to components in
a JWindow. This bug was fixed in update releases J2SDK
1.2.2_05 and J2SDK 1.3.0_02. However, it is not fixed in
J2SDK 1.3.1.


Submitted On 02-NOV-2001
krishnars
for me... i wanted to use textfiled.requestFocus(); in 
focusLost(Focusevent e) method if that textfield validation 
is wrong. no way it is not reseting to the sameTextfield on 
jdk1.2.2.

But i got solution...from cornwell...thanks

It works with....calling this method in FocusLost method

private void setTextFocus(){
	    SwingUtilities.invokeLater(new Runnable(){
	        public void run(){
	              txtBox.requestFocus();
	        }
	    });
	}

It is working fine right now on 1.2.2 also.
Is there any problems in future ? and is there any better 
work-arrounds?



PLEASE NOTE: JDK6 is formerly known as Project Mustang