2017-10-07 39 views
-1

(私はコーディングでnoobですので、悪いコードになります)基本的に私は少し前にスネークゲームを作っていました。私はバグ事件に問題があったのでそれに。基本的には、「rec」矩形が交差するときに、「食べ物」の矩形をクリアする必要がありました。仕事をする代わりに、それは1秒間白くなり、そこにとどまります。 HERESに小さなコード:相続人Graphics.clearRect()が正常に動作しない

if (food.intersects(rec)) { 
    g.clearRect(food.x, food.y, food.width, food.height); 
    System.out.println("intersect"); 
    repaint(); 
} 

プログラムのGIF:https://gyazo.com/570afb285a2806a80466b2e6d4d2440a

HERESにフルコード:

import java.awt.Color; 
import java.awt.Graphics; 
import java.awt.Rectangle; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 
import java.awt.event.KeyEvent; 
import java.awt.event.KeyListener; 
import java.util.Random; 
import javax.swing.JPanel; 
import javax.swing.Timer; 

public class SnakePanel extends JPanel implements ActionListener, KeyListener { 
    private int size = 10; 
    private int x = 0; 
    private int y = 0; 
    private boolean started; 
    private String dir; 
    int velX = 0, velY = 0; 
    Timer t = new Timer(5, this); 
    Random r = new Random(); 
    int xx = r.nextInt(560) + 1; 
    int yy = r.nextInt(540) + 1; 

    public SnakePanel() { 
     t.start(); 
     addKeyListener(this); 
     setFocusable(true); 
     setFocusTraversalKeysEnabled(false); 
    } 

    public void paint(Graphics g) { 
     super.paintComponent(g); 
     Rectangle rec = new Rectangle(x, y, size, 10); 
     Rectangle food = new Rectangle(xx, yy, 10, 10); 
     g.setColor(Color.black); 
     g.fillRect(0, 0, 600, 600); 
     g.setColor(Color.white); 
     g.fillRect(rec.x, rec.y, rec.width, rec.height); 
     g.setColor(Color.red); 
     g.fillRect(food.x, food.y, food.width, food.height); 
     if (food.intersects(rec)) { 
      g.clearRect(food.x, food.y, food.width, food.height); 
      System.out.println("TSM"); 
      repaint(); 
     } 
     food.setLocation(xx, yy); 
    } 

    public void actionPerformed(ActionEvent e) { 
     if (x < 0) { 
      x = 584; 
     } 
     if (x > 584) { 
      x = 0; 
     } 
     if (y < 0) { 
      y = 561; 
     } 
     if (y > 561) { 
      y = 0; 
     } 
     x += velX; 
     y += velY; 
     repaint(); 
    } 

    public void keyPressed(KeyEvent e) { 
     int code = e.getKeyCode(); 
     if (code == KeyEvent.VK_DOWN) { 
      velY = 1; 
      velX = 0; 
     } 
     if (code == KeyEvent.VK_UP) { 
      velY = -1; 
      velX = 0; 
     } 
     if (code == KeyEvent.VK_LEFT) { 
      velY = 0; 
      velX = -1; 
     } 
     if (code == KeyEvent.VK_RIGHT) { 
      velY = 0; 
      velX = 1; 
     } 
    } 

    @Override 
    public void keyReleased(KeyEvent e) { 
    } 

    @Override 
    public void keyTyped(KeyEvent e) { 
    } 
} 
+0

関連するすべてのコードは、リンク内ではなく、ご質問の対象となります。あなたの質問はあなただけでなく、このサイトの将来の訪問者にも役立つようにしてください。 –

+1

私はその問題を解決しました。今は、「うまくいかない」という意味を教えてください。あたかもコードを書いたり、その目的を理解していないかのように、私たちにあなたの問題を説明してください。 –

+0

注:ペイント方法の中から決して 'repaint()'を呼び出さないでください。アニメーションループを駆動する代わりにSwing Timerを使うべきです。 –

答えて

0

あなたの問題は、主であるあなたは、図面を使用してプログラムのロジックを混合していることコード。蛇の位置、蛇の動きなどのロジックは、描画コードとは別に実行する必要があります。また、プログラムの状態を変更する必要があるときには、次のゲームループが実行されてからローカル変数への変更が残らないため、ローカル変数ではなく、食品アイテムのArrayListなど、クラスのフィールドを変更する必要があります。

その他の問題

  • これは、スムーズなアニメーションになるとやる方が安全ですしますので、上書きpaintComponentないpaint、。
  • 塗装方法の中からrepaint()に電話しないでください。それは貧しい人のゲームループです。あなたがコントロールできないゲームループです。代わりにSwing Timerを使用してください(Googleのチュートリアル)。実際、使用していないと思われるタイマーがあります。
  • Swing GUIでは、通常、KeyListenersではなくキーバインディングを使用する方がよいでしょう。それ以外の場合は、アプリケーションのフォーカスが聴取先のコンポーネントを離れないようにkludgesを作成する必要があります。

    private List<Rectangle> food = new ArrayList<>(); 
    

    その後、あなたのスイングタイマーで、あなたはinteratorを使用したい、とそれぞれにヘビの頭の交差点をテスト:あなたはあなたの食べ物を表しArrayList<Rectangle>を持っている場合、どのような例えば

、食品のビット、および、それを削除します。

for (Iterator<Rectangle> iterator = food.iterator(); iterator.hasNext();) { 
    Rectangle rectangle = (Rectangle) iterator.next(); 
    if (snakeHead.intersects(rectangle)) { 
     iterator.remove(); 
    } 
} 

をし、その後、あなたは呼びたい

repaint(); 

並行処理違反を起こすことなくリストからアイテムを削除する安全な方法を提供するので、リストを経由するためにイテレータを使用しています。

+0

私は問題が検出ではなく、ちょうど長方形を移動する方法だと思う。あなたはちょうどそれに答えないと、私はちょうどばかです。 –

+0

@RadinHakimjavadi:はい、私はそれに間接的に答えました。再度、ローカル変数ではなく、***フィールド***の状態を変更する必要があります。あなたはこれをやっていない。メソッドが再コールされたときに元の状態にリセットされるローカル変数を変更するだけです。 –

+0

@RadinHakimjavadi:上記の編集をご覧ください。 –

関連する問題