package org.japura.gui; import java.awt.FontMetrics; import java.awt.event.ComponentAdapter; import java.awt.event.ComponentEvent; import java.util.ArrayList; import javax.swing.JLabel; import javax.swing.SwingUtilities; /** * Label component with a wrap function. * <P> * The default wrap width is 0 (disabled). * <P> * HTML code is not allowed. It supports <CODE>\n<CODE> code. * <P> * Copyright (C) 2009 Carlos Eduardo Leite de Andrade * <P> * This library is free software: you can redistribute it and/or modify it under * the terms of the GNU Lesser General Public License as published by the Free * Software Foundation, either version 3 of the License, or (at your option) any * later version. * <P> * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more * details. * <P> * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see <A * HREF="www.gnu.org/licenses/">www.gnu.org/licenses/</A> * <P> * For more information, contact: <A HREF="www.japura.org">www.japura.org</A> * <P> * * @author Carlos Eduardo Leite de Andrade */ public class WrapLabel extends JLabel{ public static final Align LEFT = Align.LEFT; public static final Align RIGHT = Align.RIGHT; public static final Align CENTER = Align.CENTER; private Align align = Align.LEFT; private int wrapWidth = 0; private String text; /** * Constructor * */ public WrapLabel() { addComponentListener(new ComponentAdapter() { @Override public void componentResized(ComponentEvent e) { wrapText(); } }); } /** * Constructor * * @param text * {@link String} the text */ public WrapLabel(String text) { this(); setText(text); } @Override public void setText(String text) { this.text = text; wrapText(); } /** * The plain text is converted to HTML code. The wrap locations are calculated * with the defined wrap width and component width. */ private void wrapText() { if (getFont() == null || text == null) { return; } FontMetrics fm = getFontMetrics(getFont()); StringBuilder tempText = new StringBuilder(); StringBuilder finalText = new StringBuilder("<html>"); finalText.append("<STYLE type='text/css'>BODY { text-align: "); finalText.append(align.name().toLowerCase()); finalText.append("}</STYLE><BODY>"); ArrayList<String> words = new ArrayList<String>(); text = text.replaceAll("\n", "<BR>"); String split[] = text.split("<BR>"); for (int i = 0; i < split.length; i++) { if (split[i].length() > 0) { String split2[] = split[i].split("[ \\t\\x0B\\f\\r]+"); for (int j = 0; j < split2.length; j++) { if (split2[j].length() > 0) { words.add(split2[j]); } } } if (i < split.length - 1) { words.add("<BR>"); } } for (String word : words) { if (word.equals("<BR>")) { finalText.append("<BR>"); tempText.setLength(0); } else { tempText.append(" "); tempText.append(word); int tempWidth = SwingUtilities.computeStringWidth(fm, tempText.toString().trim()); if ((wrapWidth > 0 && tempWidth > wrapWidth)) { int wordSize = SwingUtilities.computeStringWidth(fm, word); if (wordSize >= wrapWidth) { finalText.append("..."); break; } finalText.append("<BR>"); tempText.setLength(0); tempText.append(word); } if (tempText.length() > 0) { finalText.append(" "); } finalText.append(word); } } finalText.append("</BODY></html>"); super.setText(finalText.toString()); } /** * Get the wrap width. * <P> * Value 0 disable the wrap . * * @return int */ public int getWrapWidth() { return wrapWidth; } /** * Set the wrap width. * <P> * Value 0 disable the wrap. * * @param width * int */ public void setWrapWidth(int width) { this.wrapWidth = width; wrapText(); } /** * Get the alignment for the text * * @return {@link WrapLabel.Align} */ public Align getAlign() { return align; } /** * Set the alignment for the text * * @param align * {@link WrapLabel.Align} */ public void setAlign(Align align) { this.align = align; wrapText(); } /** * The alignment for the text */ public static enum Align { LEFT, CENTER, RIGHT; }; }