home *** CD-ROM | disk | FTP | other *** search
/ Chip 1998 November / Chip_1998-11_cd.bin / tema / Cafe / jfc.bin / BasicMenuUI.java < prev    next >
Text File  |  1998-02-26  |  30KB  |  693 lines

  1. /*
  2.  * @(#)BasicMenuUI.java    1.91 98/02/05
  3.  * 
  4.  * Copyright (c) 1997 Sun Microsystems, Inc. All Rights Reserved.
  5.  * 
  6.  * This software is the confidential and proprietary information of Sun
  7.  * Microsystems, Inc. ("Confidential Information").  You shall not
  8.  * disclose such Confidential Information and shall use it only in
  9.  * accordance with the terms of the license agreement you entered into
  10.  * with Sun.
  11.  * 
  12.  * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF THE
  13.  * SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
  14.  * IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
  15.  * PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR ANY DAMAGES
  16.  * SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR DISTRIBUTING
  17.  * THIS SOFTWARE OR ITS DERIVATIVES.
  18.  * 
  19.  */
  20.  
  21. package com.sun.java.swing.plaf.basic;
  22.  
  23. import java.awt.*;
  24. import java.awt.event.*;
  25. import com.sun.java.swing.*;
  26. import com.sun.java.swing.event.*;
  27. import com.sun.java.swing.plaf.*;
  28. import com.sun.java.swing.border.*;
  29. import java.io.Serializable;
  30.  
  31.  
  32. /**
  33.  * A Windows L&F implementation of MenuUI.  This implementation 
  34.  * is a "combined" view/controller.
  35.  * <p>
  36.  * Warning: serialized objects of this class will not be compatible with
  37.  * future swing releases.  The current serialization support is appropriate 
  38.  * for short term storage or RMI between Swing1.0 applications.  It will
  39.  * not be possible to load serialized Swing1.0 objects with future releases
  40.  * of Swing.  The JDK1.2 release of Swing will be the compatibility
  41.  * baseline for the serialized form of Swing objects.
  42.  *
  43.  * @version 1.91 02/05/98
  44.  * @author Georges Saab
  45.  * @author David Karlton
  46.  * @author Arnaud Weber
  47.  */
  48. public class BasicMenuUI extends MenuUI implements Serializable 
  49. {
  50.     protected JMenu menu;
  51.     protected MouseListener       mouseListener;
  52.     protected MouseMotionListener dragListener;
  53.     protected ChangeListener      menuChangeListener;
  54.  
  55.     protected static Color pressedBackground;
  56.     protected static Color pressedForeground;
  57.     private int lastMnemonic = 0;
  58.  
  59.     // visual constants
  60.     protected static final int defaultTextIconGap = 4;
  61.  
  62.     protected Icon menuArrow = null;
  63.     protected Icon checkIcon = null;
  64.  
  65.     protected boolean oldBorderPainted;
  66.  
  67.     public static ComponentUI createUI(JComponent x) {
  68.     return new BasicMenuUI();
  69.     }
  70.  
  71.     public void installUI(JComponent c) {
  72.     menu = (JMenu) c;
  73.     // Create and install listeners
  74.     menu.setDelay(200);
  75.     initListeners(c);
  76.     addListeners(c);
  77.     // Set defaults
  78.     c.setOpaque(true);
  79.     LookAndFeel.installBorder(c,"Menu.border");
  80.     oldBorderPainted = menu.isBorderPainted();
  81.     menu.setBorderPainted( ( (Boolean) (UIManager.get("MenuItem.borderPainted")) ).booleanValue() );
  82.     LookAndFeel.installColorsAndFont(c,
  83.                           "Menu.background",
  84.                           "Menu.foreground",
  85.                           "Menu.font");
  86.         validateKeyboardAccelerator();
  87.     // Menu specific defaults
  88.     if (pressedBackground == null || 
  89.         pressedBackground instanceof UIResource) {
  90.         pressedBackground = 
  91.         UIManager.getColor("Menu.pressedBackground");
  92.     }
  93.     if (pressedForeground == null || 
  94.         pressedForeground instanceof UIResource) {
  95.         pressedForeground = 
  96.         UIManager.getColor("Menu.pressedForeground");
  97.     }
  98.     }
  99.     
  100.     public void uninstallUI(JComponent c) {
  101.     menu.setArmed(false);
  102.     menu.setSelected(false);
  103.     removeListeners(c);
  104.     c.resetKeyboardActions();
  105.     LookAndFeel.uninstallBorder(c);    
  106.     ((JMenu) c).setBorderPainted( oldBorderPainted );
  107.     if (menuArrow instanceof UIResource)
  108.         menuArrow = null;
  109.     if (checkIcon instanceof UIResource)
  110.         checkIcon = null;
  111.     }
  112.  
  113.     protected void validateKeyboardAccelerator() {
  114.         if(menu.getModel().getMnemonic() != lastMnemonic) {
  115.             menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(lastMnemonic,ActionEvent.ALT_MASK,false));
  116.             lastMnemonic = menu.getModel().getMnemonic();
  117.             menu.registerKeyboardAction(new PostAction(menu,true),            
  118.                                         KeyStroke.getKeyStroke(lastMnemonic,ActionEvent.ALT_MASK,false),
  119.                                         JComponent.WHEN_IN_FOCUSED_WINDOW);
  120.         }
  121.     }
  122.  
  123.     protected MouseListener createMouseListener(JComponent c) {
  124.     return new MouseListener((JMenu)c);
  125.     }
  126.  
  127.     protected MouseMotionListener createMouseMotionListener(JComponent c) {
  128.         return new BasicMenuMouseMotionListener();
  129.     }
  130.  
  131.     protected ChangeListener createMenuChangeListener(JComponent c) {
  132.         return new MenuChangeListener((JMenu)c, this);
  133.     }
  134.     
  135.     protected void initListeners(JComponent c) {
  136.         mouseListener = createMouseListener(c);
  137.         dragListener  = createMouseMotionListener(c);
  138.         menuChangeListener = createMenuChangeListener(c);
  139.     }
  140.  
  141.     protected void addListeners(JComponent c) {
  142.         c.addMouseListener(mouseListener);
  143.         c.addMouseMotionListener(dragListener);
  144.         ((JMenu)c).addChangeListener(menuChangeListener);
  145.     }
  146.  
  147.     protected void removeListeners(JComponent c) {
  148.         c.removeMouseListener(mouseListener);
  149.         c.removeMouseMotionListener(dragListener);
  150.         ((JMenu)c).removeChangeListener(menuChangeListener);
  151.     }
  152.  
  153.     protected void installDefaultIcons() {
  154.     // Icons
  155.     if ((menu != null) &&
  156.         (menu.getParent() != null) &&
  157.         !(menu.getParent() instanceof JMenuBar)) {
  158.         if (menuArrow == null ||
  159.         menuArrow instanceof UIResource) {
  160.         menuArrow = UIManager.getIcon("Menu.arrowIcon");
  161.         }
  162.         if (checkIcon == null ||
  163.         checkIcon instanceof UIResource) {
  164.         checkIcon = UIManager.getIcon("MenuItem.checkIcon");
  165.         }
  166.     }
  167.     }
  168.  
  169.     /**
  170.      * We draw the background in BasicGraphicsUtils.paintMenuItem()
  171.      * so override update (which fills the background of opaque
  172.      * components by default) to just call paint().
  173.      *
  174.      * @see BasicGraphicsUtils#paintMenuItem
  175.      */
  176.     public void update(Graphics g, JComponent c) {
  177.         paint(g, c);
  178.     }
  179.  
  180.     public void paint(Graphics g, JComponent c) {
  181.     installDefaultIcons();
  182.         ButtonModel bm = ((AbstractButton)c).getModel();
  183.     BasicGraphicsUtils.paintMenuItem(g, c, checkIcon, menuArrow,
  184.                      pressedBackground, pressedForeground,
  185.                      defaultTextIconGap);    
  186.     }
  187.  
  188.     public Dimension getMinimumSize(JComponent c) {
  189.         return getPreferredSize(c);
  190.     }
  191.  
  192.     public Dimension getMaximumSize(JComponent c) {
  193.         return getPreferredSize(c);
  194.     }
  195.  
  196.     public Insets getDefaultMargin(AbstractButton c) { 
  197.         return new Insets(2,2,2,2);
  198.     }
  199.  
  200.     public Dimension getPreferredSize(JComponent c) {
  201.     installDefaultIcons();
  202.     return BasicGraphicsUtils.getPreferredMenuItemSize(c,
  203.                                checkIcon, 
  204.                                menuArrow, 
  205.                                defaultTextIconGap);
  206.     }
  207.  
  208.  
  209.  
  210.  
  211.     public void processMouseEvent(JMenuItem item,MouseEvent e,MenuElement path[],MenuSelectionManager manager) {
  212.         Point p = e.getPoint();
  213.     if (item.isEnabled() == false)
  214.       return;
  215.  
  216.         if(p.x >= 0 && p.x < item.getWidth() &&
  217.            p.y >= 0 && p.y < item.getHeight()) {
  218.         JMenu menu = (JMenu)item;
  219.             MenuElement selectedPath[] = manager.getSelectedPath();
  220.             if(!(selectedPath.length > 0 && 
  221.          selectedPath[selectedPath.length-1] == 
  222.          menu.getPopupMenu())) {
  223.           if(menu.isTopLevelMenu() || 
  224.          menu.getDelay() == 0  ||
  225.          e.getID() == MouseEvent.MOUSE_DRAGGED) {
  226.         MenuElement newPath[] = new MenuElement[path.length+1];
  227.         System.arraycopy(path,0,newPath,0,path.length);
  228.         newPath[path.length] = menu.getPopupMenu();
  229.         manager.setSelectedPath(newPath);
  230.                 } else {
  231.                     manager.setSelectedPath(path);
  232.                     setupPostTimer(menu);
  233.                 }
  234.             }
  235.         } else if(e.getID() == MouseEvent.MOUSE_RELEASED) {
  236.         Component c = manager.componentForPoint(e.getComponent(), e.getPoint());
  237.         if (c == null)
  238.         manager.clearSelectedPath();
  239.         }
  240.     }
  241.  
  242.     private int lower(int ascii) {
  243.         if(ascii >= 'A' && ascii <= 'Z')
  244.             return ascii + 'a' - 'A';
  245.         else
  246.             return ascii;
  247.     }
  248.     
  249.     public void processKeyEvent(JMenuItem item,KeyEvent e,MenuElement path[],MenuSelectionManager manager) {
  250.         int key = item.getMnemonic();
  251.         if(key == 0)
  252.             return;
  253.         if(e.getID() == KeyEvent.KEY_PRESSED) {
  254.             if(lower(key) == lower((int)(e.getKeyChar()))) {
  255.                 JPopupMenu popupMenu = ((JMenu)item).getPopupMenu();
  256.                 MenuElement sub[] = popupMenu.getSubElements();
  257.                 if(sub.length > 0) {
  258.                     MenuElement newPath[] = new MenuElement[path.length + 2];
  259.                     System.arraycopy(path,0,newPath,0,path.length);
  260.                     newPath[path.length] = popupMenu;
  261.                     newPath[path.length+1] = sub[0];
  262.                     manager.setSelectedPath(newPath);
  263.                 }
  264.                 e.consume();
  265.             }
  266.         }
  267.     }
  268.     
  269.     protected void setupPostTimer(JMenu menu) {
  270.         Timer timer = new Timer(menu.getDelay(),new PostAction(menu,false));
  271.         timer.setRepeats(false);
  272.         timer.start();
  273.     }
  274.  
  275.     static class PostAction extends AbstractAction {
  276.     JMenu menu;
  277.         boolean force=false;
  278.  
  279.         PostAction(JMenu menu,boolean shouldForce) {
  280.         super("postAction");
  281.         this.menu = menu;
  282.             this.force = shouldForce;
  283.     }
  284.     
  285.     public void actionPerformed(ActionEvent e) {
  286.             MenuSelectionManager defaultManager = MenuSelectionManager.defaultManager();
  287.             if(force) {
  288.                 Container cnt = menu.getParent();
  289.                 if(cnt != null && cnt instanceof JMenuBar) {
  290.                     MenuElement me[];
  291.                     MenuElement subElements[];
  292.  
  293.                     subElements = menu.getPopupMenu().getSubElements();
  294.                     if(subElements.length > 0) {
  295.                         me = new MenuElement[4];
  296.                         me[0] = (MenuElement) cnt;
  297.                         me[1] = (MenuElement) menu;
  298.                         me[2] = (MenuElement) menu.getPopupMenu();
  299.                         me[3] = subElements[0];
  300.                         defaultManager.setSelectedPath(me);
  301.                     } else {
  302.                         me = new MenuElement[2];
  303.                         me[0] = (MenuElement)cnt;
  304.                         me[1] = menu;
  305.                         defaultManager.setSelectedPath(me);
  306.                     }
  307.                 }
  308.             } else {
  309.                 MenuElement path[] = defaultManager.getSelectedPath();
  310.                 if(path.length > 0 && path[path.length-1] == menu) {
  311.                     MenuElement newPath[] = new MenuElement[path.length+1];
  312.                     System.arraycopy(path,0,newPath,0,path.length);
  313.                     newPath[path.length] = menu.getPopupMenu();
  314.                     MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  315.                 }
  316.             }
  317.         }
  318.  
  319.     public boolean isEnabled() {
  320.         return menu.getModel().isEnabled();
  321.     }
  322.     }
  323.  
  324.  
  325.     static class MouseListener extends MouseAdapter implements Serializable {
  326.         JMenu menu;
  327.         public MouseListener(JMenu m) {
  328.             menu = m;
  329.         }
  330.  
  331.         public void mousePressed(MouseEvent e) {
  332.             if(menu.isTopLevelMenu() && menu.isEnabled()) {
  333.                 Point p = e.getPoint();
  334.                 if(p.x >= 0 && p.x < menu.getWidth() &&
  335.                    p.y >= 0 && p.y < menu.getHeight()) {
  336.                     if(menu.isSelected()) {
  337.                         MenuSelectionManager.defaultManager().clearSelectedPath();
  338.                     } else {
  339.                         Container cnt = menu.getParent();
  340.                         if(cnt != null && cnt instanceof JMenuBar) {
  341.                             MenuElement me[] = new MenuElement[2];
  342.                             me[0]=(MenuElement)cnt;
  343.                             me[1]=menu;
  344.                             MenuSelectionManager.defaultManager().setSelectedPath(me);
  345.                         }
  346.                     }
  347.                 }
  348.             }
  349.             MenuSelectionManager.defaultManager().processMouseEvent(e);
  350.         }
  351.  
  352.         public void mouseReleased(MouseEvent e) {
  353.             MenuSelectionManager.defaultManager().processMouseEvent(e);
  354.         }
  355.         public void mouseEntered(MouseEvent e) {
  356.             MenuSelectionManager.defaultManager().processMouseEvent(e);
  357.         }
  358.         public void mouseExited(MouseEvent e) {
  359.             MenuSelectionManager.defaultManager().processMouseEvent(e);
  360.         }
  361.     }
  362.  
  363.     public void menuCanceled(JMenu m) {
  364.         MenuSelectionManager manager = MenuSelectionManager.defaultManager();
  365.         if(manager.isComponentPartOfCurrentMenu(m))
  366.             MenuSelectionManager.defaultManager().clearSelectedPath();
  367.     }
  368.  
  369.     static class MenuChangeListener implements ChangeListener, Serializable {
  370.         JMenu    menu;
  371.     BasicMenuUI ui;
  372.         boolean  isSelected = false;
  373.         Component wasFocused;
  374.  
  375.         public MenuChangeListener(JMenu m, BasicMenuUI ui) {
  376.             menu = m;
  377.             this.ui = ui;
  378.             validateKeyboardActions(menu.isSelected());
  379.         }
  380.  
  381.         public void stateChanged(ChangeEvent e) {
  382.             ui.validateKeyboardAccelerator();            
  383.             validateKeyboardActions(menu.isSelected());
  384.         }
  385.  
  386.         Component findFocusedComponent(Component c) {
  387.             Container parent;
  388.             for(parent = c.getParent() ; parent != null ; parent = parent.getParent()) {
  389.                 if(parent instanceof java.awt.Window)
  390.                     return ((java.awt.Window)parent).getFocusOwner();
  391.             }
  392.             return null;
  393.         }
  394.  
  395.         void validateKeyboardActions(boolean sel) {
  396.             if(sel != isSelected) {
  397.                 isSelected = sel;
  398.                 if(isSelected) {
  399.                     boolean isRequestFocusEnabled = menu.isRequestFocusEnabled();
  400.                     wasFocused = findFocusedComponent(menu);
  401.                     if(!isRequestFocusEnabled)
  402.                         menu.setRequestFocusEnabled(true);
  403.                     menu.requestFocus();
  404.                     if(!isRequestFocusEnabled)
  405.                         menu.setRequestFocusEnabled(false);
  406.                     menu.registerKeyboardAction(new CancelAction(),
  407.                                                 KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE,0,false),
  408.                                                 JComponent.WHEN_IN_FOCUSED_WINDOW);
  409.                     menu.registerKeyboardAction(new SelectNextItemAction(),
  410.                                                 KeyStroke.getKeyStroke(KeyEvent.VK_DOWN,0,false),
  411.                                                 JComponent.WHEN_IN_FOCUSED_WINDOW);
  412.                     menu.registerKeyboardAction(new SelectPreviousItemAction(),
  413.                                                 KeyStroke.getKeyStroke(KeyEvent.VK_UP,0,false),
  414.                                                 JComponent.WHEN_IN_FOCUSED_WINDOW);
  415.                     menu.registerKeyboardAction(new SelectParentItemAction(),
  416.                                                 KeyStroke.getKeyStroke(KeyEvent.VK_LEFT,0,false),
  417.                                                 JComponent.WHEN_IN_FOCUSED_WINDOW);
  418.                     menu.registerKeyboardAction(new SelectChildItemAction(),
  419.                                                 KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT,0,false),
  420.                                                 JComponent.WHEN_IN_FOCUSED_WINDOW);
  421.                     menu.registerKeyboardAction(new ReturnAction(),
  422.                                                 KeyStroke.getKeyStroke(KeyEvent.VK_ENTER,0,false),
  423.                                                 JComponent.WHEN_IN_FOCUSED_WINDOW);
  424.                 } else {
  425.                     menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE,0,false));
  426.                     menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(KeyEvent.VK_DOWN,0,false));
  427.                     menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(KeyEvent.VK_UP,0,false));
  428.                     menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT,0,false));
  429.                     menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT,0,false));
  430.                     menu.unregisterKeyboardAction(KeyStroke.getKeyStroke(KeyEvent.VK_ENTER,0,false));
  431.                     if(wasFocused != null) {
  432.                         if(wasFocused instanceof JComponent) {
  433.                             JComponent jc = (JComponent) wasFocused;
  434.                             boolean isRFEnabled = jc.isRequestFocusEnabled();
  435.                             if(!isRFEnabled)
  436.                                 jc.setRequestFocusEnabled(true);
  437.                             wasFocused.requestFocus();
  438.                             if(!isRFEnabled)
  439.                                 jc.setRequestFocusEnabled(false);
  440.                         } else
  441.                             wasFocused.requestFocus();
  442.                         wasFocused = null;
  443.                     }
  444.                 }
  445.             }
  446.         }
  447.  
  448.         private class CancelAction extends AbstractAction {
  449.             public void actionPerformed(ActionEvent e) {
  450.                 MenuElement path[] = MenuSelectionManager.defaultManager().getSelectedPath();
  451.                 if(path.length > 4) { /* PENDING(arnaud) Change this to 2 when a mouse grabber is available for MenuBar */
  452.                     MenuElement newPath[] = new MenuElement[path.length - 2];
  453.                     System.arraycopy(path,0,newPath,0,path.length-2);
  454.                     MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  455.                 } else
  456.                     MenuSelectionManager.defaultManager().clearSelectedPath();
  457.             }
  458.         }
  459.  
  460.         private class ReturnAction extends AbstractAction {
  461.             public void actionPerformed(ActionEvent e) {
  462.                 MenuElement path[] = MenuSelectionManager.defaultManager().getSelectedPath();
  463.                 MenuElement lastElement;
  464.                 if(path.length > 0) {
  465.                     lastElement = path[path.length-1];
  466.                     if(lastElement instanceof JMenu) {
  467.                         MenuElement newPath[] = new MenuElement[path.length+1];
  468.                         System.arraycopy(path,0,newPath,0,path.length);
  469.                         newPath[path.length] = ((JMenu)lastElement).getPopupMenu();
  470.                         MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  471.                     } else if(lastElement instanceof JMenuItem) {
  472.                         MenuSelectionManager.defaultManager().clearSelectedPath();
  473.                         ((JMenuItem)lastElement).doClick(0);
  474.                         ((JMenuItem)lastElement).setArmed(false);
  475.                     }
  476.                 }
  477.             }
  478.         }
  479.  
  480.         private MenuElement nextEnabledChild(MenuElement e[],int fromIndex) {
  481.             int i,c;
  482.             for(i=fromIndex,c=e.length ; i < c ; i++)
  483.                 if(e[i].getComponent().isEnabled())
  484.                     return e[i];
  485.             return null;
  486.         }
  487.  
  488.         private MenuElement previousEnabledChild(MenuElement e[],int fromIndex) {
  489.             int i;
  490.             for(i=fromIndex ; i >= 0 ; i--) 
  491.                 if(e[i].getComponent().isEnabled())
  492.                     return e[i];
  493.             return null;
  494.         }
  495.  
  496.         private class SelectNextItemAction extends AbstractAction {
  497.             public void actionPerformed(ActionEvent e) {
  498.                 MenuElement currentSelection[] = MenuSelectionManager.defaultManager().getSelectedPath();
  499.                 if(currentSelection.length > 1) {
  500.                     MenuElement parent = currentSelection[currentSelection.length-2];
  501.                     if(parent.getComponent() instanceof JMenu) {
  502.                         MenuElement childs[];
  503.                         parent = currentSelection[currentSelection.length-1];
  504.                         childs = parent.getSubElements();
  505.                         if(childs.length > 0) {
  506.                             MenuElement newPath[] = new MenuElement[currentSelection.length+1];
  507.                             System.arraycopy(currentSelection,0,
  508.                                              newPath,0,currentSelection.length);
  509.                             newPath[currentSelection.length] = nextEnabledChild(childs,0);
  510.                             if(newPath[currentSelection.length] != null)
  511.                                 MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  512.                         }
  513.                     } else {
  514.                         MenuElement childs[] = parent.getSubElements();
  515.                         MenuElement nextChild;
  516.                         int i,c;
  517.                         for(i=0,c=childs.length;i<c;i++) {
  518.                             if(childs[i] == currentSelection[currentSelection.length-1]) {
  519.                                 nextChild = nextEnabledChild(childs,i+1);
  520.                                 if(nextChild == null)
  521.                                     nextChild = nextEnabledChild(childs,0);
  522.                                 if(nextChild != null) {
  523.                                     currentSelection[currentSelection.length-1] = nextChild;
  524.                                     MenuSelectionManager.defaultManager().setSelectedPath(currentSelection);
  525.                                 }
  526.                                 break;
  527.                             }
  528.                         }
  529.                     }
  530.                 }
  531.             }
  532.         }
  533.  
  534.         private class SelectPreviousItemAction extends AbstractAction {
  535.             public void actionPerformed(ActionEvent e) {
  536.                 MenuElement currentSelection[] = MenuSelectionManager.defaultManager().getSelectedPath();
  537.                 if(currentSelection.length > 1) {
  538.                     MenuElement parent = currentSelection[currentSelection.length-2];
  539.                     if(parent.getComponent() instanceof JMenu) {
  540.                         MenuElement childs[];
  541.                         parent = currentSelection[currentSelection.length-1];
  542.                         childs = parent.getSubElements();
  543.                         if(childs.length > 0) {
  544.                             MenuElement newPath[] = new MenuElement[currentSelection.length+1];
  545.                             System.arraycopy(currentSelection,0,
  546.                                              newPath,0,currentSelection.length);
  547.                             newPath[currentSelection.length] = previousEnabledChild(childs,childs.length-1);
  548.                             if(newPath[currentSelection.length] != null)
  549.                                 MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  550.                         }
  551.                     } else {
  552.                         MenuElement childs[] = parent.getSubElements();
  553.                         MenuElement nextChild;
  554.                         int i,c;
  555.                         for(i=0,c=childs.length;i<c;i++) {
  556.                             if(childs[i] == currentSelection[currentSelection.length-1]) {
  557.                                 nextChild = previousEnabledChild(childs,i-1);
  558.                                 if(nextChild == null)
  559.                                     nextChild = previousEnabledChild(childs,childs.length-1);
  560.                                 if(nextChild != null) {
  561.                                     currentSelection[currentSelection.length-1] = nextChild;
  562.                                     MenuSelectionManager.defaultManager().setSelectedPath(currentSelection);
  563.                                 }
  564.                                 break;
  565.                             }
  566.                         }
  567.                     }
  568.                 }
  569.             }
  570.         }
  571.  
  572.         private class SelectParentItemAction extends AbstractAction {
  573.             public void actionPerformed(ActionEvent e) {
  574.                 MenuElement path[] = MenuSelectionManager.defaultManager().getSelectedPath();
  575.                 
  576.                 if(path.length > 3 && path[path.length-3].getComponent() instanceof JMenu &&
  577.                    !((JMenu)path[path.length-3].getComponent()).isTopLevelMenu()) {
  578.                     MenuElement newPath[] = new MenuElement[path.length-2];
  579.                     System.arraycopy(path,0,newPath,0,path.length-2);
  580.                     MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  581.                 } else if(path.length > 0 && path[0].getComponent() instanceof JMenuBar) {
  582.                     MenuElement nextMenu=null,popup=null,firstItem=null;
  583.                     MenuElement tmp[];
  584.                     int i,c;
  585.                     
  586.                     if(path.length > 1) {
  587.                         MenuElement previousElement;
  588.                         tmp = path[0].getSubElements();
  589.                         for(i=0,c=tmp.length;i<c;i++) {
  590.                             if(tmp[i] == path[1]) {
  591.                                 nextMenu = previousEnabledChild(tmp,i-1);
  592.                                 if(nextMenu == null)
  593.                                     nextMenu = previousEnabledChild(tmp,tmp.length-1);
  594.                             }
  595.                         }
  596.                     }
  597.                     
  598.                     if(nextMenu != null) {
  599.                         MenuElement newSelection[];
  600.                         popup = ((JMenu)nextMenu).getPopupMenu();
  601.                         if(((JMenu)nextMenu).isTopLevelMenu()) 
  602.                             firstItem = null;
  603.                         else {
  604.                             tmp = popup.getSubElements();
  605.                             if(tmp.length > 0) 
  606.                                 firstItem = nextEnabledChild(tmp,0);
  607.                         }
  608.  
  609.                         if(firstItem != null) {
  610.                             newSelection = new MenuElement[4];
  611.                             newSelection[0] = path[0];
  612.                             newSelection[1] = nextMenu;
  613.                             newSelection[2] = popup;
  614.                             newSelection[3] = firstItem;
  615.                         } else {
  616.                             newSelection = new MenuElement[3];
  617.                             newSelection[0] = path[0];
  618.                             newSelection[1] = nextMenu;
  619.                             newSelection[2] = popup;
  620.                         }
  621.                         MenuSelectionManager.defaultManager().setSelectedPath(newSelection);
  622.                     }
  623.                 }
  624.             }
  625.         }
  626.  
  627.         private class SelectChildItemAction extends AbstractAction {
  628.             public void actionPerformed(ActionEvent e) {
  629.                 MenuElement path[] = MenuSelectionManager.defaultManager().getSelectedPath();
  630.                 
  631.                 if(path.length > 0 && path[path.length-1].getComponent().isEnabled() && 
  632.                    path[path.length-1].getComponent() instanceof JMenu &&
  633.                    !((JMenu)path[path.length-1].getComponent()).isTopLevelMenu()) {
  634.                     MenuElement newPath[] = new MenuElement[path.length+2];
  635.                     MenuElement subElements[];
  636.                     System.arraycopy(path,0,newPath,0,path.length);
  637.                     newPath[path.length] = ((JMenu)path[path.length-1].getComponent()).getPopupMenu();
  638.                     subElements = newPath[path.length].getSubElements();
  639.                     if(subElements.length > 0) {
  640.                         newPath[path.length+1] = nextEnabledChild(subElements,0);
  641.                         MenuSelectionManager.defaultManager().setSelectedPath(newPath);
  642.                     }
  643.                 } else if(path.length > 0 && path[0].getComponent() instanceof JMenuBar) {
  644.                     MenuElement nextMenu=null,popup=null,firstItem=null;
  645.                     MenuElement tmp[];
  646.                     int i,c;
  647.                     
  648.                     if(path.length > 1) {
  649.                         tmp = path[0].getSubElements();
  650.                         for(i=0,c=tmp.length;i<c;i++) {
  651.                             if(tmp[i] == path[1]) {
  652.                                 nextMenu = nextEnabledChild(tmp,i+1);
  653.                                 if(nextMenu == null)
  654.                                     nextMenu = nextEnabledChild(tmp,0);
  655.                             }
  656.                         }
  657.                     }
  658.                     
  659.                     if(nextMenu != null) {
  660.                         MenuElement newSelection[];
  661.                         popup = ((JMenu)nextMenu).getPopupMenu();
  662.                         if(((JMenu)nextMenu).isTopLevelMenu()) 
  663.                             firstItem = null;
  664.                         else {
  665.                             tmp = popup.getSubElements();
  666.                             if(tmp.length > 0) 
  667.                                 firstItem = nextEnabledChild(tmp,0);
  668.                         }
  669.  
  670.                         if(firstItem != null) {
  671.                             newSelection = new MenuElement[4];
  672.                             newSelection[0] = path[0];
  673.                             newSelection[1] = nextMenu;
  674.                             newSelection[2] = popup;
  675.                             newSelection[3] = firstItem;
  676.                         } else {
  677.                             newSelection = new MenuElement[3];
  678.                             newSelection[0] = path[0];
  679.                             newSelection[1] = nextMenu;
  680.                             newSelection[2] = popup;
  681.                         }
  682.                         MenuSelectionManager.defaultManager().setSelectedPath(newSelection);
  683.                     }
  684.                 }
  685.             }
  686.         }
  687.     }
  688. }
  689.  
  690.  
  691.  
  692.  
  693.