3

だから私はあなたがあなたのキャラクターの場所に爆弾を置くことができるゲームを作っています。各爆弾は、爆弾が表示されたときにGIF画像に関連付けられ、最終的にBOOMになります(ボンバーマンについて考えてみてください)。

問題は、画面に複数の爆弾をペイントしようとすると、GIFの最後のフレームからペイントされたということでした。調べてみると、gif cicleをリセットするメソッドimage.flush()が見つかりましたが、問題は、画面に2つ目の爆弾をペイントするたびに、画面上の以前のすべての爆弾のGIFサイクルがリセットされることです。

各爆弾のコンストラクターは次のとおりです。

public Tnt(int x, int y){
    this.x = x;
    this.y = y;
    ImageIcon ii = new ImageIcon("src/main/resources/modelObjects/tnt.gif");
    image = ii.getImage();
    image.flush();
}

私が作成するすべての爆弾はArrayList(listTnt)に入り、6秒後に削除されるため、すでにアクティブになっている爆弾のみをペイントします。

これが私の描画方法です。

public void draw(Graphics2D g2d, JPanel board){
    for(Tnt tnt: listTnt){          
        g2d.drawImage(tnt.getImage(), tnt.getX(), tnt.getY(), board);
    }
}

編集:Toolkit.getImageを使用して画像を再利用するため、問題はImageIconにあるようです。代わりに、Toolkit.createImageは再利用できないイメージを作成します。

完全に機能したTntの新しいコンストラクターは次のとおりです。

public Tnt(int x, int y){
    this.x = x;
    this.y = y;
    Toolkit t = Toolkit.getDefaultToolkit ();
    image = t.createImage("src/main/resources/modelObjects/tnt.gif");
}

今も必要ありませんimage.flush()。皆さん、ありがとうございました。

4

2 に答える 2

8

基礎となるImageものは、それぞれの間で再利用されていますImageIconOpenJDKのソースコードから判断すると、それぞれがToolkit.getImageを介して画像を要求するだけであるという事実が原因のようです。ただし、この方法には注意が必要です。これにより、当面の問題が説明されます。

基盤となるツールキットは、同じファイル名の複数のリクエストを同じ返された画像に解決しようとします。

代わりに、このImageIcon手順を完全にスキップして(そもそも、Swingクラスを不必要に使用することは不適切であるため)、代わりに、ドキュメントに記載されているToolkit.createImageを呼び出す必要があります。

返されるImageは新しいオブジェクトであり、このメソッドまたはそのgetImageバリアントの他の呼び出し元とは共有されません。

幸運を。

于 2012-07-31T17:46:15.433 に答える
2

これを解決する方法がわからなかったので、@ super_ソリューションを試しましたが、非常にうまく機能します。例が必要な人のためにコードを共有します。彼に+1

import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.net.MalformedURLException;
import java.net.URL;

import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;

public class TestAnimatedGif {

    private static final int IMAGE_COUNT = 9;

    protected void initUI() {
        JFrame frame = new JFrame(TestAnimatedGif.class.getSimpleName());
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        final JPanel panel = new JPanel();
        frame.add(panel);
        frame.setSize(600, 400);
        frame.setVisible(true);
        final Timer t = new Timer(1000, null);
        t.addActionListener(new ActionListener() {

            int count = 0;

            @Override
            public void actionPerformed(ActionEvent e) {
                if (count < IMAGE_COUNT) {
                    try {
                        JLabel image = new JLabel(new ImageIcon(Toolkit.getDefaultToolkit().createImage(
                                new URL("http://www.sitevip.net/gifs/bomba/BOMB-B_animado.gif"))));
                        panel.add(image);
                        count++;
                        panel.revalidate();
                        panel.repaint();
                        System.err.println("image added");
                    } catch (MalformedURLException e1) {
                        // TODO Auto-generated catch block
                        e1.printStackTrace();
                    }
                } else {
                    t.stop();
                }
            }
        });
        t.start();
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {

            @Override
            public void run() {
                new TestAnimatedGif().initUI();
            }
        });
    }

}
于 2012-07-31T20:46:24.030 に答える