Getting the dimensions of a text in Swing

This example shows you how to center a text on the JFrame. It will take into account the specifics of the chosen font. Run it from command line like java Main Helvetica.

Main.java:

import java.awt.image.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
import java.awt.*;
 
public class Main extends JFrame {
   private String fontname;
   private String text = "Easter Island";
 
   public Main(String fontname) {
      this.fontname = fontname;
 
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
   } 

   public void paint(Graphics g) {
      super.paint(g);
 
      Graphics2D g2d = (Graphics2D) g;
      Font f = new Font(fontname, Font.BOLD, 36);
      FontMetrics fm = getFontMetrics(f);
 
      int swidth = fm.stringWidth(text);
      int sheight = fm.getAscent();
 
      int width = getSize().width;
      int height = getSize().height;
 
      g2d.setColor(Color.gray);
      g2d.drawLine(0, height/2, width, height/2);
      g2d.drawLine(width/2, 0, width/2, height);
 
      g2d.setColor(Color.black);
      g2d.setFont(f);
      g2d.drawString(text, width/2 - swidth/2, height/2 + sheight/2);
   }
  
   public static void main(String []args) {
      if (args.length == 0) {
         System.err.println("Usage: java Main <fontname>");
         System.exit(1);
      }
 
      Main main = new Main(args[0]);
      main.setVisible(true);
      main.setSize(300, 300);
   }
}

Drawing a string in a certain font in Swing

Use the method drawString that accepts the String and the x and y parameter. Be aware that the x and y coordinates refer to the baseline, so from the bottom up. If you prefer working from the top down, you can get the font ascent (from the API: the distance between the font’s baseline and the top of most alphanumerical characters) and add it to the y coordinate:

   FontMetrics fm = g2d.getFontMetrics();
   g2d.drawString("GOD'S", 20, 100+fm.getAscent());

Main.java:

import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   private Image image;
 
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      }); 
   }
 
   public void paint(Graphics g) {
      g.setColor(Color.black);
      g.fillRect(0, 0, getSize().width, getSize().height);
 
      Graphics2D g2d = (Graphics2D) g;
      Font f = new Font("Courier New", Font.BOLD, 40);
      g2d.setFont(f);
 
      g2d.setColor(Color.white);
 
      g2d.drawString("Small", 20, 60);
      g2d.drawString("and", 20, 110);
      g2d.drawString("Humble", 20, 160);  
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(180, 200);
      main.setVisible(true);
   }
}

Different types of join styles in Swing

Main.java:

import java.awt.event.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
   }
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;
 
      g2d.drawString("JOIN_BEVEL", 20, 35); 
      g2d.setStroke(new BasicStroke(15f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL));
      g2d.drawRect(20, 50, 80, 80);
 
      g2d.drawString("JOIN_MITER", 140, 35); 
      g2d.setStroke(new BasicStroke(15f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER));
      g2d.drawRect(140, 50, 80, 80);       
 
      g2d.drawString("JOIN_ROUND", 260, 35); 
      g2d.setStroke(new BasicStroke(15f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_ROUND));
      g2d.drawRect(260, 50, 80, 80);
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(360, 160);
      main.setVisible(true);
   }
}

Different types of endcap styles in Swing

Main.java:

import java.awt.event.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
   }
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;
 
      g2d.drawString("CAP_BUTT", 20, 35); 
      g2d.setStroke(new BasicStroke(10f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL,
                                    10f, new float[] { 15f }, 0f));
      g2d.drawRect(20, 50, 80, 80);
 
      g2d.drawString("CAP_ROUND", 140, 35); 
      g2d.setStroke(new BasicStroke(10f, BasicStroke.CAP_ROUND, BasicStroke.JOIN_BEVEL,
                                    10f, new float[] { 15f }, 0f));
      g2d.drawRect(140, 50, 80, 80);       
 
      g2d.drawString("CAP_SQUARE", 260, 35); 
      g2d.setStroke(new BasicStroke(10f, BasicStroke.CAP_SQUARE, BasicStroke.JOIN_BEVEL,
                                    10f, new float[] { 15f }, 0f));
      g2d.drawRect(260, 50, 80, 80);
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(360, 160);
      main.setVisible(true);
   }
}

Controlling transparancy when two Swing shapes overlap

Use the class AlphaComposite as shown in following example.

Main.java:

import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.text.*;
import java.awt.*;
 
