Java Swing Font drawCentredText(Graphics2D g, Font font, String text, int x, int y)

Here you can find the source of drawCentredText(Graphics2D g, Font font, String text, int x, int y)

Description

Draws the text by creating a rectange centered around x, y

License

Open Source License

Parameter

Parameter Description
g a parameter
font a parameter
x a parameter
y a parameter

Return

The rectangle that bounds the text

Declaration

public static Rectangle drawCentredText(Graphics2D g, Font font, String text, int x, int y) 

Method Source Code


//package com.java2s;
/*/*  w  ww. j a  v  a2  s  .com*/
 * ?Copyright (C) 2013 Atlas of Living Australia
 * All Rights Reserved.
 *
 * The contents of this file are subject to the Mozilla Public
 * License Version 1.1 (the "License"); you may not use this file
 * except in compliance with the License. You may obtain a copy of
 * the License at http://www.mozilla.org/MPL/
 *
 * Software distributed under the License is distributed on an "AS
 * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
 * implied. See the License for the specific language governing
 * rights and limitations under the License.
 */

import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;

import java.awt.Rectangle;
import java.awt.RenderingHints;

import java.awt.Toolkit;

import java.util.ArrayList;
import java.util.List;

import javax.swing.JComponent;

public class Main {
    public static boolean DEBUG = false;
    public static final int TEXT_ALIGN_RIGHT = 1;
    public static final int TEXT_ALIGN_CENTER = 2;
    private static boolean _AntiAliasedFonts = true;

    /**
     * Draws the text by creating a rectange centered around x, y
     *
     * @param g
     * @param font
     * @param x
     * @param y
     * @return The rectangle that bounds the text
     */
    public static Rectangle drawCentredText(Graphics2D g, Font font, String text, int x, int y) {
        g.setFont(font);
        FontMetrics fm = g.getFontMetrics(font);

        setPreferredAliasingMode(g);

        Rectangle ret = new Rectangle(x, y, 0, 0);

        if (text == null) {
            return ret;
        }
        String[] alines = text.split("\\n");
        ArrayList<String> lines = new ArrayList<String>();
        for (String s : alines) {
            if (s.length() > 0) {
                lines.add(s);
            }
        }
        int numlines = lines.size();
        if (numlines > 0) {
            int maxwidth = 0;
            int totalheight = 0;
            for (int idx = 0; idx < numlines; ++idx) {
                String line = lines.get(idx);
                int stringWidth = fm.stringWidth(line);
                if (stringWidth > maxwidth) {
                    maxwidth = stringWidth;
                }
                totalheight += fm.getAscent() + fm.getDescent();
            }
            ret.width = maxwidth;
            ret.height = totalheight;
            ret.x = x - (maxwidth / 2);
            ret.y = y - (totalheight / 2);

            drawString(g, font, text, ret, TEXT_ALIGN_CENTER);

            return ret;
        }
        return ret;

    }

    /**
     * Returns the FontMetrics for the current Font of the passed in Graphics. This method is used when a Graphics is available, typically when painting. If a Graphics is not available the JComponent method of the same name should be used.
     * <p>
     * Callers should pass in a non-null JComponent, the exception to this is if a JComponent is not readily available at the time of painting.
     * <p>
     * This does not necessarily return the FontMetrics from the Graphics.
     *
     * @param c
     *            JComponent requesting FontMetrics, may be null
     * @param g
     *            Graphics Graphics
     */
    public static FontMetrics getFontMetrics(JComponent c, Graphics g) {
        return getFontMetrics(c, g, g.getFont());
    }

    /**
     * Returns the FontMetrics for the specified Font. This method is used when a Graphics is available, typically when painting. If a Graphics is not available the JComponent method of the same name should be used.
     * <p>
     * Callers should pass in a non-null JComonent, the exception to this is if a JComponent is not readily available at the time of painting.
     * <p>
     * This does not necessarily return the FontMetrics from the Graphics.
     *
     * @param c
     *            JComponent requesting FontMetrics, may be null
     * @param c
     *            Graphics Graphics
     * @param font
     *            Font to get FontMetrics for
     */
    @SuppressWarnings("deprecation")
    public static FontMetrics getFontMetrics(JComponent c, Graphics g, Font font) {
        if (c != null) {
            // Note: We assume that we're using the FontMetrics
            // from the widget to layout out text, otherwise we can get
            // mismatches when printing.
            return c.getFontMetrics(font);
        }
        return Toolkit.getDefaultToolkit().getFontMetrics(font);
    }

