JDK-8154043 : Fields not reachable anymore by tab-key, because of new tabbing behaviour of radio button groups.
  • Type: Bug
  • Component: client-libs
  • Sub-Component: javax.swing
  • Affected Version: 7u80,8u40,9
  • Priority: P3
  • Status: Resolved
  • Resolution: Fixed
  • OS: windows_7
  • CPU: x86_64
  • Submitted: 2016-04-11
  • Updated: 2016-10-13
  • Resolved: 2016-09-26
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 9
9 b140Fixed
Related Reports
Duplicate :  
Relates :  
Relates :  
Relates :  
Relates :  
Description
FULL PRODUCT VERSION :
JDK1.8.0_66

ADDITIONAL OS VERSION INFORMATION :
Window 7

A DESCRIPTION OF THE PROBLEM :
In one of the last JDK 1.8 versions the tabbing behaviour for radio button groups was changed. 
See e.g. https://bugs.openjdk.java.net/browse/JDK-8033699

Now, under circumstances, some focusable fields are not reachable anymore.

For example:

<Radio Button 1> <Radio Button 2> <Textarea 1>
<Radio Button 3> <Radio Button 4> <Textarea 2>
<Radio Button 7> <Radio Button 6> <Textarea 3>

The focus will always jump to "Textarea 3" if the user uses "tabs" at RadioButton1, RB3, RB7 or RB6. 
Textarea 1 and Textarea 2 are only reachable, if the user uses the cursor-keys to select RB2 or RB4 and presses thereafter the tab-key.

The expected behaviour in current Java version for this example is: (some RB auf RB-Group) -> Textarea 1 -> Textarea 2 -> Testarea 3 -> back to start...
The old expected behaviour before 1.8_40 was: RB1 -> RB2 -> Textarea 1 --> RB3 -> ...

Currently the behaviour is nonpractical. The user could not tab to "Textarea 1" or "Textarea 2" in an easily comprehensible manner.

Perhaps a property to switch to the old behaviour would be a workaround, because the new behaviour is not always the best idea...

REGRESSION.  Last worked in version 8u72

ADDITIONAL REGRESSION INFORMATION: 
I suppose the bug results from a change in 1.8_4x 
JDK-8033699

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
See source code example

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
The new expected behaviour for the example is: (some RB auf RB-Group) -> Textarea 1 -> Textarea 2 -> Testarea 3 -> back to start...
ACTUAL -
"Option 1" pressing Tab --> cursor Jumps to Textfield 2
"Option 2" pressing Tab --> cursor Jumps to Textfield 1

REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
public class FocusCycleRootTest 
{ 
    public static void main(String[] args) 
    { 
        JFrame window = new JFrame("Test"); 
        window.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); 
         
        JPanel rootPanel = new JPanel(); 
        rootPanel.setLayout(new BorderLayout()); 
         
        JPanel formPanel = new JPanel(new GridLayout(3, 3)); 
        formPanel.setFocusTraversalPolicy(new LayoutFocusTraversalPolicy()); 
        formPanel.setFocusCycleRoot(true); 
         
        JRadioButton option1 = new JRadioButton("Option 1", true); 
        JRadioButton option2 = new JRadioButton("Option 2");
        JRadioButton option3 = new JRadioButton("Option 3");
        JRadioButton option4 = new JRadioButton("Option 4");
         
        ButtonGroup radioButtonGroup = new ButtonGroup(); 
        radioButtonGroup.add(option1); 
        radioButtonGroup.add(option2);
        radioButtonGroup.add(option3);
        radioButtonGroup.add(option4);
         
        formPanel.add(option1); 
        formPanel.add(option2);
        formPanel.add(new JTextField("1 - focusable, but not reachable"));
        formPanel.add(option3);
        formPanel.add(option4);
        formPanel.add(new JTextField("2 - focusable, great!"));
        formPanel.add(new JTextField("3 - another focusable textfield"));
         
        rootPanel.add(formPanel, BorderLayout.CENTER); 
         
        JButton okButton = new JButton("OK"); 
        rootPanel.add(okButton, BorderLayout.SOUTH); 
         
        window.add(rootPanel); 
        window.pack(); 
        window.setVisible(true); 
    } 
} 
---------- END SOURCE ----------

CUSTOMER SUBMITTED WORKAROUND :
I spent some time on debugging the java swing code and discovered the following cause:

In SortingFocusTraversalPolicy the focus cycle is calculated.
See getFocusTraversalCycle(aContainer) --> enumerateAndSortCycle()

In this order the RadioButton entries are separately arranged.
Later in BasicRadioButtonUI.class the method "containsInGroup" checks, whether the component belongs to a buttongroup. In this case the element behind the last buttongroup element will be taken. --> That is why the focus jumps from the first element to the element behind the last element of the radiobutton-group. But this is not correct, if there are other components between the radio button group elements, that do not belong to the radio-button group.

Solution:
The button group should be considered while sorting the focus-cycle. The containsInGroup check in BasicRadioButtonUI::getFocusTransferBaseComponent is to late to fix the focus behaviour.


Comments
Semyon, please look at this bug, can we fix it for 9?
09-09-2016

Rajeev, since this is a regression from 8 b132, you should fix or propose to defer with label
09-09-2016

No plans to fix for JDK 7 and 8. Dev may decide to fix for tbd_minor/tbd_major If there's a customer bug filed we may revisit the 7-wnf/8-wnf - will not fix position, and of course the OpenJDK community may decide to address this if they require.
01-09-2016

The new RadioButton group focus traversal algorithm introduced by JDK-8033699 doesn't take into account that group of radio buttons can be layouted in several lines in container. In this case the LayoutFocusTraversalPolicy may mix radio buttons of the same group with other components in its focus traversal order and break the assumption used in BasicRadioButtonUI#getFocusTransferBaseComponent() that radio buttons are sequenced in the focus policy order.
13-04-2016