1 /* BasicMenuBarUI.java --
2    Copyright (C) 2002, 2004, 2005  Free Software Foundation, Inc.
3 
4 This file is part of GNU Classpath.
5 
6 GNU Classpath is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10 
11 GNU Classpath is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 General Public License for more details.
15 
16 You should have received a copy of the GNU General Public License
17 along with GNU Classpath; see the file COPYING.  If not, write to the
18 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19 02110-1301 USA.
20 
21 Linking this library statically or dynamically with other modules is
22 making a combined work based on this library.  Thus, the terms and
23 conditions of the GNU General Public License cover the whole
24 combination.
25 
26 As a special exception, the copyright holders of this library give you
27 permission to link this library with independent modules to produce an
28 executable, regardless of the license terms of these independent
29 modules, and to copy and distribute the resulting executable under
30 terms of your choice, provided that you also meet, for each linked
31 independent module, the terms and conditions of the license of that
32 module.  An independent module is a module which is not derived from
33 or based on this library.  If you modify this library, you may extend
34 this exception to your version of the library, but you are not
35 obligated to do so.  If you do not wish to do so, delete this
36 exception statement from your version. */
37 
38 
39 package javax.swing.plaf.basic;
40 
41 import java.awt.Dimension;
42 import java.awt.event.ContainerEvent;
43 import java.awt.event.ContainerListener;
44 import java.awt.event.MouseEvent;
45 import java.beans.PropertyChangeEvent;
46 import java.beans.PropertyChangeListener;
47 
48 import javax.swing.BoxLayout;
49 import javax.swing.JComponent;
50 import javax.swing.JMenu;
51 import javax.swing.JMenuBar;
52 import javax.swing.LookAndFeel;
53 import javax.swing.MenuElement;
54 import javax.swing.event.ChangeEvent;
55 import javax.swing.event.ChangeListener;
56 import javax.swing.event.MouseInputListener;
57 import javax.swing.plaf.ComponentUI;
58 import javax.swing.plaf.MenuBarUI;
59 
60 /**
61  * UI Delegate for JMenuBar.
62  */
63 public class BasicMenuBarUI extends MenuBarUI
64 {
65   protected ChangeListener changeListener;
66 
67   /*ContainerListener that listens to the ContainerEvents fired from menu bar*/
68   protected ContainerListener containerListener;
69 
70   /*Property change listeners that listener to PropertyChangeEvent from menu bar*/
71   protected PropertyChangeListener propertyChangeListener;
72 
73   /* menu bar for which this UI delegate is for*/
74   protected JMenuBar menuBar;
75 
76   /* MouseListener that listens to the mouseEvents fired from menu bar*/
77   private MouseInputListener mouseListener;
78 
79   /**
80    * Creates a new BasicMenuBarUI object.
81    */
BasicMenuBarUI()82   public BasicMenuBarUI()
83   {
84     changeListener = createChangeListener();
85     containerListener = createContainerListener();
86     propertyChangeListener = new PropertyChangeHandler();
87     mouseListener = new MouseInputHandler();
88   }
89 
90   /**
91    * Creates ChangeListener
92    *
93    * @return The ChangeListener
94    */
createChangeListener()95   protected ChangeListener createChangeListener()
96   {
97     return new ChangeHandler();
98   }
99 
100   /**
101    * Creates ContainerListener() to listen for ContainerEvents
102    * fired by JMenuBar.
103    *
104    * @return The ContainerListener
105    */
createContainerListener()106   protected ContainerListener createContainerListener()
107   {
108     return new ContainerHandler();
109   }
110 
111   /**
112    * Factory method to create a BasicMenuBarUI for the given {@link
113    * JComponent}, which should be a {@link JMenuBar}.
114    *
115    * @param x The {@link JComponent} a UI is being created for.
116    *
117    * @return A BasicMenuBarUI for the {@link JComponent}.
118    */
createUI(JComponent x)119   public static ComponentUI createUI(JComponent x)
120   {
121     return new BasicMenuBarUI();
122   }
123 
124   /**
125    * Returns maximum size for the specified menu bar
126    *
127    * @param c component for which to get maximum size
128    *
129    * @return  Maximum size for the specified menu bar
130    */
getMaximumSize(JComponent c)131   public Dimension getMaximumSize(JComponent c)
132   {
133     // let layout manager calculate its size
134     return null;
135   }
136 
137   /**
138    * Returns maximum allowed size of JMenuBar.
139    *
140    * @param c menuBar for which to return maximum size
141    *
142    * @return Maximum size of the give menu bar.
143    */
getMinimumSize(JComponent c)144   public Dimension getMinimumSize(JComponent c)
145   {
146     // let layout manager calculate its size
147     return null;
148   }
149 
150   /**
151    * Returns preferred size of JMenuBar.
152    *
153    * @param c menuBar for which to return preferred size
154    *
155    * @return Preferred size of the give menu bar.
156    */
getPreferredSize(JComponent c)157   public Dimension getPreferredSize(JComponent c)
158   {
159     // let layout manager calculate its size
160     return null;
161   }
162 
163   /**
164    * Initializes any default properties that this UI has from the defaults for
165    * the Basic look and feel.
166    */
installDefaults()167   protected void installDefaults()
168   {
169     LookAndFeel.installBorder(menuBar, "MenuBar.border");
170     LookAndFeel.installColorsAndFont(menuBar, "MenuBar.background",
171                                      "MenuBar.foreground", "MenuBar.font");
172     menuBar.setOpaque(true);
173   }
174 
175   /**
176    * This method installs the keyboard actions for the JMenuBar.
177    */
installKeyboardActions()178   protected void installKeyboardActions()
179   {
180     // FIXME: implement
181   }
182 
183   /**
184    * This method installs the listeners needed for this UI to function.
185    */
installListeners()186   protected void installListeners()
187   {
188     menuBar.addContainerListener(containerListener);
189     menuBar.addPropertyChangeListener(propertyChangeListener);
190     menuBar.addMouseListener(mouseListener);
191   }
192 
193   /**
194   * Installs and initializes all fields for this UI delegate. Any properties
195   * of the UI that need to be initialized and/or set to defaults will be
196   * done now. It will also install any listeners necessary.
197   *
198   * @param c The {@link JComponent} that is having this UI installed.
199   */
installUI(JComponent c)200   public void installUI(JComponent c)
201   {
202     super.installUI(c);
203     menuBar = (JMenuBar) c;
204     menuBar.setLayout(new BoxLayout(menuBar, BoxLayout.X_AXIS));
205     installDefaults();
206     installListeners();
207     installKeyboardActions();
208   }
209 
210   /**
211    * This method uninstalls the defaults and nulls any objects created during
212    * install.
213    */
uninstallDefaults()214   protected void uninstallDefaults()
215   {
216     menuBar.setBackground(null);
217     menuBar.setBorder(null);
218     menuBar.setFont(null);
219     menuBar.setForeground(null);
220   }
221 
222   /**
223    * This method reverses the work done in installKeyboardActions.
224    */
uninstallKeyboardActions()225   protected void uninstallKeyboardActions()
226   {
227     // FIXME: implement.
228   }
229 
230   /**
231    * Unregisters all the listeners that this UI delegate was using.
232    */
uninstallListeners()233   protected void uninstallListeners()
234   {
235     menuBar.removeContainerListener(containerListener);
236     menuBar.removePropertyChangeListener(propertyChangeListener);
237     menuBar.removeMouseListener(mouseListener);
238   }
239 
240   /**
241    * Performs the opposite of installUI. Any properties or resources that need
242    * to be cleaned up will be done now. It will also uninstall any listeners
243    * it has. In addition, any properties of this UI will be nulled.
244    *
245    * @param c The {@link JComponent} that is having this UI uninstalled.
246    */
uninstallUI(JComponent c)247   public void uninstallUI(JComponent c)
248   {
249     uninstallDefaults();
250     uninstallListeners();
251     uninstallKeyboardActions();
252     menuBar = null;
253   }
254 
255   protected class ChangeHandler implements ChangeListener
256   {
stateChanged(ChangeEvent event)257     public void stateChanged(ChangeEvent event)
258     {
259       // TODO: What should be done here, if anything?
260     }
261   }
262 
263   /**
264    * This class handles ContainerEvents fired by JMenuBar. It revalidates
265    * and repaints menu bar whenever menu is added or removed from it.
266    */
267   protected class ContainerHandler implements ContainerListener
268   {
269     /**
270      * This method is called whenever menu is added to the menu bar
271      *
272      * @param e The ContainerEvent.
273      */
componentAdded(ContainerEvent e)274     public void componentAdded(ContainerEvent e)
275     {
276       menuBar.revalidate();
277       menuBar.repaint();
278     }
279 
280     /**
281      * This method is called whenever menu is removed from the menu bar.
282      *
283      * @param e The ContainerEvent.
284      */
componentRemoved(ContainerEvent e)285     public void componentRemoved(ContainerEvent e)
286     {
287       menuBar.revalidate();
288       menuBar.repaint();
289     }
290   }
291 
292   /**
293    * This class handles PropertyChangeEvents fired from the JMenuBar
294    */
295   protected class PropertyChangeHandler implements PropertyChangeListener
296   {
297     /**
298      * This method is called whenever one of the properties of the MenuBar
299      * changes.
300      *
301      * @param e The PropertyChangeEvent.
302      */
propertyChange(PropertyChangeEvent e)303     public void propertyChange(PropertyChangeEvent e)
304     {
305       if (e.getPropertyName().equals("borderPainted"))
306         menuBar.repaint();
307       if (e.getPropertyName().equals("margin"))
308         menuBar.repaint();
309     }
310   }
311 
312   private class MouseInputHandler implements MouseInputListener
313   {
314     /**
315      * Handles mouse clicked event
316      *
317      * @param e Mouse event
318      */
mouseClicked(MouseEvent e)319     public void mouseClicked(MouseEvent e)
320     {
321       MenuElement[] me = menuBar.getSubElements();
322 
323       for (int i = 0; i < me.length; i++)
324         {
325           JMenu menu = menuBar.getMenu(i);
326           if (menu != null)
327             menu.setSelected(false);
328         }
329     }
330 
331     /**
332      * Handles mouse pressed event
333      *
334      * @param e Mouse event
335      */
mousePressed(MouseEvent e)336     public void mousePressed(MouseEvent e)
337     {
338       // TODO: What should be done here, if anything?
339     }
340 
341     /**
342      * Handles mouse released event
343      *
344      * @param e Mouse event
345      */
mouseReleased(MouseEvent e)346     public void mouseReleased(MouseEvent e)
347     {
348       // TODO: What should be done here, if anything?
349     }
350 
351     /**
352      * Handles mouse exited event
353      *
354      * @param e Mouse event
355      */
mouseExited(MouseEvent e)356     public void mouseExited(MouseEvent e)
357     {
358       // TODO: What should be done here, if anything?
359     }
360 
361     /**
362      * Handles mouse dragged event
363      *
364      * @param e Mouse event
365      */
mouseDragged(MouseEvent e)366     public void mouseDragged(MouseEvent e)
367     {
368       // TODO: What should be done here, if anything?
369     }
370 
371     /**
372      * Handles mouse moved event
373      *
374      * @param e Mouse event
375      */
mouseMoved(MouseEvent e)376     public void mouseMoved(MouseEvent e)
377     {
378       // TODO: What should be done here, if anything?
379     }
380 
381     /**
382      * Handles mouse entered event
383      *
384      * @param e Mouse event
385      */
mouseEntered(MouseEvent e)386     public void mouseEntered(MouseEvent e)
387     {
388       // TODO: What should be done here, if anything?
389     }
390   }
391 }
392