    public static void setPreferredAliasingMode(Graphics g) {
        if (g instanceof Graphics2D) {
            Graphics2D g2 = (Graphics2D) g;
            g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                    (_AntiAliasedFonts ? RenderingHints.VALUE_ANTIALIAS_ON : RenderingHints.VALUE_ANTIALIAS_OFF));
        }
    }

    /**
     * Returns the width of the passed in String.
     *
     * @param c
     *            JComponent that will display the string, may be null
     * @param fm
     *            FontMetrics used to measure the String width
     * @param string
     *            String to get the width of
     */
    public static int stringWidth(JComponent c, FontMetrics fm, String string) {
        return fm.stringWidth(string);
    }

    public static Rectangle drawString(Graphics g, Font font, String text, Rectangle rect, int align) {
        return drawString(g, font, text, rect.x, rect.y, rect.width, rect.height, align);
    }

    public static Rectangle drawString(Graphics g, Font font, String text, int x, int y, int width, int height,
            int align) {
        return drawString(g, font, text, x, y, width, height, align, false);
    }

    public static Rectangle drawString(Graphics g, Font font, String text, int x, int y, int width, int height,
            int align, boolean wrap) {
        g.setFont(font);
        FontMetrics fm = g.getFontMetrics(font);

        setPreferredAliasingMode(g);

        Rectangle ret = new Rectangle(0, 0, 0, 0);

        if (text == null) {
            return ret;
        }
        String[] alines = text.split("\\n");
        ArrayList<String> lines = new ArrayList<String>();
        for (String s : alines) {
            if (wrap && fm.stringWidth(s) > width) {
                // need to split this up into multiple lines...
                List<String> splitLines = wrapString(s, fm, width);
                lines.addAll(splitLines);
            } else {
                lines.add(s);
            }
        }
        int numlines = lines.size();
        while (fm.getHeight() * numlines > height) {
            numlines--;
        }
        if (numlines > 0) {
            int maxwidth = 0;
            int minxoffset = y + width;
            int totalheight = (numlines * fm.getHeight());

            int linestart = ((height / 2) - (totalheight / 2));

            if (!wrap) {
                ret.y = y + linestart;
            } else {
                ret.y = y;
                linestart = 0;
            }
            for (int idx = 0; idx < numlines; ++idx) {
                String line = lines.get(idx);
                int stringWidth = fm.stringWidth(line);
                // the width of the label depends on the font :
                // if the width of the label is larger than the item
                if (stringWidth > 0 && width < stringWidth) {
                    // We have to truncate the label
                    line = clipString(null, fm, line, width);
                    stringWidth = fm.stringWidth(line);
                }

                int xoffset = 0;
                int yoffset = linestart + fm.getHeight() - fm.getDescent();
                if (align == TEXT_ALIGN_RIGHT) {
                    xoffset = (width - stringWidth);
                } else if (align == TEXT_ALIGN_CENTER) {
                    xoffset = (int) Math.round((double) (width - stringWidth) / (double) 2);
                }

                if (xoffset < minxoffset) {
                    minxoffset = xoffset;
                }
                g.drawString(line, x + xoffset, y + yoffset);
                if (stringWidth > maxwidth) {
                    maxwidth = stringWidth;
                }
                linestart += fm.getHeight();
            }

            ret.width = maxwidth;
            ret.height = totalheight;
            ret.x = x + minxoffset;

            // Debug only...
            if (DEBUG) {
                Graphics2D g2d = (Graphics2D) g;
                g2d.setStroke(new BasicStroke(1));
                g.setColor(Color.blue);
                g.drawRect(ret.x, ret.y, ret.width, ret.height);
                g.setColor(Color.green);
                g.drawRect(x, y, width, height);
            }

            return ret;
        }
        return ret;
    }

    private static List<String> wrapString(String s, FontMetrics fm, int width) {
        List<String> lines = new ArrayList<String>();
        StringBuilder line = new StringBuilder();
        for (int i = 0; i < s.length(); ++i) {
            char ch = s.charAt(i);
            String test = line.toString() + ch;
            if (fm.stringWidth(test) > width) {
                if (test.length() > 1) {
                    // Backtrack to look for a space...
                    boolean breakFound = false;
                    if (ch != ' ') {

                        for (int j = line.length() - 1; j > 0; --j) {
                            if (line.charAt(j) == ' ') {
                                lines.add(line.substring(0, j));
                                line = new StringBuilder(line.substring(j + 1));
                                breakFound = true;
                                break;
                            }
                        }
                    }
                    if (!breakFound) {
                        lines.add(line.toString());
                        line = new StringBuilder();
                    }
                    line.append(ch);
                } else {
                    lines.add(test);
                    line = new StringBuilder();
                }
            } else {
                line.append(ch);
            }
        }
        if (line.length() > 0) {
            lines.add(line.toString());
        }
        return lines;
    }

    /**
     * Clips the passed in String to the space provided. NOTE: this assumes the string does not fit in the available space.
     *
     * @param c
     *            JComponent that will display the string, may be null
     * @param fm
     *            FontMetrics used to measure the String width
     * @param string
     *            String to display
     * @param availTextWidth
     *            Amount of space that the string can be drawn in
     * @return Clipped string that can fit in the provided space.
     */
    public static String clipString(JComponent c, FontMetrics fm, String string, int availTextWidth) {
        // c may be null here.
        String clipString = "...";
        int width = stringWidth(c, fm, clipString);
        // NOTE: This does NOT work for surrogate pairs and other fun
        // stuff
        int nChars = 0;
        for (int max = string.length(); nChars < max; nChars++) {
            width += fm.charWidth(string.charAt(nChars));
            if (width > availTextWidth) {
                break;
            }
        }
        string = string.substring(0, nChars) + clipString;
        return string;
    }
}

Related

  1. boldFont(JComponent component)
  2. clipText(JComponent c, Font fnt, String val, int xFrom, int xTo)
  3. createTextAttributes(Font baseFont, Color color, boolean bold, boolean italic)
  4. createTextLayout(JComponent c, String s, Font f, FontRenderContext frc)
  5. defaultFont()
  6. drawString(Graphics g, Font font, String text, Rectangle rect, int align)
  7. drawString(Graphics g, String text, int x, int y, Font font, Color color)
  8. getAsNotUIResource(Font font)
  9. getDefaultFont()