Here you can find the source of drawString(String pString, Graphics2D pG, int pX, int pY, int pWidth, int pHeight, boolean pYOverflow, boolean pShrinkWords, String pJustification, boolean pDraw)
Parameter | Description |
---|---|
pString | Words to draw |
pG | Graphics2D object reference used to draw |
pX | Top left ordinate of where to start drawing down from |
pY | Top left ordinate of where to start drawing down from |
pWidth | Width to wrap string at in pixels |
pHeight | Height to cut off overflow at in pixels |
pYOverflow | Boolean to allow overflow or not |
pShrinkWords | Boolean to shrink words that are bigger than the width |
pJustification | Left/right/centre line justification |
pDraw | Boolean to switch drawing on or off (handy for just getting bounds before drawing) |
public static Rectangle drawString(String pString, Graphics2D pG, int pX, int pY, int pWidth, int pHeight, boolean pYOverflow, boolean pShrinkWords, String pJustification, boolean pDraw)
//package com.java2s; //License from project: Open Source License import java.awt.*; public class Main { /**/* w ww . j a va2 s. c o m*/ * Draw a string onto a graphics2d object, wrapping words at pWidth pixels wide. * If a word has to be cut, if less than 75% is cut off it's added back on and the word shrunk, if pShrinkWords == true * * @param pString Words to draw * @param pG Graphics2D object reference used to draw * @param pX Top left ordinate of where to start drawing down from * @param pY Top left ordinate of where to start drawing down from * @param pWidth Width to wrap string at in pixels * @param pHeight Height to cut off overflow at in pixels * @param pYOverflow Boolean to allow overflow or not * @param pShrinkWords Boolean to shrink words that are bigger than the width * @param pJustification Left/right/centre line justification * @param pDraw Boolean to switch drawing on or off (handy for just getting bounds before drawing) * @return Rectangle of the bounding box */ public static Rectangle drawString(String pString, Graphics2D pG, int pX, int pY, int pWidth, int pHeight, boolean pYOverflow, boolean pShrinkWords, String pJustification, boolean pDraw) { FontMetrics lFontMetrics = pG.getFontMetrics(); Font lDrawFont = pG.getFont(); char[] lCharacters = pString.toCharArray(); int lFontHeight = lFontMetrics.getHeight(); int lLeading = 0;//lFontMetrics.getLeading()/2; int lY = pY; boolean lFirstLine = true; boolean lSuppressLastLine = false; Integer lLastSpace = null; int lCharsInBuffer = 0; StringBuffer lLineBuffer = new StringBuffer(); for (int i = 0; i < lCharacters.length; ++i) { if (lFontMetrics.stringWidth(lLineBuffer.toString() + lCharacters[i]) < pWidth) { if (!isNewLine(lCharacters[i])) { lLineBuffer.append(lCharacters[i]); lCharsInBuffer++; if (isBreakable(lCharacters[i])) { lLastSpace = new Integer(i); } } else { //Find the next Y position for the new line lY += lFontHeight + (lFirstLine ? -lFontMetrics.getDescent() : lLeading); if ((lY + lFontHeight) > pHeight && pYOverflow == false) { //Break loop if it's hit the Y limit break; } //Draw the line if (pDraw) { drawLine(lLineBuffer.toString(), pG, pX, lY, pWidth, pJustification); } //Start the new buffer lLineBuffer.setLength(0); lLineBuffer.append(lCharacters[i]); lLastSpace = null; lCharsInBuffer = 0; lFirstLine = false; } } else { //Try and go back to the last space if (lLastSpace != null) { //Space found in line, cut down buffer and hop i back a bit int lNextBreak = 0; int j; for (j = i; j < Math.min((i + (int) (lCharsInBuffer * 0.15)), lCharacters.length); ++j) { if (isBreakable(lCharacters[j])) { lNextBreak = j; break; } } if (j == lCharacters.length) { lNextBreak = lCharacters.length; } if (lNextBreak != 0 && pShrinkWords) { String lNewString = lLineBuffer.toString() + pString.substring(i, j); int lFontSize; for (lFontSize = lDrawFont.getSize(); lFontSize > 1; lFontSize--) { Font lNewSmallerFont = new Font(lDrawFont.getName(), lDrawFont.getStyle(), lFontSize); pG.setFont(lNewSmallerFont); if (pG.getFontMetrics().stringWidth(lNewString) < pWidth) { lY += pG.getFontMetrics().getHeight() + (lFirstLine ? -pG.getFontMetrics().getDescent() : lLeading); if (pDraw) { drawLine(lNewString, pG, pX, lY, pWidth, pJustification); } i = j + 1; pG.setFont(lDrawFont); break; } } if (i >= lCharacters.length) { lSuppressLastLine = true; break; } pG.setFont(lDrawFont); lLineBuffer.setLength(0); lLineBuffer.append(lCharacters[i]); lLastSpace = null; lCharsInBuffer = 0; lFirstLine = false; continue; } else { lLineBuffer.setLength(lCharsInBuffer - (i - lLastSpace.intValue()) + 1); i = lLastSpace.intValue() + 1; } } else if (pShrinkWords) { //Shrink word if It's not too big int lNextBreak = 0; int j; for (j = i; j < Math.min((i + (int) (lCharsInBuffer * 0.50)), lCharacters.length); ++j) { if (isBreakable(lCharacters[j])) { lNextBreak = j; break; } } if (j == lCharacters.length) { lNextBreak = lCharacters.length; } if (lNextBreak != 0) { String lNewString = lLineBuffer.toString() + pString.substring(i, j); int lFontSize; for (lFontSize = lDrawFont.getSize(); lFontSize > 1; lFontSize--) { Font lNewSmallerFont = new Font(lDrawFont.getName(), lDrawFont.getStyle(), lFontSize); pG.setFont(lNewSmallerFont); if (pG.getFontMetrics().stringWidth(lNewString) < pWidth) { lY += pG.getFontMetrics().getHeight() + (lFirstLine ? -pG.getFontMetrics().getDescent() : lLeading); if (pDraw) { drawLine(lNewString, pG, pX, lY, pWidth, pJustification); } i = j + 1; pG.setFont(lDrawFont); break; } } if (i >= lCharacters.length) { lSuppressLastLine = true; break; } pG.setFont(lDrawFont); lLineBuffer.setLength(0); lLineBuffer.append(lCharacters[i]); lLastSpace = null; lCharsInBuffer = 0; lFirstLine = false; continue; } } //Find the next Y position for the new line lY += lFontHeight + (lFirstLine ? -lFontMetrics.getDescent() : lLeading); if ((lY + lFontHeight) > pHeight && pYOverflow == false) { //Break loop if it's hit the Y limit break; } //Draw the line if (pDraw) { drawLine(lLineBuffer.toString(), pG, pX, lY, pWidth, pJustification); } //Start the new buffer lLineBuffer.setLength(0); lLineBuffer.append(lCharacters[i]); lLastSpace = null; lCharsInBuffer = 0; lFirstLine = false; } } if (!lSuppressLastLine) { //Find the next Y position for the new line lY = lY + lFontHeight + (lFirstLine ? -lFontMetrics.getDescent() : lLeading); //Draw the line if (pDraw) { drawLine(lLineBuffer.toString(), pG, pX, lY, pWidth, pJustification); } } //Calculate final bounding box int lHeight = lY + lFontMetrics.getDescent() - pY; int lWidth = pWidth; Rectangle lR = new Rectangle(pX, pY, lWidth, lHeight); return lR; } private static boolean isNewLine(char c) { return (c == '\n' || c == '\r'); } private static boolean isBreakable(char c) { return (c == ' ' || c == '\t' || c == '-' || c == '\\' || c == '/' || c == '_'); } /** * Draw a line of text with justification * * @param pLine String of text to draw * @param pG Graphics object to draw on * @param pX Position to start at * @param pY Position to start at * @param pWidth Width of the line, to know where to right align to * @param pJustification LEFT|RIGHT|CENTRE justification */ public static void drawLine(String pLine, Graphics2D pG, int pX, int pY, int pWidth, String pJustification) { FontMetrics lFontMetrics = pG.getFontMetrics(); if (pLine.trim().length() > 0) { if ("RIGHT".equals(pJustification.toUpperCase())) { pG.drawString(pLine.trim(), pX + pWidth - lFontMetrics.stringWidth(pLine.trim()), pY); } else if ("CENTRE".equals(pJustification.toUpperCase())) { pG.drawString(pLine.trim(), pX + (pWidth / 2) - (lFontMetrics.stringWidth(pLine.trim()) / 2), pY); } else { pG.drawString(pLine.trim(), pX, pY); } } } }