简体   繁体   English

如果run()方法中的if语句为true,为什么我不能再使用keyPressed?

[英]Why can't i use keyPressed anymore once the if-statement is true in the run()-methode?

I'm trying to make a kind of brickbreaker game but once I press the start button ("starten" = true). 我正在尝试制作一种突破性游戏,但是一旦按下开始按钮(“ starten” = true)。 I can't use the keyPressed()-utility anymore but before i pressed the start button I could use the keyPressed()-utility. 我不能再使用keyPressed()-utility,但在按下开始按钮之前,我可以使用keyPressed()-utility。 Could somebody please tell me why I suddenly can't use the keyPressed()-utility anymore and give me a possible solution too? 有人可以告诉我为什么我突然不能再使用keyPressed()-utility并给我一个可能的解决方案了吗?

import java.util.*;
import java.awt.*;
import java.awt.event.*;

import javax.swing.*;

public class VGKernel extends JPanel implements KeyListener {

public Rectangle screen, ball, block; // The screen area and ball location/size.
public Rectangle bounds;  // The boundaries of the drawing area.
public JFrame frame; // A JFrame to put the graphics into.
public VGTimerTask vgTask; // The TimerTask that runs the game.
public boolean down, right, starten = false; // Direction of ball's travel.
public JButton start;

public VGKernel(){
    super();
    screen = new Rectangle(0, 0, 600, 400);
    ball   = new Rectangle(0, 0, 20, 20);
    block = new Rectangle(260, 350, 40, 10);
    bounds = new Rectangle(0, 0, 600, 400); // Give some starter values.
    frame = new JFrame("VGKernel");
    vgTask = new VGTimerTask();
    addKeyListener(this);
    setFocusable(true);
    start = new JButton("Start");
    start.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent e) {
            starten = true;
        }
    });
    add(start);
}

class VGTimerTask extends TimerTask{
    public void run(){
        repaint();

        if(starten){
        moveBall();
        frame.repaint();
        }
    }
  }

// Now the instance methods:
  public void paintComponent(Graphics g){
    // Get the drawing area bounds for game logic.
    bounds = g.getClipBounds();
    // Clear the drawing area, then draw the ball.
    g.clearRect(screen.x, screen.y, screen.width, screen.height);
    g.fillRect(ball.x, ball.y, ball.width, ball.height);
    g.fillRect(block.x, block.y, block.width, block.height);
  }

  public void moveBall(){
  // Ball should really be its own class with this as a method.
    if (right) ball.x+=1; // If right is true, move ball right,
    else ball.x-=1;       // otherwise move left.
    if (down)  ball.y+=1; // Same for up/down.
    else ball.y-=1;
    if (ball.x > (bounds.width - ball.width)) // Detect edges and bounce.
      { right = false; ball.x = bounds.width -  ball.width; }
    if (ball.y > (bounds.height - ball.height))
      { down  = false; ball.y = bounds.height - ball.height;}
    if (ball.x == 0) { right = true; ball.x = 0; }
    if (ball.y == 0) { down  = true; ball.y = 0; }
  }

  public void keyPressed(KeyEvent evt) {
      if(evt.getKeyCode() == KeyEvent.VK_G && block.x > 0) {
          block.x -= 20;
      }

      if(evt.getKeyCode() == KeyEvent.VK_H && block.x < 540) {
          block.x += 20;
      }
  }

  public void keyTyped(KeyEvent evt){  }
  public void keyReleased(KeyEvent evt){ }

  public void startActionPerformed(java.awt.event.ActionEvent evt) {
      starten = true;
  }

  public static void main(String arg[]){
    java.util.Timer vgTimer = new java.util.Timer();  // Create a Timer.
    VGKernel panel = new VGKernel(); // Create and instance of our kernel.

    // Set the intial ball movement direction.
    panel.down = true;
    panel.right = true;

    // Set up our JFRame
    panel.frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    panel.frame.setSize(panel.screen.width, panel.screen.height);
    panel.frame.setContentPane(panel); 
    panel.frame.setVisible(true);

    // Set up a timer to do the vgTask regularly.
    vgTimer.schedule(panel.vgTask, 0, 10);
  }

} }

You need to make sure whatever component you're listening for KeyEvents on has the focus. 您需要确保要监听KeyEvent的任何组件都具有焦点。

Once you click the button, that button has focus instead of your JPanel. 单击按钮后,该按钮将具有焦点而不是JPanel。 More info here: http://docs.oracle.com/javase/tutorial/uiswing/misc/focus.html 此处的更多信息: http : //docs.oracle.com/javase/tutorial/uiswing/misc/focus.html

You can use the requestFocusInWindow() method on your JPanel, or you can call setFocusable(false) on your JButton. 您可以在JPanel上使用requestFocusInWindow()方法,也可以在JButton上调用setFocusable(false)。

Or you could use key bindings instead: http://docs.oracle.com/javase/tutorial/uiswing/misc/keybinding.html 或者,您可以改用按键绑定: http : //docs.oracle.com/javase/tutorial/uiswing/misc/keybinding.html

Add VGKernel.this.grabFocus(); 添加VGKernel.this.grabFocus(); to the ActionListener to return focus to the VGKernel panel after clicking the button. 单击按钮后,将VGKernel返回到ActionListener以将焦点返回到VGKernel面板。

start.addActionListener(new ActionListener() {
    @Override
    public void actionPerformed(ActionEvent e) {
        starten = true;
        VGKernel.this.grabFocus();
    }
});

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM