package arcane.ui.util; import javax.swing.*; import java.awt.*; import java.awt.font.FontRenderContext; import java.awt.font.LineBreakMeasurer; import java.awt.font.TextAttribute; import java.awt.font.TextLayout; import java.text.AttributedCharacterIterator; import java.text.AttributedString; import java.text.BreakIterator; import java.util.Locale; /** * <p>GlowText class.</p> * * @author Forge * @version $Id: GlowText.java 10038 2011-06-25 08:29:06Z jendave.hudson@gmail.com $ */ public class GlowText extends JLabel { /** Constant <code>serialVersionUID=-2868833097364223352L</code> */ private static final long serialVersionUID = -2868833097364223352L; private int glowSize; private Color glowColor; private boolean wrap; /** * <p>setGlow.</p> * * @param glowColor a {@link java.awt.Color} object. * @param size a int. * @param intensity a float. */ public void setGlow(Color glowColor, int size, float intensity) { this.glowColor = glowColor; this.glowSize = size; } /** * <p>Setter for the field <code>wrap</code>.</p> * * @param wrap a boolean. */ public void setWrap(boolean wrap) { this.wrap = wrap; } /** * <p>getPreferredSize.</p> * * @return a {@link java.awt.Dimension} object. */ public Dimension getPreferredSize() { Dimension size = super.getPreferredSize(); size.width += glowSize; size.height += glowSize / 2; return size; } /** {@inheritDoc} */ public void setText(String text) { super.setText(text); } /** {@inheritDoc} */ public void paint(Graphics g) { if (getText().length() == 0) return; Graphics2D g2d = (Graphics2D) g; g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); g2d.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON); Dimension size = getSize(); int textX = 0, textY = 0; int wrapWidth = Math.max(0, wrap ? size.width - glowSize : Integer.MAX_VALUE); AttributedString attributedString = new AttributedString(getText()); attributedString.addAttribute(TextAttribute.FONT, getFont()); AttributedCharacterIterator charIterator = attributedString.getIterator(); FontRenderContext fontContext = g2d.getFontRenderContext(); LineBreakMeasurer measurer = new LineBreakMeasurer(charIterator, BreakIterator.getWordInstance(Locale.ENGLISH), fontContext); int lineCount = 0; while (measurer.getPosition() < charIterator.getEndIndex()) { measurer.nextLayout(wrapWidth); lineCount++; if (lineCount > 2) break; } charIterator.first(); // Use char wrap if word wrap would cause more than two lines of text. if (lineCount > 2) measurer = new LineBreakMeasurer(charIterator, BreakIterator.getCharacterInstance(Locale.ENGLISH), fontContext); else measurer.setPosition(0); while (measurer.getPosition() < charIterator.getEndIndex()) { TextLayout textLayout = measurer.nextLayout(wrapWidth); float ascent = textLayout.getAscent(); textY += ascent; // Move down to baseline. g2d.setColor(glowColor); g2d.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.8f)); textLayout.draw(g2d, textX + glowSize / 2 + 1, textY + glowSize / 2 - 1); textLayout.draw(g2d, textX + glowSize / 2 + 1, textY + glowSize / 2 + 1); textLayout.draw(g2d, textX + glowSize / 2 - 1, textY + glowSize / 2 - 1); textLayout.draw(g2d, textX + glowSize / 2 - 1, textY + glowSize / 2 + 1); g2d.setColor(getForeground()); g2d.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 1.0f)); textLayout.draw(g2d, textX + glowSize / 2, textY + glowSize / 2); textY += textLayout.getDescent() + textLayout.getLeading(); // Move down to top of next line. } } }