在BufferedImage上绘制Image对象供以后使用

时间:2013-05-24 13:40:53

标签: java image panel bufferedimage drawimage

我需要一些帮助,在BufferedImage上/ inside /上绘制一个Image对象,然后在JPanel上绘制BufferedImage。

我准备了一个小程序来说明我的问题。只是一个带有面板并带有ImageLoader的框架。

图像与代码放在同一文件夹中。刚绘制时,sten Image已成功绘制,但是当我尝试使用BufferedImage绘制它时,如果您尝试运行该程序,则会注意到它。只需创建Test对象,构造函数完成剩下的工作。

提前致谢!

我的代码:

public class Test extends JFrame{

static class ImageLoader {
    public static Image loadImage(String name){
        Image img = null;
        img = Toolkit.getDefaultToolkit().getImage(ImageLoader.class.getResource(name));
        return img;
    }
}

class Panel extends JPanel{

    Image sten;
    BufferedImage bf = new BufferedImage(500,500,BufferedImage.TYPE_INT_RGB);

    public Panel(Image sten){
        super();
        this.sten = sten;
        initBF();
    } 

    private void initBF(){
        Graphics2D g = (Graphics2D) bf.createGraphics();
        g.drawImage(sten, 0,0,this);
    }

    public void paintComponent (Graphics g)
    {
        g.drawImage(bf, 100,100,null);
        g.drawImage(sten, 0,0,null);
        repaint();
    } 
}


public Test(){
    setSize(new Dimension(500, 500));
    setEnabled(true);
    this.setBounds(50, 150, 500, 500);
    setVisible(true);

    Image sten = ImageLoader.loadImage("sten.png");;

    Panel panel = new Panel(sten);
    panel.setBackground(Color.GREEN);
    panel.setSize(500, 500);
    this.add(panel);

    setDefaultCloseOperation(EXIT_ON_CLOSE);

    panel.paintComponent(this.getGraphics());
}

}

2 个答案:

答案 0 :(得分:1)

问题是Toolkit.getDefaultToolkit().getImage异步加载图像,因此在调用paintComponent时不会加载。{1}}使用MediaTracker进行阻止,直到图片已加载为止:

public Image loadImage(String name) {
   Image img = null;
   MediaTracker tracker = new MediaTracker(myPanel); // pass the panel from ctor
   img = Toolkit.getDefaultToolkit().getImage(ImageLoader.class.getResource(name));
   tracker.addImage(img, 0);
   try {
      tracker.waitForID(0);
   } catch (InterruptedException e) {
      e.printStackTrace();
   }

   return img;
}

更简单

img = ImageIO.read(ImageLoader.class.getResource(name)));

这将消除使用MediaTracker

的需要

一些注意事项:

  • 请勿直接致电paintComponent,请通过调用repaint请求重拍。
  • 请勿使用getGraphics进行自定义绘画 - 这会使用暂时的Graphics参考。
  • 使用自定义Graphics参考时,请务必在完成参考后致电Graphics#dispose

答案 1 :(得分:1)

除了Reimeus'aswer之外,请注意Toolkit.getDefaultToolkit().getImage()是非阻塞的,它会异步加载图片,所以当您致电g.drawImage(sten, 0,0,this); sten时,可能仍然不会加载(参见方法的文档)。另见(假)bug report