I use NetBeans and I wanted to show an image on a jPanel (basically to make it scroll).
I wrote this code
Graphics g=jPanelScrolling.getGraphics();
File fileBackground = new File("background.jpg");
Image background;
try{
background=ImageIO.read(fileBackground);
final int WIDTH=background.getWidth(rootPane);
final int HEIGHT=background.getHeight(rootPane);
g.drawImage(background, WIDTH, HEIGHT, rootPane);
}
catch(IOException e){
background=null;
jPanelScrolling.setBackground(Color.red); //to test if the image has been succesfully uploaded
}
but when I execute it, it shows me only the void jPanel
How can I make it work?
Try,
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.*;
public class ImageInFrame {
public static void main(String[] args) throws IOException {
String path = "Image1.jpg";
File file = new File(path);
BufferedImage image = ImageIO.read(file);
JLabel label = new JLabel(new ImageIcon(image));
JFrame f = new JFrame();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.getContentPane().add(label);
f.pack();
f.setLocation(200,200);
f.setVisible(true);
}
}
Want to display Image, try something like this:
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.imageio.ImageIO;
import javax.swing.*;
public class ImagePanel extends JPanel{
private BufferedImage bi;
public ImagePanel() {
try {
bi = ImageIO.read(new File("Your Image Path"));
} catch (IOException ex) {
Logger.getLogger(ImagePanel.class.getName()).log(Level.SEVERE, null, ex);
}
final JPanel panel = new JPanel(){
#Override
protected void paintComponent(Graphics g){
Graphics g2 = g.create();
g2.drawImage(bi, 0, 0, getWidth(), getHeight(), null);
g2.dispose();
}
#Override
public Dimension getPreferredSize(){
return new Dimension(bi.getWidth()/2, bi.getHeight()/2);
//return new Dimension(200, 200);
}
};
add(panel);
}
public static void main(String args[]){
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
ImagePanel imgPanel=new ImagePanel();
JOptionPane.showMessageDialog(
null, imgPanel, "Image Panel", JOptionPane.PLAIN_MESSAGE);
}
});
}
}
Output
Related
I want draw a picture with Java.
And I want rotate this picture along the X-axis or Y-axis to make the picture perspective.
It can make the image three-dimensional.
Do you know the function '3D rotation' in the PowerPoint? I just want to achieve this effect.
Can I use java to make it?
I am sorry that I have not describe my question carefully before.
This is the original image:
original image
I added a shear operation when I drew it
#Override
protected void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D)g;
g2d.clearRect(0, 0, this.getWidth(), this.getHeight());
if (sourceImage != null) {
g2d.shear(0.5, 0);
g2d.drawImage(sourceImage, 0, 0, sourceImage.getWidth(), sourceImage.getHeight(), null);
}
}
And then it looks like this
The transformed image
But this is a linear transformation, I want perspective image, just like this
What I need to achieve
The AffineTransform in JAVA can only do linear transformations.
How can I use PerspectiveTransform, Do I need to use OpenGL or OpenCV to achieve it?
This is my complete code
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import javax.swing.JPanel;
public class ImagePanel extends JPanel{
private static final long serialVersionUID = 1L;
private BufferedImage sourceImage;
public ImagePanel() {
}
#Override
protected void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D)g;
g2d.clearRect(0, 0, this.getWidth(), this.getHeight());
if (sourceImage != null) {
g2d.shear(0.5, 0);
g2d.drawImage(sourceImage, 0, 0, sourceImage.getWidth(), sourceImage.getHeight(), null);
}
}
public BufferedImage getSourceImage() {
return sourceImage;
}
public void setSourceImage(BufferedImage sourceImage) {
this.sourceImage = sourceImage;
}
}
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.JButton;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.filechooser.FileNameExtensionFilter;
public class MainUI extends JFrame implements ActionListener {
private static final long serialVersionUID = 1L;
public static final String IMAGE_CMD = "choose image ... ";
private JButton imgBtn;
private ImagePanel imagePanel;
private BufferedImage srcImage;
public MainUI() {
setTitle("image demo");
imgBtn = new JButton(IMAGE_CMD);
JPanel btnPanel = new JPanel();
btnPanel.setLayout(new FlowLayout(FlowLayout.RIGHT));
btnPanel.add(imgBtn);
imagePanel = new ImagePanel();
getContentPane().setLayout(new BorderLayout());
getContentPane().add(imagePanel, BorderLayout.CENTER);
getContentPane().add(btnPanel, BorderLayout.SOUTH);
imgBtn.addActionListener(this);
}
#Override
public void actionPerformed(ActionEvent e) {
if(IMAGE_CMD.equals(e.getActionCommand())){
try {
JFileChooser chooser = new JFileChooser();
setFileTypeFilter(chooser);
chooser.showOpenDialog(null);
File f = chooser.getSelectedFile();
if (f != null) {
srcImage = ImageIO.read(f);
imagePanel.setSourceImage(srcImage);
imagePanel.repaint();
}
} catch (IOException e1) {
e1.printStackTrace();
}
imagePanel.repaint();
}
}
public void setFileTypeFilter(JFileChooser chooser){
FileNameExtensionFilter filter = new FileNameExtensionFilter("JPG & PNG Images", "jpg", "png");
chooser.setFileFilter(filter);
}
public void openView(){
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setPreferredSize(new Dimension(1280, 960));
pack();
setVisible(true);
}
public static void main(String[] args) {
MainUI ui = new MainUI();
ui.openView();
}
}
I want to fill a panel with a BufferedImage (striped, see link below) and print it on a printer. The thing is that the pattern doesn't print, but it is visible as wanted on the panel. If I use a color instead of the striped image this gets printed.
You see two comments in the paintComponent-method below. Any ideas why I don't see the BufferedImage when I print?
Thanks!
You can find the image used here: http://imgur.com/sSlVUzK
package printbufferedimagepanel;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.TexturePaint;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import java.awt.print.PageFormat;
import java.awt.print.Printable;
import static java.awt.print.Printable.NO_SUCH_PAGE;
import static java.awt.print.Printable.PAGE_EXISTS;
import java.awt.print.PrinterException;
import java.awt.print.PrinterJob;
import java.io.File;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.imageio.ImageIO;
public class PrintBufferedImagePanel {
JFrame mainFrame;
JPanel mainPanel;
Buff printMe;
JButton printButton;
BufferedImage bf;
public PrintBufferedImagePanel() {
prepareGUI();
}
public static void main(String[] args) {
PrintBufferedImagePanel bip = new PrintBufferedImagePanel();
}
private void prepareGUI() {
mainFrame = new JFrame();
mainFrame.setLayout(new FlowLayout());
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainPanel = new JPanel();
printMe = new Buff();
printButton = new JButton("Print");
mainPanel.setSize(400, 150);
mainPanel.add(printMe);
mainFrame.add(mainPanel);
mainFrame.add(printButton);
mainFrame.setSize(400, 250);
mainFrame.setVisible(true);
printButton.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
PrinterJob job = PrinterJob.getPrinterJob();
job.setPrintable(printMe);
boolean ok = job.printDialog();
if (ok) {
try {
job.print();
} catch (PrinterException de) {
System.err.println("Oops!");
}
}
}
});
}
class Buff extends JPanel implements Printable {
#Override
public Dimension getPreferredSize() {
return new Dimension(400,150);
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
BufferedImage bImage = null;
TexturePaint tp = null;
try {
bImage = ImageIO.read(new File("src/printbufferedimagepanel/blueStripes.jpg"));
tp = new TexturePaint(bImage, new Rectangle(0,0,bImage.getWidth(),bImage.getHeight()));
Graphics2D g2 = (Graphics2D)g;
g2.setPaint(tp); //<-- doesn't show at print, Why?
//g2.setColor(Color.CYAN); //<-- does show at print
g2.fillRect(0, 0, 400, 150);
} catch (Exception e) {
System.out.println("oops");
}
}
#Override
public int print(Graphics graphics, PageFormat pageFormat, int pageIndex) throws PrinterException {
if (pageIndex > 0) {
return NO_SUCH_PAGE;
}
Graphics2D g2d = (Graphics2D)graphics;
g2d.translate(pageFormat.getImageableX(), pageFormat.getImageableY());
this.printAll(graphics);
return PAGE_EXISTS;
}
}
}
I want to achieve following functionality :
Eg :
When user selects "Profile Pic"item from JComboBox releted images from "Profile Pic" folder should be loaded on same frame.
Again when user selects "Product Img" item related images from "Product Img" folder should be loaded replacing previous images.
Following is code snippet , please suggest any changes
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.event.ActionEvent;
import java.awt.event.FocusAdapter;
import java.awt.event.FocusEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.image.BufferedImage;
import java.net.URL;
import java.util.ArrayList;
import javax.imageio.ImageIO;
import javax.swing.AbstractAction;
import javax.swing.Icon;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.KeyStroke;
import javax.swing.SwingUtilities;
import javax.swing.border.LineBorder;
public class NewClass1 {
public static void main(String[] args) {
createAndShowJFrame();
}
public static void createAndShowJFrame() {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
JFrame frame = createJFrame();
frame.setVisible(true);
}
});
}
private static JFrame createJFrame() {
JFrame frame = new JFrame();
//frame.setResizable(false);//make it un-resizeable
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setTitle("Test");
ArrayList<BufferedImage> images = null;
try {
images = getImagesArrayList();
} catch (Exception ex) {
ex.printStackTrace();
}
final ImageViewPanel imageViewPanel = new ImageViewPanel(images);
JScrollPane jsp = new JScrollPane(imageViewPanel);
jsp.setPreferredSize(new Dimension(400, 400));
frame.add(jsp);
final javax.swing.JComboBox filter = new javax.swing.JComboBox<>();
filter.addItem("All");
filter.addItem("Profile Pic");
filter.addItem("Company Logo");
filter.addItem("Product Img");
JPanel controlPanel = new JPanel();
JButton addLabelButton = new JButton("Delete Selected Image");
addLabelButton.addActionListener(new AbstractAction() {
#Override
public void actionPerformed(ActionEvent e) {
imageViewPanel.removeFocusedImageLabel();
}
});
JLabel label =new JLabel("Filter By :");
filter.addActionListener(new AbstractAction() {
#Override
public void actionPerformed(ActionEvent e) {
String cat=(String) filter.getSelectedItem();
createJFrame(cat);
}
});
controlPanel.add(addLabelButton);
controlPanel.add(label);
controlPanel.add(filter);
frame.add(controlPanel, BorderLayout.NORTH);
frame.pack();
return frame;
}
private static ArrayList<BufferedImage> getImagesArrayList(String cat) throws Exception {
System.out.println(cat);
ArrayList<BufferedImage> images = new ArrayList<>();
if(cat.equals("Profile Pic"))
images.add(resize(ImageIO.read(new URL("http://192.168.1.25:8080/pic/ProfilePic/1.jpg")), 100, 100));
else if(cat.equals("Product Img"))
{
images.add(resize(ImageIO.read(new URL("http://192.168.1.25:8080/pic/ProductImg/2.jpg")), 100, 100));
}
return images;
}
private static ArrayList<BufferedImage> getImagesArrayList() throws Exception {
ArrayList<BufferedImage> images = new ArrayList<>();
images.add(resize(ImageIO.read(new URL("http://localhost:8080/pic/All/a.jpg")), 100, 100));
images.add(resize(ImageIO.read(new URL("http://localhost:8080/pic/All/b.jpg")), 100, 100));
return images;
}
public static BufferedImage resize(BufferedImage image, int width, int height) {
BufferedImage bi = new BufferedImage(width, height, BufferedImage.TRANSLUCENT);
Graphics2D g2d = (Graphics2D) bi.createGraphics();
g2d.addRenderingHints(new RenderingHints(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY));
g2d.drawImage(image, 0, 0, width, height, null);
g2d.dispose();
return bi;
}
}
I would urge you to have another look at the code I posted (which you seem to be using) Deleting images from JFrame.
However:
In your code I see:
filter.addActionListener(new AbstractAction() {
#Override
public void actionPerformed(ActionEvent e) {
String cat=(String) filter.getSelectedItem();
createJFrame(cat);
}
});
I cannot even find the method createJFrame(String cat);?
As far as I see you should be doing this:
filter.addActionListener(new AbstractAction() {
#Override
public void actionPerformed(ActionEvent e) {
String cat=(String) filter.getSelectedItem();
ArrayList<BufferedImage> images=getImagesArrayList(cat);//get the new images for the selected item in combo
//refresh the layout by removing old pics and itertating the new array and adding pics to the panel as you iterate
layoutLabels(images);
}
});
....
private JLabel NO_IMAGES=new JLabel("No Images");
private void layoutLabels(ArrayList<BufferedImage> images) {
removeAll();//remove all components from our panel (the panel should only have the images on if not use setActionCommand("Image") on your images/JLabels and than use getComponents of JPanel and iterate through them looking for getActionCommand.equals("Image")
if (images.isEmpty()) {//if the list is empty
add(NO_IMAGES);//add Jlabel to show message of no images
} else {
remove(NO_IMAGES);
for (BufferedImage i : images) {//iterate through ArrayList of images
add(new JLabel(new ImageIcon(i)));//add each to the panel using JLabel as container for image
}
}
revalidate();
repaint();
}
I got a problem with two problematics classes. One for drawing things, and other for implementing pan and zoom onto the previously drawn objects.
Imagine my interface as only two spitted panels, one empty(top) and one with a slider(bot):
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import javax.swing.JFrame;
import javax.swing.JScrollPane;
import java.awt.BorderLayout;
import javax.swing.JSplitPane;
import javax.swing.JPanel;
import javax.swing.BoxLayout;
import javax.swing.JLabel;
import javax.swing.JSlider;
import java.awt.FlowLayout;
public class Interface {
private JFrame mainFrame;
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {Interface window = new Interface();window.mainFrame.setVisible(true);
} catch (Exception e) { e.printStackTrace();}
}
});
}
public Interface() {initialize();}
private void initialize() {
mainFrame = new JFrame();
mainFrame.setTitle("LXView");
mainFrame.setMinimumSize(new Dimension(800, 600));
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainFrame.setExtendedState(mainFrame.getExtendedState()| JFrame.MAXIMIZED_BOTH);
mainFrame.getContentPane().setBackground(Color.WHITE);
mainFrame.getContentPane().setLayout(new BorderLayout(0, 0));
JSplitPane splitPane = new JSplitPane();
splitPane.setOrientation(JSplitPane.VERTICAL_SPLIT);
splitPane.setOneTouchExpandable(true);
splitPane.setBackground(Color.WHITE);
mainFrame.getContentPane().add(splitPane, BorderLayout.CENTER);
splitPane.setResizeWeight(0.99);
JScrollPane scrollPane = new JScrollPane();
scrollPane.setEnabled(false);
splitPane.setLeftComponent(scrollPane);
Render topPane = new Render();
scrollPane.setViewportView(topPane);
topPane.setLayout(new BoxLayout(topPane, BoxLayout.X_AXIS));
JPanel botPane = new JPanel();
splitPane.setRightComponent(botPane);
botPane.setLayout(new FlowLayout(FlowLayout.CENTER, 5, 5));
JLabel zoomLevel = new JLabel("Zoom level:");
botPane.add(zoomLevel);
JSlider slider = new JSlider(JSlider.HORIZONTAL, 25, 100, 100);
slider.setMajorTickSpacing(15);
slider.setMinorTickSpacing(5);
slider.setPaintTicks(true);
slider.setPaintLabels(true);
slider.setPreferredSize(new Dimension(600,40));
botPane.add(slider);
PanAndZoom zoomer=new PanAndZoom(topPane.getLabel());
slider.addChangeListener(zoomer);
}
The top panel uses the render class which was made to draw graphics. Simplifying:
import javax.swing.ImageIcon;
import javax.swing.JLabel;
import javax.swing.JPanel;
public class Render extends JPanel {
JLabel envContainer;
Render() {
super();
ImageIcon imageIcon = new ImageIcon("/path/to/img1");
JLabel envContainer = new JLabel(imageIcon);
super.add(envContainer);
}
#Override
public void paint(Graphics g) {
super.paint(g);
/*Render stuff*/
}
public JLabel getLabel() {
return envContainer;
}
}
And the third class which is giving me the trouble, listens on the slider and sets the JLabel icon according to it:
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JLabel;
import javax.swing.JSlider;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
public class PanAndZoom implements ChangeListener {
private JLabel label;
private BufferedImage image;
public PanAndZoom(JLabel lab){
this.label=lab;
try {
image = ImageIO.read(new File("/path/to/img1"));
} catch (IOException e) {
e.printStackTrace();
}
label.setIcon(new ImageIcon("/path/to/img2"));//To test another img. It gives runtime errors.
}
public void stateChanged(ChangeEvent e) {
int value = ((JSlider) e.getSource()).getValue();
double scale = value / 100.0;
BufferedImage scaled = getScaledImage(scale); // It also gives runtime errors.
System.out.println("Scale:"+scale+" Value:"+value);
label.setIcon(new ImageIcon(scaled));
label.revalidate();
}
private BufferedImage getScaledImage(double scale) {
int w = (int) (scale * image.getWidth());
int h = (int) (scale * image.getHeight());
BufferedImage bi = new BufferedImage(w, h, image.getType());
Graphics2D g2 = bi.createGraphics();
g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION,RenderingHints.VALUE_INTERPOLATION_BICUBIC);
AffineTransform at = AffineTransform.getScaleInstance(scale, scale);
g2.drawRenderedImage(image, at);
g2.dispose();
return bi;
}
}
Why cant i use the JLabel if it was successfully returned by the getLabel method?
You're local version of envContainer in class Render's constructor is overriding the class instance envContainer.
public class Render extends JPanel {
JLabel envContainer; //<---- class instance
Render() {
super();
ImageIcon imageIcon = new ImageIcon("/path/to/img1");
JLabel envContainer = new JLabel(imageIcon); //<---- overriden by local instance, hence class instance remains null
super.add(envContainer);
}
My guess is that you didn't mean to make it a local version since you're not using it within the constructor for anything. Make the following change to your Render constructor.
Render() {
..
this.envContainer = new JLabel(imageIcon);
...
}
I am writing a program in which I paint on a JPanel. How do I get an Image of the JPanel which is painted on it?
I tried this code but all I get is a blank image with the Background color of my JPanel.
The BufferedImage does not contain what is painted on my panel.
private BufferedImage createImage(JPanel panel) {
int w = panel.getWidth();
int h = panel.getHeight();
BufferedImage bi = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
Graphics2D g = bi.createGraphics();
panel.paint(g);
return bi;
}
What am I doing wrong?
Here is an SSCCE illustrating that it works. A common mistake is to pass null as the ImageObserver of the drawImage method, because the loading of the image is asynchronous.
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
public class TestPrint {
protected static void initUI() throws MalformedURLException {
final ImageIcon image = new ImageIcon(new URL("http://www.travelblog.org/Wallpaper/pix/tb_fiji_sunset_wallpaper.jpg"));
JPanel panel = new JPanel() {
#Override
protected void paintComponent(java.awt.Graphics g) {
super.paintComponent(g);
g.drawImage(image.getImage(), 0, 0, this);
};
};
panel.setPreferredSize(new Dimension(image.getIconWidth(), image.getIconHeight()));
panel.setSize(panel.getPreferredSize());
BufferedImage bi = new BufferedImage(panel.getWidth(), panel.getHeight(), BufferedImage.TYPE_INT_RGB);
Graphics g = bi.createGraphics();
panel.print(g);
g.dispose();
try {
ImageIO.write(bi, "png", new File("test.png"));
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
try {
initUI();
} catch (MalformedURLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
}
}
Here's a quick example method that you can add to any of your Java 2/JDK 1.2 applications. Simply pass in the component you want to snapshot and the filename you want to save into.
public void saveComponentAsJPEG(Component myComponent, String filename) {
Dimension size = myComponent.getSize();
BufferedImage myImage = new BufferedImage(size.width, size.height, BufferedImage.TYPE_INT_RGB);
Graphics2D g2 = myImage.createGraphics();
myComponent.paint(g2);
try {
OutputStream out = new FileOutputStream(filename);
JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
encoder.encode(myImage);
out.close();
} catch (Exception e) {
System.out.println(e);
}
}
This method is very versatile. It can be used to take snapshots of a wide variety of Java application components. Please do be forewarned, however, that you use com.sun.image.codec.jpeg at some risk to the portability of your code.
EDIT:
I tested the code to make sure and all seems fine:
import com.sun.image.codec.jpeg.JPEGCodec;
import com.sun.image.codec.jpeg.JPEGImageEncoder;
import java.awt.*;
import java.awt.geom.Ellipse2D;
import java.awt.image.BufferedImage;
import java.io.FileOutputStream;
import java.io.OutputStream;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class ScreenCapture extends JFrame {
public ScreenCapture() {
createAndShowUI();
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
ScreenCapture screenCapture = new ScreenCapture();
}
});
}
private void createAndShowUI() {
setTitle("Test Screen Capture");
setSize(300, 300);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
getContentPane().add(new DrawingPanel());
setVisible(true);
saveComponentAsJPEG(this, "C:/test.jpg");
}
public void saveComponentAsJPEG(Component myComponent, String filename) {
Dimension size = myComponent.getSize();
BufferedImage myImage = new BufferedImage(size.width, size.height, BufferedImage.TYPE_INT_RGB);
Graphics2D g2 = myImage.createGraphics();
myComponent.paint(g2);
try {
OutputStream out = new FileOutputStream(filename);
JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
encoder.encode(myImage);
out.close();
} catch (Exception e) {
System.out.println(e);
}
}
class DrawingPanel extends JPanel {
public DrawingPanel() {
setDoubleBuffered(true);
}
#Override
public void paintComponent(Graphics grphcs) {
super.paintComponents(grphcs);
Graphics2D g2d = (Graphics2D) grphcs;
RenderingHints rhints = g2d.getRenderingHints();
boolean antialiasOn = rhints.containsValue(RenderingHints.VALUE_ANTIALIAS_ON);
if (!antialiasOn) {
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
}
Shape circle = new Ellipse2D.Float(100.0f, 100.0f, 100.0f, 100.0f);
g2d.setColor(Color.RED);
g2d.draw(circle);
g2d.fill(circle);
}
}
}
Your code works for me.
Here is a simple example. Resize the frame to see the panel change size and the image move around.
public static void main(String[] args) {
JFrame frame = new JFrame("Test");
JPanel panel = new JPanel();
panel.setBackground(Color.BLUE);
JLabel label = new JLabel("Image");
label.setForeground(Color.RED);
panel.add(label);
frame.add(panel, BorderLayout.NORTH);
frame.pack();
JLabel image = new JLabel(new ImageIcon(createImage(panel)));
frame.add(image, BorderLayout.SOUTH);
frame.pack();
label.setText("Original");
frame.setVisible(true);
}
private static BufferedImage createImage(JPanel panel) {
int w = panel.getWidth();
int h = panel.getHeight();
BufferedImage bi = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
Graphics2D g = bi.createGraphics();
panel.paint(g);
return bi;
}
So your problem must be elsewhere. Make sure your panel has positive size at the point that you create an image of it.