    001    /* ========================================================================
    002     * JCommon : a free general purpose class library for the Java(tm) platform
    003     * ========================================================================
    004     *
    005     * (C) Copyright 2000-2005, by Object Refinery Limited and Contributors.
    006     *
    007     * Project Info:  http://www.jfree.org/jcommon/index.html
    008     *
    009     * This library is free software; you can redistribute it and/or modify it
    010     * under the terms of the GNU Lesser General Public License as published by
    011     * the Free Software Foundation; either version 2.1 of the License, or
    012     * (at your option) any later version.
    013     *
    014     * This library is distributed in the hope that it will be useful, but
    015     * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
    016     * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
    017     * License for more details.
    018     *
    019     * You should have received a copy of the GNU Lesser General Public
    020     * License along with this library; if not, write to the Free Software
    021     * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301,
    022     * USA.
    023     *
    024     * [Java is a trademark or registered trademark of Sun Microsystems, Inc.
    025     * in the United States and other countries.]
    026     *
    027     * ----------------------
    028     * RefineryUtilities.java
    029     * ----------------------
    030     * (C) Copyright 2000-2005, by Object Refinery Limited.
    031     *
    032     * Original Author:  David Gilbert (for Object Refinery Limited);
    033     * Contributor(s):   Jon Iles;
    034     *
    035     * $Id: RefineryUtilities.java,v 1.11 2007/11/02 17:50:36 taqua Exp $
    036     *
    037     * Changes (from 26-Oct-2001)
    038     * --------------------------
    039     * 26-Oct-2001 : Changed package to com.jrefinery.ui.*;
    040     * 26-Nov-2001 : Changed name to SwingRefinery.java to make it obvious that this is not part of
    041     *               the Java APIs (DG);
    042     * 10-Dec-2001 : Changed name (again) to JRefineryUtilities.java (DG);
    043     * 28-Feb-2002 : Moved system properties classes into com.jrefinery.ui.about (DG);
    044     * 19-Apr-2002 : Renamed JRefineryUtilities-->RefineryUtilities.  Added drawRotatedString()
    045     *               method (DG);
    046     * 21-May-2002 : Changed frame positioning methods to accept Window parameters, as suggested by
    047     *               Laurence Vanhelsuwe (DG);
    048     * 27-May-2002 : Added getPointInRectangle method (DG);
    049     * 26-Jun-2002 : Removed unnecessary imports (DG);
    050     * 12-Jul-2002 : Added workaround for rotated text (JI);
    051     * 14-Oct-2002 : Fixed errors reported by Checkstyle (DG);
    052     * 08-May-2003 : Added a new drawRotatedString() method (DG);
    053     * 09-May-2003 : Added a drawRotatedShape() method (DG);
    054     * 10-Jun-2003 : Updated aligned and rotated string methods (DG);
    055     * 29-Oct-2003 : Added workaround for font alignment in PDF output (DG);
    056     * 07-Nov-2003 : Added rotateShape() method (DG);
    057     * 16-Mar-2004 : Moved rotateShape() method to ShapeUtils.java (DG);
    058     * 07-Apr-2004 : Modified text bounds calculation with TextUtilities.getTextBounds() (DG);
    059     * 21-May-2004 : Fixed bug 951870 - precision in drawAlignedString() method (DG);
    060     * 30-Sep-2004 : Deprecated and moved a number of methods to the TextUtilities class (DG);
    061     * 04-Oct-2004 : Renamed ShapeUtils --> ShapeUtilities (DG);
    062     * 11-Jan-2005 : Removed deprecated code in preparation for the 1.0.0 release (DG);
    063     *
    064     */
    065
    066    package org.jfree.ui;
    067
    068    import java.awt.BorderLayout;
    069    import java.awt.Color;
    070    import java.awt.Container;
    071    import java.awt.Dialog;
    072    import java.awt.Dimension;
    073    import java.awt.Font;
    074    import java.awt.GraphicsEnvironment;
    075    import java.awt.Point;
    076    import java.awt.Rectangle;
    077    import java.awt.Toolkit;
    078    import java.awt.Window;
    079    import java.lang.reflect.Method;
    080    import javax.swing.JButton;
    081    import javax.swing.JLabel;
    082    import javax.swing.JPanel;
    083    import javax.swing.JScrollPane;
    084    import javax.swing.JTable;
    085    import javax.swing.table.TableColumn;
    086    import javax.swing.table.TableModel;
    087
    088    /**
    089     * A collection of utility methods relating to user interfaces.
    090     *
    091     * @author David Gilbert
    092     */
    093    public class RefineryUtilities {
    094
    095        private RefineryUtilities() {
    096        }
    097
    098        /** Access to logging facilities. */
    099        // private static final LogContext logger = Log.createContext(RefineryUtilities.class);
    100
    101        /**
    102         * Computes the center point of the current screen device. If this method is called on JDK 1.4, Xinerama-aware
    103         * results are returned. (See Sun-Bug-ID 4463949 for details).
    104         *
    105         * @return the center point of the current screen.
    106         */
    107        public static Point getCenterPoint ()
    108        {
    109          final GraphicsEnvironment localGraphicsEnvironment = GraphicsEnvironment.getLocalGraphicsEnvironment();
    110          try
    111          {
    112            final Method method = GraphicsEnvironment.class.getMethod("getCenterPoint", (Class[]) null);
    113            return (Point) method.invoke(localGraphicsEnvironment, (Object[]) null);
    114          }
    115          catch(Exception e)
    116          {
    117            // ignore ... will fail if this is not a JDK 1.4 ..
    118          }
    119
    120          final Dimension s = Toolkit.getDefaultToolkit().getScreenSize();
    121          return new Point (s.width / 2, s.height / 2);
    122        }
    123
    124      /**
    125       * Computes the maximum bounds of the current screen device. If this method is called on JDK 1.4, Xinerama-aware
    126       * results are returned. (See Sun-Bug-ID 4463949 for details).
    127       *
    128       * @return the maximum bounds of the current screen.
    129       */
    130        public static Rectangle getMaximumWindowBounds ()
    131        {
    132          final GraphicsEnvironment localGraphicsEnvironment = GraphicsEnvironment.getLocalGraphicsEnvironment();
    133          try
    134          {
    135            final Method method = GraphicsEnvironment.class.getMethod("getMaximumWindowBounds", (Class[]) null);
    136            return (Rectangle) method.invoke(localGraphicsEnvironment, (Object[]) null);
    137          }
    138          catch(Exception e)
    139          {
    140            // ignore ... will fail if this is not a JDK 1.4 ..
    141          }
    142
    143          final Dimension s = Toolkit.getDefaultToolkit().getScreenSize();
    144          return new Rectangle (0, 0, s.width, s.height);
    145        }
    146
    147        /**
    148         * Positions the specified frame in the middle of the screen.
    149         *
    150         * @param frame  the frame to be centered on the screen.
    151         */
    152        public static void centerFrameOnScreen(final Window frame) {
    153            positionFrameOnScreen(frame, 0.5, 0.5);
    154        }
    155
    156        /**
    157         * Positions the specified frame at a relative position in the screen, where 50% is considered
    158         * to be the center of the screen.
    159         *
    160         * @param frame  the frame.
    161         * @param horizontalPercent  the relative horizontal position of the frame (0.0 to 1.0,
    162         *                           where 0.5 is the center of the screen).
    163         * @param verticalPercent  the relative vertical position of the frame (0.0 to 1.0, where
    164         *                         0.5 is the center of the screen).
    165         */
    166        public static void positionFrameOnScreen(final Window frame,
    167                                                 final double horizontalPercent,
    168                                                 final double verticalPercent) {
    169
    170            final Rectangle s = getMaximumWindowBounds();
    171            final Dimension f = frame.getSize();
    172            final int w = Math.max(s.width - f.width, 0);
    173            final int h = Math.max(s.height - f.height, 0);
    174            final int x = (int) (horizontalPercent * w) + s.x;
    175            final int y = (int) (verticalPercent * h) + s.y;
    176            frame.setBounds(x, y, f.width, f.height);
    177
    178        }
    179
    180        /**
    181         * Positions the specified frame at a random location on the screen while ensuring that the
    182         * entire frame is visible (provided that the frame is smaller than the screen).
    183         *
    184         * @param frame  the frame.
    185         */
    186        public static void positionFrameRandomly(final Window frame) {
    187            positionFrameOnScreen(frame, Math.random(), Math.random());
    188        }
    189
    190        /**
    191         * Positions the specified dialog within its parent.
    192         *
    193         * @param dialog  the dialog to be positioned on the screen.
    194         */
    195        public static void centerDialogInParent(final Dialog dialog) {
    196            positionDialogRelativeToParent(dialog, 0.5, 0.5);
    197        }
    198
    199        /**
    200         * Positions the specified dialog at a position relative to its parent.
    201         *
    202         * @param dialog  the dialog to be positioned.
    203         * @param horizontalPercent  the relative location.
    204         * @param verticalPercent  the relative location.
    205         */
    206        public static void positionDialogRelativeToParent(final Dialog dialog,
    207                                                          final double horizontalPercent,
    208                                                          final double verticalPercent) {
    209            final Dimension d = dialog.getSize();
    210            final Container parent = dialog.getParent();
    211            final Dimension p = parent.getSize();
    212
    213            final int baseX = parent.getX() - d.width;
    214            final int baseY = parent.getY() - d.height;
    215            final int w = d.width + p.width;
    216            final int h = d.height + p.height;
    217            int x = baseX + (int) (horizontalPercent * w);
    218            int y = baseY + (int) (verticalPercent * h);
    219
    220            // make sure the dialog fits completely on the screen...
    221            final Rectangle s = getMaximumWindowBounds();
    222            x = Math.min(x, (s.width - d.width));
    223            x = Math.max(x, 0);
    224            y = Math.min(y, (s.height - d.height));
    225            y = Math.max(y, 0);
    226
    227            dialog.setBounds(x + s.x, y + s.y, d.width, d.height);
    228
    229        }
    230
    231        /**
    232         * Creates a panel that contains a table based on the specified table model.
    233         *
    234         * @param model  the table model to use when constructing the table.
    235         *
    236         * @return The panel.
    237         */
    238        public static JPanel createTablePanel(final TableModel model) {
    239
    240            final JPanel panel = new JPanel(new BorderLayout());
    241            final JTable table = new JTable(model);
    242            for (int columnIndex = 0; columnIndex < model.getColumnCount(); columnIndex++) {
    243                final TableColumn column = table.getColumnModel().getColumn(columnIndex);
    244                final Class c = model.getColumnClass(columnIndex);
    245                if (c.equals(Number.class)) {
    246                    column.setCellRenderer(new NumberCellRenderer());
    247                }
    248            }
    249            panel.add(new JScrollPane(table));
    250            return panel;
    251
    252        }
    253
    254        /**
    255         * Creates a label with a specific font.
    256         *
    257         * @param text  the text for the label.
    258         * @param font  the font.
    259         *
    260         * @return The label.
    261         */
    262        public static JLabel createJLabel(final String text, final Font font) {
    263
    264            final JLabel result = new JLabel(text);
    265            result.setFont(font);
    266            return result;
    267
    268        }
    269
    270        /**
    271         * Creates a label with a specific font and color.
    272         *
    273         * @param text  the text for the label.
    274         * @param font  the font.
    275         * @param color  the color.
    276         *
    277         * @return The label.
    278         */
    279        public static JLabel createJLabel(final String text, final Font font, final Color color) {
    280
    281            final JLabel result = new JLabel(text);
    282            result.setFont(font);
    283            result.setForeground(color);
    284            return result;
    285
    286        }
    287
    288        /**
    289         * Creates a {@link JButton}.
    290         *
    291         * @param label  the label.
    292         * @param font  the font.
    293         *
    294         * @return The button.
    295         */
    296        public static JButton createJButton(final String label, final Font font) {
    297
    298            final JButton result = new JButton(label);
    299            result.setFont(font);
    300            return result;
    301
    302        }
    303
    304    }
    305
    306