public class Main extends JFrame {
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
   }
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;
 
      g2d.setColor(Color.blue);
      g2d.fill(new Ellipse2D.Float(50, 30, 80, 50));
      g2d.setColor(Color.red);
      g2d.fill(new Ellipse2D.Float(100, 30, 80, 50));
 
      g2d.setColor(Color.black);
      g2d.drawLine(0, 90, 250, 90);
      
      DecimalFormat decimalFormat = (DecimalFormat)NumberFormat.getInstance();
      decimalFormat.applyPattern("0.0");
 
      int yd = 80;
      for (float f = 1f; f>=0f; f-=.2f) {
         g2d.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 1f));
         g2d.setColor(Color.black);
         g2d.drawString("AlphaComposite = " + decimalFormat.format(f), 50, 50 + yd - 10);
         g2d.setColor(Color.blue);
         g2d.fill(new Ellipse2D.Float(50, 50 + yd, 80, 50));
 
         AlphaComposite ac = AlphaComposite.getInstance(AlphaComposite.SRC_OVER, f);
         g2d.setComposite(ac);
 
         g2d.setColor(Color.red);
         g2d.fill(new Ellipse2D.Float(100, 50 + yd, 80, 50));
 
         yd += 80;
      }
   }
  
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(250, 600);
      main.setVisible(true);
   }
}

Drawing a curve with two control points

Use the class CubicCurve.

This example draws a curve on a frame using two end points and two control points. It allows you to grab an end or control point and drag it around. In addition, the curve has been texture-painted.

Main.java:

import java.awt.image.*;
import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   private BufferedImage image; 
   Point2D[] curvePoints; 
   Point2D selectedCurvePoint;
 
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
 
      image = toBufferedImage(new javax.swing.ImageIcon("c:\djkrush.jpg").getImage());
 
      curvePoints = new Point2D[4];
      curvePoints[0] = new Point2D.Double( 50, 150);
      curvePoints[1] = new Point2D.Double(100,  50);
      curvePoints[2] = new Point2D.Double(200, 250);
      curvePoints[3] = new Point2D.Double(250, 150);
 
      addMouseListener(new MouseAdapter() {
         public void mousePressed(MouseEvent me) {
            selectedCurvePoint = null;
            for (int i=0; i<curvePoints.length; i++) {
               Rectangle2D rect = getCurvePoint(curvePoints[i]);
               if (rect.contains(me.getPoint())) {
                  selectedCurvePoint = curvePoints[i];
                  break;
               }
            }
         }
      });
 
      addMouseMotionListener(new MouseMotionAdapter() {
         public void mouseDragged(MouseEvent me) {
            if (selectedCurvePoint != null) {
               selectedCurvePoint.setLocation(me.getPoint());
               repaint();
            }
         }
      });
   }
 
 
   public void paint(Graphics g) {
      super.paint(g); 
 
      Graphics2D g2d = (Graphics2D) g;
 
      Rectangle2D tr = new Rectangle2D.Double(0, 0, image.getWidth(), image.getHeight());
      TexturePaint tp = new TexturePaint(image, tr);
 
      // draw texture filled ellipse, but with antialiasing
      g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                           RenderingHints.VALUE_ANTIALIAS_ON);
      BasicStroke bs = new BasicStroke(5, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           10, null, 0);
      g2d.setStroke(bs);
      g2d.setPaint(tp);
 
      CubicCurve2D cc = new CubicCurve2D.Float();
      cc.setCurve(curvePoints, 0);
      g2d.draw(cc);
      g2d.setColor(Color.black);
      for (int i=0; i<4; i++) {
         g2d.draw(getCurvePoint(curvePoints[i]));
      } 
   }
 
   public Rectangle2D.Float getCurvePoint(Point2D p2d) {
      return new Rectangle2D.Float((int) p2d.getX()-2, (int) p2d.getY()-2, 4, 4);
   }
 
   public BufferedImage toBufferedImage(Image image) {
      BufferedImage bi = new BufferedImage(image.getWidth(null), image.getHeight(null), 
                                           BufferedImage.TYPE_INT_RGB); 
 
      // copy the original image
      Graphics g = bi.createGraphics();
    
      g.drawImage(image, 0, 0, null);
      g.dispose();
 
      return bi;
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(300, 300);
      main.setVisible(true);
   }
}

Image used:

Checking for a mouseclick on a Swing shapes

This following example create an arbitrary shape using GeneralPath and allows you to click anywhere on the JFrame. If the mouseclick x and y coordinate are within the shape, e method contains will return true.

Main.java:

import java.awt.image.*;
import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   private GeneralPath gp;
  
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
 
      constructShape();
  
      addMouseListener(new MouseAdapter() {
         public void mouseClicked(MouseEvent me) {
            me.translatePoint(-150, -150);
 
            if (gp.contains(me.getX(), me.getY())) {
               System.out.println(me.getX() + ", " + me.getY() + 
                                  " lies within the shape.");
            }
            else {
               System.out.println(me.getX() + ", " + me.getY() + 
                                  " lies not within the shape.");
            }
         }
      });
   }
 
   public void constructShape() {
      gp = new GeneralPath();
      gp.moveTo(   0,  100);
      gp.quadTo( -75,   25,    0, -100);
      gp.quadTo(  75,   25,    0,  100);
      gp.lineTo( -50,  -50);
      gp.lineTo(  50,  -50);
      gp.closePath();
   }   
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;
 
      // set origin to middle of window
      g2d.translate(150f, 150f);
 
      g2d.draw(gp);
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(300, 300);
      main.setVisible(true);
   }
}

