2004-08-12 Janis Johnson <janis187@us.ibm.com>
[official-gcc.git] / libjava / javax / swing / SwingUtilities.java
blob62b156161f3f174837b1abeb362e8071de81ab69
1 /* SwingUtilities.java --
2 Copyright (C) 2002, 2004 Free Software Foundation, Inc.
4 This file is part of GNU Classpath.
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.
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.
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., 59 Temple Place, Suite 330, Boston, MA
19 02111-1307 USA.
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.
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. */
38 package javax.swing;
40 import java.applet.Applet;
41 import java.awt.Component;
42 import java.awt.ComponentOrientation;
43 import java.awt.Container;
44 import java.awt.Font;
45 import java.awt.FontMetrics;
46 import java.awt.Frame;
47 import java.awt.Graphics;
48 import java.awt.Insets;
49 import java.awt.Point;
50 import java.awt.Rectangle;
51 import java.awt.Shape;
52 import java.awt.Toolkit;
53 import java.awt.Window;
54 import java.awt.event.InputEvent;
55 import java.awt.event.MouseEvent;
56 import java.lang.reflect.InvocationTargetException;
59 /**
60 * This class contains a number of static utility functions which are
61 * useful when drawing swing components, dispatching events, or calculating
62 * regions which need painting.
64 * @author Graydon Hoare (graydon@redhat.com)
66 public class SwingUtilities implements SwingConstants
68 /**
69 * This frame should be used as parent for JWindow or JDialog
70 * that doesn't an owner
72 private static OwnerFrame ownerFrame;
74 /**
75 * Calculates the portion of the base rectangle which is inside the
76 * insets.
78 * @param base The rectangle to apply the insets to
79 * @param insets The insets to apply to the base rectangle
80 * @param ret A rectangle to use for storing the return value, or
81 * <code>null</code>
83 * @return The calculated area inside the base rectangle and its insets,
84 * either stored in ret or a new Rectangle if ret is <code>null</code>
86 * @see #calculateInnerArea
88 public static Rectangle calculateInsetArea(Rectangle base, Insets insets,
89 Rectangle ret)
91 if (ret == null)
92 ret = new Rectangle();
93 ret.setBounds(base.x + insets.left, base.y + insets.top,
94 base.width - (insets.left + insets.right),
95 base.height - (insets.top + insets.bottom));
96 return ret;
99 /**
100 * Calculates the portion of the component's bounds which is inside the
101 * component's border insets. This area is usually the area a component
102 * should confine its painting to. The coordinates are returned in terms
103 * of the <em>component's</em> coordinate system, where (0,0) is the
104 * upper left corner of the component's bounds.
106 * @param c The component to measure the bounds of
107 * @param r A Rectangle to store the return value in, or
108 * <code>null</code>
110 * @return The calculated area inside the component and its border
111 * insets
113 * @see #calculateInsetArea
115 public static Rectangle calculateInnerArea(JComponent c, Rectangle r)
117 Rectangle b = getLocalBounds(c);
118 return calculateInsetArea(b, c.getInsets(), r);
122 * Calculates the bounds of a component in the component's own coordinate
123 * space. The result has the same height and width as the component's
124 * bounds, but its location is set to (0,0).
126 * @param aComponent The component to measure
128 * @return The component's bounds in its local coordinate space
130 public static Rectangle getLocalBounds(Component aComponent)
132 Rectangle bounds = aComponent.getBounds();
133 return new Rectangle(0, 0, bounds.width, bounds.height);
137 * Returns the font metrics object for a given font. The metrics can be
138 * used to calculate crude bounding boxes and positioning information,
139 * for laying out components with textual elements.
141 * @param font The font to get metrics for
143 * @return The font's metrics
145 * @see java.awt.font.GlyphMetrics
147 public static FontMetrics getFontMetrics(Font font)
149 return Toolkit.getDefaultToolkit().getFontMetrics(font);
153 * If <code>comp</code> is a RootPaneContainer, return its JRootPane.
154 * Otherwise call <code>getAncestorOfClass(JRootPane.class, a)</code>.
156 * @param comp The component to get the JRootPane of
158 * @return a suitable JRootPane for <code>comp</code>, or <code>null</code>
160 * @see javax.swing.RootPaneContainer#getRootPane
161 * @see #getAncestorOfClass
163 public static JRootPane getRootPane(Component comp)
165 if (comp instanceof RootPaneContainer)
166 return ((RootPaneContainer)comp).getRootPane();
167 else
168 return (JRootPane) getAncestorOfClass(JRootPane.class, comp);
172 * Returns the least ancestor of <code>comp</code> which has the
173 * specified name.
175 * @param name The name to search for
176 * @param comp The component to search the ancestors of
178 * @return The nearest ancestor of <code>comp</code> with the given
179 * name, or <code>null</code> if no such ancestor exists
181 * @see java.awt.Component#getName
182 * @see #getAncestorOfClass
184 public static Container getAncestorNamed(String name, Component comp)
186 while (comp != null && (comp.getName() != name))
187 comp = comp.getParent();
188 return (Container) comp;
192 * Returns the least ancestor of <code>comp</code> which is an instance
193 * of the specified class.
195 * @param c The class to search for
196 * @param comp The component to search the ancestors of
198 * @return The nearest ancestor of <code>comp</code> which is an instance
199 * of the given class, or <code>null</code> if no such ancestor exists
201 * @see #getAncestorOfClass
202 * @see #windowForComponent
204 public static Container getAncestorOfClass(Class c, Component comp)
206 while (comp != null && (! c.isInstance(comp)))
207 comp = comp.getParent();
208 return (Container) comp;
212 * Equivalent to calling <code>getAncestorOfClass(Window, comp)</code>.
214 * @param comp The component to search for an ancestor window
216 * @return An ancestral window, or <code>null</code> if none exists
218 public static Window windowForComponent(Component comp)
220 return (Window) getAncestorOfClass(Window.class, comp);
224 * Returns the "root" of the component tree containint <code>comp</code>
225 * The root is defined as either the <em>least</em> ancestor of
226 * <code>comp</code> which is a {@link Window}, or the <em>greatest</em>
227 * ancestor of <code>comp</code> which is a {@link Applet} if no {@link
228 * Window} ancestors are found.
230 * @param comp The component to search for a root
232 * @return The root of the component's tree, or <code>null</code>
234 public static Component getRoot(Component comp)
236 Applet app = null;
237 Window win = null;
239 while (comp != null)
241 if (win == null && comp instanceof Window)
242 win = (Window) comp;
243 else if (comp instanceof Applet)
244 app = (Applet) comp;
245 comp = comp.getParent();
248 if (win != null)
249 return win;
250 else
251 return app;
255 * Return true if a descends from b, in other words if b is an
256 * ancestor of a.
258 * @param a The child to search the ancestry of
259 * @param b The potential ancestor to search for
261 * @return true if a is a descendent of b, false otherwise
263 public static boolean isDescendingFrom(Component a, Component b)
265 while (true)
267 if (a == null || b == null)
268 return false;
269 if (a == b)
270 return true;
271 a = a.getParent();
276 * Returns the deepest descendent of parent which is both visible and
277 * contains the point <code>(x,y)</code>. Returns parent when either
278 * parent is not a container, or has no children which contain
279 * <code>(x,y)</code>. Returns <code>null</code> when either
280 * <code>(x,y)</code> is outside the bounds of parent, or parent is
281 * <code>null</code>.
283 * @param parent The component to search the descendents of
284 * @param x Horizontal coordinate to search for
285 * @param y Vertical coordinate to search for
287 * @return A component containing <code>(x,y)</code>, or
288 * <code>null</code>
290 * @see java.awt.Container#findComponentAt
292 public static Component getDeepestComponentAt(Component parent, int x, int y)
294 if (parent == null || (! parent.contains(x, y)))
295 return null;
297 if (! (parent instanceof Container))
298 return parent;
300 Container c = (Container) parent;
301 return c.findComponentAt(x, y);
305 * Converts a point from a component's local coordinate space to "screen"
306 * coordinates (such as the coordinate space mouse events are delivered
307 * in). This operation is equivalent to translating the point by the
308 * location of the component (which is the origin of its coordinate
309 * space).
311 * @param p The point to convert
312 * @param c The component which the point is expressed in terms of
314 * @see convertPointFromScreen
316 public static void convertPointToScreen(Point p, Component c)
318 Point c0 = c.getLocationOnScreen();
319 p.translate(c0.x, c0.y);
323 * Converts a point from "screen" coordinates (such as the coordinate
324 * space mouse events are delivered in) to a component's local coordinate
325 * space. This operation is equivalent to translating the point by the
326 * negation of the component's location (which is the origin of its
327 * coordinate space).
329 * @param p The point to convert
330 * @param c The component which the point should be expressed in terms of
332 public static void convertPointFromScreen(Point p, Component c)
334 Point c0 = c.getLocationOnScreen();
335 p.translate(-c0.x, -c0.y);
339 * Converts a point <code>(x,y)</code> from the coordinate space of one
340 * component to another. This is equivalent to converting the point from
341 * <code>source</code> space to screen space, then back from screen space
342 * to <code>destination</code> space. If exactly one of the two
343 * Components is <code>null</code>, it is taken to refer to the root
344 * ancestor of the other component. If both are <code>null</code>, no
345 * transformation is done.
347 * @param source The component which the point is expressed in terms of
348 * @param x Horizontal coordinate of point to transform
349 * @param y Vertical coordinate of point to transform
350 * @param destination The component which the return value will be
351 * expressed in terms of
353 * @return The point <code>(x,y)</code> converted from the coordinate space of the
354 * source component to the coordinate space of the destination component
356 * @see #convertPointToScreen
357 * @see #convertPointFromScreen
358 * @see #convertRectangle
359 * @see #getRoot
361 public static Point convertPoint(Component source, int x, int y,
362 Component destination)
364 Point pt = new Point(x, y);
366 if (source == null && destination == null)
367 return pt;
369 if (source == null)
370 source = getRoot(destination);
372 if (destination == null)
373 destination = getRoot(source);
375 convertPointToScreen(pt, source);
376 convertPointFromScreen(pt, destination);
378 return pt;
381 public static Point convertPoint(Component source, Point aPoint, Component destination)
383 return convertPoint(source, aPoint.x, aPoint.y, destination);
387 * Converts a rectangle from the coordinate space of one component to
388 * another. This is equivalent to converting the rectangle from
389 * <code>source</code> space to screen space, then back from screen space
390 * to <code>destination</code> space. If exactly one of the two
391 * Components is <code>null</code>, it is taken to refer to the root
392 * ancestor of the other component. If both are <code>null</code>, no
393 * transformation is done.
395 * @param source The component which the rectangle is expressed in terms of
396 * @param rect The rectangle to convert
397 * @param destination The component which the return value will be
398 * expressed in terms of
400 * @return A new rectangle, equal in size to the input rectangle, but
401 * with its position converted from the coordinate space of the source
402 * component to the coordinate space of the destination component
404 * @see #convertPointToScreen
405 * @see #convertPointFromScreen
406 * @see #convertPoint
407 * @see #getRoot
409 public static Rectangle convertRectangle(Component source,
410 Rectangle rect,
411 Component destination)
413 Point pt = convertPoint(source, rect.x, rect.y, destination);
414 return new Rectangle(pt.x, pt.y, rect.width, rect.height);
418 * Convert a mouse event which refrers to one component to another. This
419 * includes changing the mouse event's coordinate space, as well as the
420 * source property of the event. If <code>source</code> is
421 * <code>null</code>, it is taken to refer to <code>destination</code>'s
422 * root component. If <code>destination</code> is <code>null</code>, the
423 * new event will remain expressed in <code>source</code>'s coordinate
424 * system.
426 * @param source The component the mouse event currently refers to
427 * @param sourceEvent The mouse event to convert
428 * @param destination The component the new mouse event should refer to
430 * @return A new mouse event expressed in terms of the destination
431 * component's coordinate space, and with the destination component as
432 * its source
434 * @see #convertPoint
436 public static MouseEvent convertMouseEvent(Component source,
437 MouseEvent sourceEvent,
438 Component destination)
440 Point newpt = convertPoint(source, sourceEvent.getX(), sourceEvent.getY(),
441 destination);
443 return new MouseEvent(destination, sourceEvent.getID(),
444 sourceEvent.getWhen(), sourceEvent.getModifiers(),
445 newpt.x, newpt.y, sourceEvent.getClickCount(),
446 sourceEvent.isPopupTrigger(), sourceEvent.getButton());
450 * Recursively walk the component tree under <code>comp</code> calling
451 * <code>updateUI</code> on each {@link JComponent} found. This causes
452 * the entire tree to re-initialize its UI delegates.
454 * @param comp The component to walk the children of, calling <code>updateUI</code>
456 public static void updateComponentTreeUI(Component comp)
458 if (comp == null)
459 return;
461 if (comp instanceof Container)
463 Component[] children = ((Container)comp).getComponents();
464 for (int i = 0; i < children.length; ++i)
465 updateComponentTreeUI(children[i]);
468 if (comp instanceof JComponent)
469 ((JComponent)comp).updateUI();
474 * <p>Layout a "compound label" consisting of a text string and an icon
475 * which is to be placed near the rendered text. Once the text and icon
476 * are laid out, the text rectangle and icon rectangle parameters are
477 * altered to store the calculated positions.</p>
479 * <p>The size of the text is calculated from the provided font metrics
480 * object. This object should be the metrics of the font you intend to
481 * paint the label with.</p>
483 * <p>The position values control where the text is placed relative to
484 * the icon. The horizontal position value should be one of the constants
485 * <code>LEADING</code>, <code>TRAILING</code>, <code>LEFT</code>,
486 * <code>RIGHT</code> or <code>CENTER</code>. The vertical position value
487 * should be one fo the constants <code>TOP</code>, <code>BOTTOM</code>
488 * or <code>CENTER</code>.</p>
490 * <p>The text-icon gap value controls the number of pixels between the
491 * icon and the text.</p>
493 * <p>The alignment values control where the text and icon are placed, as
494 * a combined unit, within the view rectangle. The horizontal alignment
495 * value should be one of the constants <code>LEADING</code>,
496 * <code>TRAILING</code>, <code>LEFT</code>, <code>RIGHT</code> or
497 * <code>CENTER</code>. The vertical alignment valus should be one of the
498 * constants <code>TOP</code>, <code>BOTTOM</code> or
499 * <code>CENTER</code>.</p>
501 * <p>If the <code>LEADING</code> or <code>TRAILING</code> constants are
502 * given for horizontal alignment or horizontal text position, they are
503 * interpreted relative to the provided component's orientation property,
504 * a constant in the {@link java.awt.ComponentOrientation} class. For
505 * example, if the component's orientation is <code>LEFT_TO_RIGHT</code>,
506 * then the <code>LEADING</code> value is a synonym for <code>LEFT</code>
507 * and the <code>TRAILING</code> value is a synonym for
508 * <code>RIGHT</code></p>
510 * <p>If the text and icon are equal to or larger than the view
511 * rectangle, the horizontal and vertical alignment values have no
512 * affect.</p>
514 * @param c A component used for its orientation value
515 * @param fm The font metrics used to measure the text
516 * @param text The text to place in the compound label
517 * @param icon The icon to place next to the text
518 * @param verticalAlignment The vertical alignment of the label relative
519 * to its component
520 * @param horizontalAlignment The horizontal alignment of the label
521 * relative to its component
522 * @param verticalTextPosition The vertical position of the label's text
523 * relative to its icon
524 * @param horizontalTextPosition The horizontal position of the label's
525 * text relative to its icon
526 * @param viewR The view rectangle, specifying the area which layout is
527 * constrained to
528 * @param iconR A rectangle which is modified to hold the laid-out
529 * position of the icon
530 * @param textR A rectangle which is modified to hold the laid-out
531 * position of the text
532 * @param textIconGap The distance between text and icon
534 * @return The string of characters, possibly truncated with an elipsis,
535 * which is laid out in this label
538 public static String layoutCompoundLabel(JComponent c,
539 FontMetrics fm,
540 String text,
541 Icon icon,
542 int verticalAlignment,
543 int horizontalAlignment,
544 int verticalTextPosition,
545 int horizontalTextPosition,
546 Rectangle viewR,
547 Rectangle iconR,
548 Rectangle textR,
549 int textIconGap)
552 // Fix up the orientation-based horizontal positions.
554 if (horizontalTextPosition == LEADING)
556 if (c.getComponentOrientation() == ComponentOrientation.RIGHT_TO_LEFT)
557 horizontalTextPosition = RIGHT;
558 else
559 horizontalTextPosition = LEFT;
561 else if (horizontalTextPosition == TRAILING)
563 if (c.getComponentOrientation() == ComponentOrientation.RIGHT_TO_LEFT)
564 horizontalTextPosition = LEFT;
565 else
566 horizontalTextPosition = RIGHT;
569 // Fix up the orientation-based alignments.
571 if (horizontalAlignment == LEADING)
573 if (c.getComponentOrientation() == ComponentOrientation.RIGHT_TO_LEFT)
574 horizontalAlignment = RIGHT;
575 else
576 horizontalAlignment = LEFT;
578 else if (horizontalAlignment == TRAILING)
580 if (c.getComponentOrientation() == ComponentOrientation.RIGHT_TO_LEFT)
581 horizontalAlignment = LEFT;
582 else
583 horizontalAlignment = RIGHT;
586 return layoutCompoundLabel(fm, text, icon,
587 verticalAlignment,
588 horizontalAlignment,
589 verticalTextPosition,
590 horizontalTextPosition,
591 viewR, iconR, textR, textIconGap);
595 * <p>Layout a "compound label" consisting of a text string and an icon
596 * which is to be placed near the rendered text. Once the text and icon
597 * are laid out, the text rectangle and icon rectangle parameters are
598 * altered to store the calculated positions.</p>
600 * <p>The size of the text is calculated from the provided font metrics
601 * object. This object should be the metrics of the font you intend to
602 * paint the label with.</p>
604 * <p>The position values control where the text is placed relative to
605 * the icon. The horizontal position value should be one of the constants
606 * <code>LEFT</code>, <code>RIGHT</code> or <code>CENTER</code>. The
607 * vertical position value should be one fo the constants
608 * <code>TOP</code>, <code>BOTTOM</code> or <code>CENTER</code>.</p>
610 * <p>The text-icon gap value controls the number of pixels between the
611 * icon and the text.</p>
613 * <p>The alignment values control where the text and icon are placed, as
614 * a combined unit, within the view rectangle. The horizontal alignment
615 * value should be one of the constants <code>LEFT</code>, <code>RIGHT</code> or
616 * <code>CENTER</code>. The vertical alignment valus should be one of the
617 * constants <code>TOP</code>, <code>BOTTOM</code> or
618 * <code>CENTER</code>.</p>
620 * <p>If the text and icon are equal to or larger than the view
621 * rectangle, the horizontal and vertical alignment values have no
622 * affect.</p>
624 * <p>Note that this method does <em>not</em> know how to deal with
625 * horizontal alignments or positions given as <code>LEADING</code> or
626 * <code>TRAILING</code> values. Use the other overloaded variant of this
627 * method if you wish to use such values.
629 * @param fm The font metrics used to measure the text
630 * @param text The text to place in the compound label
631 * @param icon The icon to place next to the text
632 * @param verticalAlignment The vertical alignment of the label relative
633 * to its component
634 * @param horizontalAlignment The horizontal alignment of the label
635 * relative to its component
636 * @param verticalTextPosition The vertical position of the label's text
637 * relative to its icon
638 * @param horizontalTextPosition The horizontal position of the label's
639 * text relative to its icon
640 * @param viewR The view rectangle, specifying the area which layout is
641 * constrained to
642 * @param iconR A rectangle which is modified to hold the laid-out
643 * position of the icon
644 * @param textR A rectangle which is modified to hold the laid-out
645 * position of the text
646 * @param textIconGap The distance between text and icon
648 * @return The string of characters, possibly truncated with an elipsis,
649 * which is laid out in this label
652 public static String layoutCompoundLabel(FontMetrics fm,
653 String text,
654 Icon icon,
655 int verticalAlignment,
656 int horizontalAlignment,
657 int verticalTextPosition,
658 int horizontalTextPosition,
659 Rectangle viewR,
660 Rectangle iconR,
661 Rectangle textR,
662 int textIconGap)
665 // Work out basic height and width.
667 if (icon == null)
669 textIconGap = 0;
670 iconR.width = 0;
671 iconR.height = 0;
673 else
675 iconR.width = icon.getIconWidth();
676 iconR.height = icon.getIconHeight();
678 if (text == null)
680 textIconGap = 0;
681 textR.width = 0;
682 textR.height = 0;
684 else
686 textR.width = fm.stringWidth(text);
687 textR.height = fm.getHeight();
690 // Work out the position of text and icon, assuming the top-left coord
691 // starts at (0,0). We will fix that up momentarily, after these
692 // "position" decisions are made and we look at alignment.
694 switch (horizontalTextPosition)
696 case LEFT:
697 textR.x = 0;
698 iconR.x = textR.width + textIconGap;
699 break;
700 case RIGHT:
701 iconR.x = 0;
702 textR.x = iconR.width + textIconGap;
703 break;
704 case CENTER:
705 int centerLine = Math.max(textR.width, iconR.width) / 2;
706 textR.x = centerLine - textR.width/2;
707 iconR.x = centerLine - iconR.width/2;
708 break;
711 switch (verticalTextPosition)
713 case TOP:
714 textR.y = 0;
715 iconR.y = (horizontalTextPosition == CENTER
716 ? textR.height + textIconGap : 0);
717 break;
718 case BOTTOM:
719 iconR.y = 0;
720 textR.y = (horizontalTextPosition == CENTER
721 ? iconR.height + textIconGap
722 : iconR.height - textR.height);
723 break;
724 case CENTER:
725 int centerLine = Math.max(textR.height, iconR.height) / 2;
726 textR.y = centerLine - textR.height/2;
727 iconR.y = centerLine - iconR.height/2;
728 break;
730 // The two rectangles are laid out correctly now, but only assuming
731 // that their upper left corner is at (0,0). If we have any alignment other
732 // than TOP and LEFT, we need to adjust them.
734 Rectangle u = textR.union(iconR);
735 int horizontalAdjustment = viewR.x;
736 int verticalAdjustment = viewR.y;
737 switch (verticalAlignment)
739 case TOP:
740 break;
741 case BOTTOM:
742 verticalAdjustment += (viewR.height - u.height);
743 break;
744 case CENTER:
745 verticalAdjustment += ((viewR.height/2) - (u.height/2));
746 break;
748 switch (horizontalAlignment)
750 case LEFT:
751 break;
752 case RIGHT:
753 horizontalAdjustment += (viewR.width - u.width);
754 break;
755 case CENTER:
756 horizontalAdjustment += ((viewR.width/2) - (u.width/2));
757 break;
760 iconR.x += horizontalAdjustment;
761 iconR.y += verticalAdjustment;
763 textR.x += horizontalAdjustment;
764 textR.y += verticalAdjustment;
766 return text;
769 /**
770 * Calls {@link java.awt.EventQueue.invokeLater} with the
771 * specified {@link Runnable}.
773 public static void invokeLater(Runnable doRun)
775 java.awt.EventQueue.invokeLater(doRun);
778 /**
779 * Calls {@link java.awt.EventQueue.invokeAndWait} with the
780 * specified {@link Runnable}.
782 public static void invokeAndWait(Runnable doRun)
783 throws InterruptedException,
784 InvocationTargetException
786 java.awt.EventQueue.invokeAndWait(doRun);
789 /**
790 * Calls {@link java.awt.EventQueue.isEventDispatchThread}.
792 public static boolean isEventDispatchThread()
794 return java.awt.EventQueue.isDispatchThread();
798 * This method paints the given component at the given position and size.
799 * The component will be reparented to the container given.
801 * @param g The Graphics object to draw with.
802 * @param c The Component to draw
803 * @param p The Container to reparent to.
804 * @param x The x coordinate to draw at.
805 * @param y The y coordinate to draw at.
806 * @param w The width of the drawing area.
807 * @param h The height of the drawing area.
809 public static void paintComponent(Graphics g, Component c, Container p,
810 int x, int y, int w, int h)
812 Container parent = c.getParent();
813 if (parent != null)
814 parent.remove(c);
815 if (p != null)
816 p.add(c);
818 Shape savedClip = g.getClip();
820 g.setClip(x, y, w, h);
821 g.translate(x, y);
823 c.paint(g);
825 g.translate(-x, -y);
826 g.setClip(savedClip);
830 * This method paints the given component in the given rectangle.
831 * The component will be reparented to the container given.
833 * @param g The Graphics object to draw with.
834 * @param c The Component to draw
835 * @param p The Container to reparent to.
836 * @param r The rectangle that describes the drawing area.
838 public static void paintComponent(Graphics g, Component c,
839 Container p, Rectangle r)
841 paintComponent(g, c, p, r.x, r.y, r.width, r.height);
845 * This method returns the common Frame owner used in JDialogs or
846 * JWindow when no owner is provided.
848 * @return The common Frame
850 static Frame getOwnerFrame()
852 if (ownerFrame == null)
853 ownerFrame = new OwnerFrame();
854 return ownerFrame;
858 * Checks if left mouse button was clicked.
860 * @param event the event to check
862 * @return true if left mouse was clicked, false otherwise.
864 public static boolean isLeftMouseButton(MouseEvent event)
866 return ((event.getModifiers() & InputEvent.BUTTON1_DOWN_MASK)
867 == InputEvent.BUTTON1_DOWN_MASK);
871 * Checks if middle mouse button was clicked.
873 * @param event the event to check
875 * @return true if middle mouse was clicked, false otherwise.
877 public static boolean isMiddleMouseButton(MouseEvent event)
879 return ((event.getModifiers() & InputEvent.BUTTON2_DOWN_MASK)
880 == InputEvent.BUTTON2_DOWN_MASK);
884 * Checks if right mouse button was clicked.
886 * @param event the event to check
888 * @return true if right mouse was clicked, false otherwise.
890 public static boolean isRightMouseButton(MouseEvent event)
892 return ((event.getModifiers() & InputEvent.BUTTON3_DOWN_MASK)
893 == InputEvent.BUTTON3_DOWN_MASK);
897 * This frame should be used when constructing a Window/JDialog without
898 * a parent. In this case, we are forced to use this frame as a window's
899 * parent, because we simply cannot pass null instead of parent to Window
900 * constructor, since doing it will result in NullPointerException.
902 private static class OwnerFrame extends Frame
904 public void setVisible(boolean b)
906 // Do nothing here.
909 public boolean isShowing()
911 return true;