Denis Sablukov
Denis Sablukov

Reputation: 3690

Is it possible to set outer stroke for text?

I'm trying to make outer stroke for text. When I increase width parameter of BasicStroke my outline spreads both inside and outside text, but I need only outside part.

My result: Outlined Text

Are there some properties for that? Or maybe there is a way to cut stroke from within text?

Example code:

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.Shape;
import java.awt.font.FontRenderContext;
import java.awt.font.TextLayout;
import java.awt.geom.AffineTransform;


import javax.swing.JPanel;
import javax.swing.JApplet;
import javax.swing.JFrame;

public class FontPaint extends JApplet {
  public void init() {
    FontPanel fontPanel = new FontPanel();
    getContentPane().add(fontPanel, BorderLayout.CENTER);
  }

  public static void main(String[] args) {
    FontPanel starPanel = new FontPanel();

    JFrame f = new JFrame("Font");
    f.addWindowListener(new WindowAdapter() {
      public void windowClosing(WindowEvent e) {
        System.exit(0);
      }
    });

    f.getContentPane().add(starPanel, BorderLayout.CENTER);
    f.setSize(new Dimension(550, 200));
    f.setVisible(true);
  }
}

class FontPanel extends JPanel {
  public void paintComponent(Graphics g) {
    super.paintComponent(g);
    setBackground(Color.white);

    Graphics2D g2 = (Graphics2D) g;

    g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
        RenderingHints.VALUE_ANTIALIAS_ON);

    g2.setRenderingHint(RenderingHints.KEY_RENDERING,
        RenderingHints.VALUE_RENDER_QUALITY);

    FontRenderContext frc = g2.getFontRenderContext();
    Font f = new Font("Helvetica", 1, 60);
    String s1 = "Java Source and Support.";
    TextLayout textTl = new TextLayout(s1, f, frc);

    AffineTransform transform1;
    Shape outline1 = textTl.getOutline(null);
    transform1 = g2.getTransform();

    double newWidth1 = 301;
    double newHeight1 = 427;

    textTl.draw(g2, (int)newWidth1, (int)newHeight1);

    transform1.translate(newWidth1, newHeight1);

    g2.transform(transform1);
    g2.setColor(Color.blue);
    g2.setStroke(new BasicStroke(4.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_ROUND));
    g2.draw(outline1);

  }
}

Upvotes: 1

Views: 907

Answers (1)

Joop Eggen
Joop Eggen

Reputation: 109603

There probably is no nice "half stroke." So first draw the outline, then fill the glyph vector. (For opaque colors only.)

transform1 = g2.getTransform();

double newWidth1 = 301;
double newHeight1 = 427;

transform1.translate(newWidth1, newHeight1);

g2.transform(transform1);
g2.setColor(Color.blue);
g2.setStroke(new BasicStroke(4.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_ROUND));
g2.draw(outline1);

textTl.draw(g2, 0, 0);

Which should be a short cut for:

...
transform1.translate(-newWidth1, -newHeight1);
textTl.draw(g2, (int)newWidth1, (int)newHeight1);

Upvotes: 2

Related Questions