Java 将 JPanel 转换为图像

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1349220/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 08:30:34  来源:igfitidea点击:

Convert JPanel to image

javaimageswingjpanel

提问by Jeff Storey

Is there a way to convert a JPanel (that has not yet been displayed) to a BufferedImage?

有没有办法将 JPanel(尚未显示)转换为 BufferedImage?

thanks,

谢谢,

Jeff

杰夫

采纳答案by Tom

From the BufferedImage you can create a graphics object, which you can use to call paint on the JPanel, something like:

从 BufferedImage 您可以创建一个图形对象,您可以使用它来调用 JPanel 上的绘制,例如:

public 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);
    g.dispose();
    return bi;
}

You may need to make sure you set the size of the panel first.

您可能需要确保首先设置面板的大小。

回答by camickr

Basically I'm building a component that needs to get written to an image but not displayed

基本上我正在构建一个需要写入图像但不显示的组件

ScreenImageexplains how to do what you want.

ScreenImage解释了如何做你想做的事。



Relevant section of ScreenImage.java (slightly edited). layoutComponentforces all buttons appear in the image.

ScreenImage.java 的相关部分(略有编辑)。layoutComponent强制所有按钮出现在图像中。

/**
 * @return Renders argument onto a new BufferedImage
 */
public BufferedImage createImage(JPanel panel, int width, int height) {
    BufferedImage bi = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
    Graphics2D g = bi.createGraphics();
    panel.setSize(width, height); // or panel.getPreferedSize()
    layoutComponent(panel);
    panel.print(g);
    g.dispose();
    return bi;
}

private void layoutComponent(Component component) {
    synchronized (component.getTreeLock()) {
        component.doLayout();

        if (component instanceof Container) {
            for (Component child : ((Container) component).getComponents()) {
                layoutComponent(child);
            }
        }
    }
}

回答by Rastislav Komara

Take a look at BasicTableUI. The cell renderer is drawn on image without showing and then drawn on visible table component.

看看 BasicTableUI。单元格渲染器在不显示的情况下绘制在图像上,然后绘制在可见的表格组件上。

回答by Pham Trung

The answer from Tom is basically correct, but invoke paint()directly is not recommended, as it is a synchronous call and can interrupt with other operation on the swing thread. Instead of using paint(), we should use print()instead

Tom的回答基本正确,但paint()不建议直接调用,因为它是同步调用,可以中断swing线程上的其他操作。而不是使用的paint(),我们应该用print()代替

public 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.print(g);
    g.dispose();
    return bi;
}