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: 6385366
Votes 0
Synopsis REGRESSION: Descriptive text and accelerator text overlap on JMenuItem.
Category java:classes_swing
Reported Against
Release Fixed mustang(b80)
State 10-Fix Delivered, bug
Priority: 3-Medium
Related Bugs 6408269 , 6438430 , 6181935 , 6197830 , 4991607 , 4729669 , 4199382
Submit Date 14-FEB-2006
Description
FULL PRODUCT VERSION :
java version "1.6.0-rc"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.6.0-rc-b71)
Java HotSpot(TM) Client VM (build 1.6.0-rc-b71, mixed mode, sharing)

ADDITIONAL OS VERSION INFORMATION :
 customer  Windows XP [Version 5.1.2600]

A DESCRIPTION OF THE PROBLEM :
Under certain circumstances the descriptive text and accelerator text overlap on JMenuItems.
This behaviour occurs in the following situation:
An entry earlier in the menu has an accelerator set on it (eg Ctrl+L) and no icon.
A later entry possesses an icon and the descriptive text is shorter than the previous entry.

The resulting width of the JMenu seems to completley ignore the extra size required by the accelerator text and overlaps it with the descriptive text.



REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class MenuTest{
	public static void main(String[] args){
		int modifier = Toolkit.getDefaultToolkit().getMenuShortcutKeyMask();
		ImageIcon  customer  = new ImageIcon(Toolkit.getDefaultToolkit().getImage("Document.gif"));
		
		JMenuItem shortitem1 = new JMenuItem("Short", customer );
		JMenuItem longitem1 = new JMenuItem("Very long menu entry");
		longitem1.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L,modifier));
		JMenu testmenu1 = new JMenu("Test1");
		testmenu1.add(shortitem1);
		testmenu1.add(longitem1);
		
		JMenuItem shortitem2 = new JMenuItem("Short", customer );
		JMenuItem longitem2 = new JMenuItem("Very long menu entry");
		longitem2.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L,modifier));
		JMenu testmenu2 = new JMenu("Test2");
		testmenu2.add(longitem2);
		testmenu2.add(shortitem2);
		
		JMenuItem shortitem3 = new JMenuItem("Short");
		JMenuItem longitem3 = new JMenuItem("Very long menu entry");
		longitem3.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L,modifier));
		JMenu testmenu3 = new JMenu("Test3");
		testmenu3.add(longitem3);
		testmenu3.add(shortitem3);
		
		JMenuItem shortitem4 = new JMenuItem("Short", customer );
		JMenuItem longitem4 = new JMenuItem("Very long menu entry", customer );
		longitem4.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L,modifier));
		JMenu testmenu4 = new JMenu("Test4");
		testmenu4.add(longitem4);
		testmenu4.add(shortitem4);
		
		JMenuItem shortitem5 = new JMenuItem("Short", customer );
		JMenuItem longitem5 = new JMenuItem("Very long menu entry");
		shortitem5.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S,modifier));
		longitem5.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L,modifier));
		JMenu testmenu5 = new JMenu("Test5");
		testmenu5.add(longitem5);
		testmenu5.add(shortitem5);
		
		JMenuBar appmenu = new JMenuBar();
		appmenu.add(testmenu1);
		appmenu.add(testmenu2);
		appmenu.add(testmenu3);
		appmenu.add(testmenu4);
		appmenu.add(testmenu5);
		JFrame f = new JFrame();
		f.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
		f.setJMenuBar(appmenu);
		f.setVisible(true);
		f.pack();
		f.setLocationRelativeTo(null);
	}
}
---------- END SOURCE ----------

Release Regression From : 5.0u6
The above release value was the last known release where this 
bug was known to work. Since then there has been a regression.
Posted Date : 2006-02-14 12:10:01.0
Work Around
N/A
Evaluation
work in progress...
Posted Date : 2006-03-09 18:41:46.0

I have found the cause: it lies in the BasicMenuItemUI.getPreferredMenuItemSize() method. It sometimes does not take in account the icon width of neighbour menu items for the widest menu item without icon.
Posted Date : 2006-03-22 10:54:17.0

The old algorithm of menu viewable width calculation is:

> walk through all menu children:
    
    > ...
    
    > get MAX_TEXT_OFFSET from parent's client property (client properties are available during of the menu width calculation)

    > current text offset = MAX_ICON_OFFSET + ...

    > if current text offset greater than MAX_TEXT_OFFSET, store it as MAX_TEXT_OFFSET

    > preferredWidth = MAX_TEXT_OFFSET + ...

> menu viewable width = preferred width of the longest menu item


The traversal order of menu items is determined by BoxLayout. It is equal to the order of item addition to parent menu.

If the widest menu item without an icon is traversed earlier than a shorter item with an icon, MAX_TEXT_OFFSET will be smaller (on the icon width) at the moment of preferred width calculation. Consequently, the longest item preferred width will be shorter than it should be. Menu viewable width will be shorter. The longest menu item will not be able to place the accelerator text in the short viewable box. It is the bug.

To fix it, we should have the width of the widest icon among neighbor menu items at the moment of menu item preferred size calculation.
Posted Date : 2006-03-23 09:25:15.0
Comments
  
  Include a link with my name & email   


PLEASE NOTE: JDK6 is formerly known as Project Mustang