I would like to render a Java Swing component, e.g. a JButton, which I also put on a JFrame, to a BufferedImage. This works in general, but with a major drawback: Text anti aliasing, especially "LCD" anti aliasing mode, is not working when rendering to a BufferedImage.
I've put some example code together to demonstrate the problem, but first my system information:
- OS: Windows 7 64 Bit
- JVM: 1.6.0_26-b03 (32 Bit)
The following example code will create a simple JFrame, put a JButton on it and then renders the JButton to a file "test.png":
public class TextAntiAliasingTest
{
public TextAntiAliasingTest() throws IOException
{
// Create Test-Button which will be rendered to an image
JButton button = new JButton( "The Test-Button" );
button.setSize( 200, 70 );
button.setLocation( 200, 150 );
// Create JFrame
final JFrame frame = new JFrame();
frame.setSize( 800, 600 );
frame.setDefaultCloseOperation( JFrame.EXIT_ON_CLOSE );
frame.setLayout( null );
frame.setLocationRelativeTo( null );
frame.add( button );
// Show JFrame
SwingUtilities.invokeLater( new Runnable() {
@Override public void run() {
frame.setVisible( true );
}
});
// Render JButton to an BufferedImage
BufferedImage image = new BufferedImage( 800, 600, BufferedImage.TYPE_INT_ARGB );
Graphics2D g2d = (Graphics2D)image.getGraphics();
button.paint( g2d );
// Write BufferedImage to a PNG file
ImageIO.write( image, "PNG", new File( "test.png" ) );
}
public static void main( String[] args ) throws Exception
{
UIManager.setLookAndFeel( "com.sun.java.swing.plaf.windows.WindowsLookAndFeel" );
System.setProperty( "awt.useSystemAAFontSettings", "lcd" );
new TextAntiAliasingTest();
}
}
The following image shows the difference between the JButton in the JFrame on screen, and the same rendered JButton in the image file:
Actually there is some text anti aliasing in the image, but not the LCD optimized anti aliasing which is shown on screen in the JFrame (this problem occurs also with the default LookAndFeel, not only with the "WindowsLookAndFeel").
I already tried to explicitely set the RenderingHint for text anti aliasing on the "g2d", the Graphics2D context of the BufferedImage like so:
g2d.setRenderingHint( RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_LCD_HRGB );
But it had no effect at all.
I urgently need to render the JButton to an image file like it is rendered on screen (this is just an example, actually I need to render some more complex components, which all suffer from that anti aliasing problem) and I hope there is a real solution without any nasty workaround like taking a screenshot or something.
I really appreciate any help - thanks a lot!