2

JApplet で小さなゲームを作って Java を学んでいます。スプライトのアニメーションに少し問題がありました。

コードは次のとおりです。

this.sprite.setBounds(0,0,20,17);

this.sprite.setIcon(this.rangerDown);
for(int i = 0; i< 16;i++)
{
    this.sprite.setBounds(this.sprite.getX(), this.sprite.getY()+1, 20, 17);
    this.sprite.update(this.sprite.getGraphics());

    try{
        Thread.currentThread().sleep(100);
    }catch(InterruptedException e){
}

}

アニメーション中にちらつきが残りました。アニメーションが終了すると、ちらつきは消えますが、それはちょっと醜いです... 私が見逃したステップがあると思います. 今のところより良い結果が得られるため、この方法を使用しますが、可能であれば AWT を使用せずに、代わりに Swing を使用したいと考えています。

ちらつきを取り除く方法はありますか?

読んでくれてありがとう。

スクリーンショット(画像を投稿できません、申し訳ありません)。

4

2 に答える 2

2

問題はダブルバッファリングです。

アプレットの場合:ダブルバッファリングはほぼ自動的に行われます。メソッドでpaintの代わりにrepaint()を呼び出します。

Swingでは、それを行う方法はたくさんあります。私は通常、BufferStrategyルートに行きます。フレームを初期化するときは、次のようにします。

JFrame frame;
... code to init frame here
frame.createBufferStrategy(2);

次に、描画メソッドで:

Graphics g = getBufferStrategy().getDrawGraphics();
..code to do drawing here...
g.dispose();
getBufferStrategy().show();
于 2009-11-01T05:45:10.727 に答える
2

これは影ではありません。スプライトの境界線です。たまたま黒くて影のように見えるだけです。スプライトをシフトする量を変更すると (1 ピクセルだけでなく 50 ピクセルとしましょう)、私の言いたいことがわかります。

これを修正するには、スプライトの位置を更新するたびに背景も描画する必要があります。これはおそらくちらつきを生成しますが。

それを行う正しい方法は、オブジェクトの描画方法を変更することです。パネルの paintComponent メソッドをオーバーライドし、スプライトの位置を更新するたびに repaint を呼び出す必要があります。

編集:

基本的な使用方法については、このコード サンプルを参照してください。注: これは、スレッドを使用してアニメーションを記述する方法ではありません。paintComponent メソッドで何が行われるかを示すためにそれを書き、アニメーション スレッドを書いて、あなたが言及した「影」がなくなったことを示しました。スレッドに終了しない実行ループを持たないでください:)

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;

import javax.swing.JFrame;
import javax.swing.JPanel;


public class Test {

    public static void main(String[] args) {
        JFrame f = new JFrame("Test");
        MyPanel c = new MyPanel();
        f.getContentPane().add(c);
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setSize(350, 100);
        f.setVisible(true);
    }

}

class MyPanel extends JPanel {

    int x = 0;
    boolean toTheRight = true;

    public MyPanel() {
        new Thread(new Runnable() {

            @Override
            public void run() {
                while (true) {
                    x = (toTheRight)?x+5:x-5;
                    if (x>300)
                        toTheRight = false;
                    if (x<0)
                        toTheRight = true;
                    repaint();
                    try {
                        Thread.sleep(50);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        }).start();
    }

    @Override
    protected void paintComponent(Graphics g) {
        Graphics2D g2 = (Graphics2D)g.create();
        g2.setPaint(Color.white);
        g2.fillRect(0, 0, getWidth(), getHeight());
        g2.setPaint(Color.red);
        g2.fillOval(x-2, 50, 4, 4);
    }

}
于 2009-11-01T00:20:32.843 に答える