将JUNG图写入图像:无法可靠地呈现完整的图形

时间:2011-02-28 17:28:15

标签: java image jung

我一直在使用JUNG来显示一些简单的图形,我想将它们中的几个写入PNG文件。不幸的是,图像经常在图形完成绘制之前呈现出来,这意味着我得到了不完整的图形 - 也就是说,只绘制了一个边缘或节点的图形 - 大约一半的时间。渲染到屏幕工作正常,这是为什么我很困惑的一部分。正如您将在下面看到的,我尝试了几种解决方法,但它们没有帮助。知道我正在使用的basicVisualizationServer不会直接绘制对BufferedImage有用的东西可能很有用 - 我尝试时只得到一个黑色图像。

谢谢!

  public void writeImage(String filename) {
    Layout layout = new CircleLayout<V, E>(jungGraph);
    layout.setSize(innerSize);
    bvs = new BasicVisualizationServer<V,E>(layout);
    float strokeWidth = 8f;
    bvs.getRenderContext().setVertexShapeTransformer(new ConstantTransformer(new Ellipse2D.Float(-24,-24,48,48)));
    bvs.getRenderContext().setArrowDrawPaintTransformer(new ConstantTransformer(Color.black));
    bvs.getRenderContext().setEdgeStrokeTransformer(new ConstantTransformer(new BasicStroke(strokeWidth)));
    bvs.getRenderContext().setEdgeArrowStrokeTransformer(new ConstantTransformer(new BasicStroke(strokeWidth)));
    bvs.getRenderContext().setEdgeLabelTransformer(new ToStringLabeller<E>());
    bvs.getRenderContext().setVertexLabelTransformer(new ToStringLabeller<V>());
    bvs.setPreferredSize(viewSize);
    //int width = bvs.getWidth(); // Always returns zero
    int width = viewFrame.getWidth();
    //int height = bvs.getHeight(); // Always returns zero
    int height = viewFrame.getHeight();

    BufferedImage bim = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
    Graphics2D g = bim.createGraphics();
    viewFrame.paintAll(g);

    g.dispose();
    //this.viewFrame.paintComponents(g);
    //try{Thread.sleep(1000);} catch(Exception e) {throw new RuntimeException(e);} // Sleeping doesn't help.
    try {
        File f = new File(filename);
        ImageIO.write(bim,"png",f);
        System.out.println("wrote image for " + jungGraph + " to "+ filename+ ":" + f.toString());
        //try{Thread.sleep(500);} catch(Exception e) {throw new RuntimeException(e);} // Doesn't help
    } catch (Exception e) {
        throw new RuntimeException(e);
    }
}

2 个答案:

答案 0 :(得分:2)

您也可以使用VisualizationImageServer。它是BasicVisualizationServer的子类型,它添加了一个getImage方法。我没有遇到正确渲染图形的麻烦。

您的代码将如下:

public void writeImage(String filename) {
    Layout layout = new CircleLayout<V, E>(jungGraph);
    layout.setSize(innerSize);
    bvs = new VisualizationImageServer<V,E>(layout);
    // [...]
    BufferedImage image = (BufferedImage)bvs.getImage();
}

答案 1 :(得分:1)

我们通常希望保存被操纵图形的状态。我们按照我们喜欢的方式缩放和定位组件,然后我们制作容器的照片。这可以这样实现:

  1. 从优秀的Rob Camick's blog
  2. 获取ScreenImage类
  3. 将JScrollPane中的JPanel或承载JUNG2图形的任何Component传递给ScreenImage.createImage以创建图像。

    private void writeToImageFile(String imageFileName) {
    
       BufferedImage bufImage = ScreenImage.createImage((JComponent) jPanel1);
       try {
           File outFile = new File(imageFileName);
           ImageIO.write(bufImage, "png", outFile);
           System.out.println("wrote image to " + imageFileName);
       } catch (Exception e) {
           System.out.println("writeToImageFile(): " + e.getMessage());
       }
    }
    
  4. 另请阅读上述博客的其他主题: - )