1

我正在使用 RadialGradientPaint 创建一个 cricle 渐变,将它放在一个 BufferedImage 上并将图像渲染到我的 2d 游戏屏幕上,从而创建一个很好的暗光效果。但是,我想创建更多光源,但是为每个灯创建和渲染一个新的 BufferedImage 并不能完成这项工作(通常只看到最后一个灯,其他所有灯都是黑色的)。是否可以将一些 RadialGradientPaint 烘焙到一个 BufferedImage 中或以其他方式实现多灯效果?

附上你可以找到一盏灯的样子的图像。它是一个黑色的 BufferedImage,在屏幕顶部应用了 RadialGradientPaint。我想以某种方式添加更多这些。

单灯

4

2 回答 2

2

这个问题的解决方案是使用这个(正如@JanDvorak 评论中指出的那样:合并两个图像

我使用的确切代码是这样的:

public static BufferedImage mergeImages2(BufferedImage base, Collection<Light> images) {
    BufferedImage output = new BufferedImage(base.getWidth(), base.getHeight(), BufferedImage.TYPE_INT_ARGB);

    Graphics2D g = output.createGraphics();
    g.drawImage(base, 0, 0, null);
    g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_IN, 1.0f));
    for (Light l : images) {
        g.drawImage(l.LIGHT_IMAGE, l.x, l.y, null);
        l.LIGHT_IMAGE.flush();
    }
    g.dispose();
    output.flush();
    return output;
}

注意:这解决了问题,但会产生内存泄漏,我已经描述过希望在这里得到一些帮助:BufferedImage.createGraphics() memory leak

于 2012-11-23T12:11:02.590 回答
0

另一种方法是通过两次不同的方式混合您的图像。第一次通过,您只需在黑色矩形上添加多个辐射点,来自 White-Green-Transparency。

然后,在同一点,您从第 1 步中挖掘出您的第一张图像,并进行了 XOR 混合。

结果:

http://img11.imageshack.us/img11/7066/step3yr.png

编码:

public void creerLightMap(){
        lightMap = new BufferedImage(this.getWidth(), this.getHeight(), BufferedImage.TYPE_INT_ARGB);
        Graphics2D g = lightMap.createGraphics();
         g.setColor(Color.BLACK);
         g.fillRect(0, 0, this.getWidth(), this.getHeight());
         float radius = 100;
         //create color circle
         for(int i=0; i<lumiere.size(); i++){
            Point2D center = lumiere.get(i);
            float[] dist = {0.0f, 0.5f, 1.0f};
            Color[] colors = {new Color( 1.0f , 1.0f , 1.0f , 1.0f), new Color( 0.0f , 1.0f , 0.0f , 0.5f) , new Color( 0.0f , 1.0f , 0.0f , 0.0f)};
            RadialGradientPaint p = new RadialGradientPaint(center, radius, dist, colors);
            g.setPaint(p);
            g.fillRect(0, 0, this.getWidth(), this.getHeight());
        }

         //add an alpha into theses same circle
         for(int i=0; i<lumiere.size(); i++){
            Point2D center = lumiere.get(i);
            float[] dist = {0.0f, 1.0f};
            Color[] colors = {new Color( 1.0f , 1.0f , 1.0f , 1.0f) , new Color( 1.0f , 1.0f , 1.0f , 0.0f)};
            RadialGradientPaint p = new RadialGradientPaint(center, radius, dist, colors);
            g.setComposite(AlphaComposite.getInstance(AlphaComposite.XOR, 1.0f));
            g.setPaint(p);
            g.fillRect(0, 0, this.getWidth(), this.getHeight());
         }
         g.dispose();
    }

    @Override
    public void paintComponent(Graphics g) {
        super.paintComponent(g);

        Graphics2D g2d = (Graphics2D)g;
        g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                RenderingHints.VALUE_ANTIALIAS_ON);
        g2d.drawImage(this.lightMap, 0, 0, null);
    }
于 2013-03-27T17:38:41.933 回答