Combining two shapes in Swing

Cast the shapes to areas where you have the methods add, subtract, intersect and exclusiveOr.

Main.java:

import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      }); 
   }
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;
 
      Shape shape1 = new Rectangle2D.Double(80, 50, 40, 40);
      Shape shape2 = new Rectangle2D.Double(20, 60, 160, 20);
 
      g2d.setColor(Color.black); 
      g2d.drawString("normal:", 20, 40);
      g2d.draw(shape1); 
      g2d.draw(shape2); 
 
      g2d.translate(0, 70);
      g2d.setColor(Color.yellow); 
      g2d.fill(combine("add", shape1, shape2));
      g2d.setColor(Color.black); 
      g2d.drawString("area add:", 20, 40);
      g2d.draw(shape1); 
      g2d.draw(shape2); 
 
      g2d.translate(0, 70);
      g2d.setColor(Color.yellow); 
      g2d.fill(combine("subtract", shape1, shape2));
      g2d.setColor(Color.black); 
      g2d.drawString("area subtract:", 20, 40);
      g2d.draw(shape1); 
      g2d.draw(shape2); 
 
      g2d.translate(0, 70);
      g2d.setColor(Color.yellow); 
      g2d.fill(combine("intersect", shape1, shape2));
      g2d.setColor(Color.black); 
      g2d.drawString("area intersect:", 20, 40);
      g2d.draw(shape1); 
      g2d.draw(shape2); 
 
      g2d.translate(0, 70);
      g2d.setColor(Color.yellow); 
      g2d.fill(combine("exclusiveOr", shape1, shape2));
      g2d.setColor(Color.black); 
      g2d.drawString("area exclusiveOr:", 20, 40);
      g2d.draw(shape1); 
      g2d.draw(shape2); 
   }
 
   public Shape combine(String op, Shape shape1, Shape shape2) {
      Area area1 = new Area(shape1);
      Area area2 = new Area(shape2);
      
      if (op.equals("add")) area1.add(area2);
      else if (op.equals("subtract")) area1.subtract(area2);
      else if (op.equals("intersect")) area1.intersect(area2);
      else if (op.equals("exclusiveOr")) area1.exclusiveOr(area2);
 
      return area1;
   }
  
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(200, 400);
      main.setVisible(true);
   }
}

Changing the outline thickness of a shape in Swing

Main.java:

import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
   }
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;
 
      BasicStroke bs = new BasicStroke(3, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                                       10, null, 0);
      g2d.setStroke(bs);
      QuadCurve2D.Float qc = new QuadCurve2D.Float(20, 50, 100, 50, 100, 170);
      g2d.draw(qc);
 
      bs = new BasicStroke(5, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           10, null, 0);
      g2d.setStroke(bs);
      Ellipse2D.Float e = new Ellipse2D.Float(140, 50, 80, 120);
      g2d.draw(e);
 
      bs = new BasicStroke(10, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           10, null, 0);
      g2d.setStroke(bs);
      g2d.drawRect(260, 50, 80, 120);
 
      GradientPaint gp = new GradientPaint(380, 50, Color.red, 460, 170, Color.blue);
      g2d.setPaint(gp);
      bs = new BasicStroke(15, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           10, null, 0);
      g2d.setStroke(bs);
      g2d.drawRect(380, 50, 80, 120);
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(480, 200);
      main.setVisible(true);
   }
}

Drawing a rectangle with dashed lines in Swing

Main.java:

import java.awt.event.*;
import javax.swing.*;
import java.awt.*;
 
public class Main extends JFrame {
   public Main() {
      addWindowListener(new WindowAdapter() {
         public void windowClosing(WindowEvent we) {
            System.exit(1);
         }
      });
   }
 
   public void paint(Graphics g) {
      Graphics2D g2d = (Graphics2D) g;

      BasicStroke bs = new BasicStroke(1, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                                       10, new float[] {10}, 0);
      g2d.setStroke(bs);
      g2d.drawRect(20, 50, 80, 80);
 
      bs = new BasicStroke(1, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           10, new float[] {1, 2, 4, 8, 16, 32}, 0);
      g2d.setStroke(bs);
      g2d.drawRect(140, 50, 80, 80);
 
      bs = new BasicStroke(5, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           5, new float[] {10}, 0);
      g2d.setStroke(bs);
      g2d.drawRect(260, 50, 80, 80);
 
      bs = new BasicStroke(1, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER,
                           10, new float[] {1}, 0);
      g2d.setStroke(bs);
      g2d.drawRect(380, 50, 80, 80);
   }
 
   public static void main(String []args) {
      Main main = new Main();
      main.setSize(480, 160);
      main.setVisible(true);
   }
}