所以这个程序的目标(以及最后的起点)是按箭头键,并且箭头方向的子弹从屏幕中间出来。我有四张我在油漆中创建的子弹图像,并使用这两个类:
这是创建和组织项目符号的类:
public class BulletAnimator extends JPanel implements ActionListener
{
int startX,startY;
boolean yAxis = false;
boolean xAxis = false;
Timer animator;
String direction;
public BulletAnimator(int sX, int sY, String d)
{
direction = d;
startX = sX;
startY = sY;
animator = new Timer (10, this);
animator.start();
}
//chooses the right picture for the right direction
public ImageIcon chooseBulletPicture ()
{
String path = "bullet";
if (direction.equals("left"))
path += "LEFT";
else if (direction.equals ("right"))
path += "RIGHT";
else if (direction.equals ("up"))
path += "UP";
else
path += "DOWN";
path += ".png";
ImageIcon b= new ImageIcon (path);
return b;
}
public void paintComponent (Graphics g)
{
super. paintComponent(g);
if (startX >= 500 || startY >= 500)
animator.stop();
if (direction.equals ("up"))
startY -=2;
else if (direction.equals ("down"))
startY +=2;
else if (direction.equals ("right"))
startX += 2;
else
startX -=2;
chooseBulletPicture().paintIcon (this, g, startX, startY);
}
public void actionPerformed(ActionEvent e)
{
repaint ();
}
}
这是类添加keyListeners并测试它:
import java.awt.event.*;
import java.awt.*;
import javax.swing.*;
public class Test extends JFrame implements KeyListener
{
JFrame f;
public Test ()
{
addKeyListener (this);
setFocusable (true);
f = new JFrame ();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setVisible(true);
f.setSize(500, 500);
}
public void keyPressed(KeyEvent e)
{
BulletAnimator s = new BulletAnimator (250, 250, "initialized---blank");
//creates bullet w/ correct direction
if (e.getKeyCode() == KeyEvent.VK_RIGHT )
{
s = new BulletAnimator (250, 250, "right");
}
else if (e.getKeyCode() == KeyEvent.VK_LEFT )
{
s = new BulletAnimator (250, 250, "left");
}
else if (e.getKeyCode() == KeyEvent.VK_UP )
{
s = new BulletAnimator (250, 250, "up");
}
else if (e.getKeyCode() == KeyEvent.VK_DOWN )
{
s = new BulletAnimator (250, 250, "down");
}
System.out.println ("keyPressed method read");//checks if keyPressed method was looked at
f.add (s);
repaint();
}
public void keyReleased (KeyEvent e)
{}
public void keyTyped (KeyEvent e)
{}
public static void main (String [] args)
{
Test t = new Test ();
}
}
正如你所看到的,我试图进行一项测试,说" keyPressed方法读取" ...当程序运行时它不会打印。实际上什么都没有发生它只是一个灰色的屏幕......真的很令人沮丧。如果你花时间看它,那么提前谢谢你,我非常感谢任何建议!
答案 0 :(得分:4)
同样,不要使用KeyListeners,使用键绑定,这将允许您在应用程序范围内监听键击,而不必担心焦点和更高的抽象级别(使用起来也更安全)。
例如:
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import javax.swing.*;
public class Test2 extends JPanel {
private static final int PREF_W = 400;
private static final int PREF_H = PREF_W;
private static final int TIMER_DELAY = 50;
private Timer leftKeyTimer = new Timer(TIMER_DELAY , new TimerListener());
public Test2() {
int condition = JComponent.WHEN_IN_FOCUSED_WINDOW;
InputMap inputMap = getInputMap(condition );
ActionMap actionMap = getActionMap();
String leftDownKey = "Left Down";
String leftUpKey = "Left Up";
KeyStroke leftDown = KeyStroke.getKeyStroke(KeyEvent.VK_LEFT , 0, false);
KeyStroke leftUp = KeyStroke.getKeyStroke(KeyEvent.VK_LEFT , 0, true);
inputMap.put(leftDown, leftDownKey);
inputMap.put(leftUp, leftUpKey);
actionMap.put(leftDownKey, new LeftKeyAction(false));
actionMap.put(leftUpKey, new LeftKeyAction(true));
leftKeyTimer.setActionCommand("Left Key");
}
@Override
public Dimension getPreferredSize() {
return new Dimension(PREF_W, PREF_H);
}
private class LeftKeyAction extends AbstractAction {
private boolean onKeyRelease;
public LeftKeyAction(boolean onKeyRelease) {
this.onKeyRelease = onKeyRelease;
}
@Override
public void actionPerformed(ActionEvent e) {
if (onKeyRelease) {
if (leftKeyTimer != null && leftKeyTimer.isRunning()) {
leftKeyTimer.stop();
}
} else {
if (leftKeyTimer != null && !leftKeyTimer.isRunning()) {
leftKeyTimer.start();
}
}
}
}
private class TimerListener implements ActionListener {
public void actionPerformed(ActionEvent actEvt) {
System.out.println(actEvt.getActionCommand());
}
}
private static void createAndShowGui() {
Test2 mainPanel = new Test2();
JFrame frame = new JFrame("Test2");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
答案 1 :(得分:2)
您正在扩展JFrame
类,以便new Test()
正在创建JFrame
的(扩展)实例,然后您将KeyListener添加到此实例。但是,您可见的框架是您在Test()
构造函数中通过
f = new JFrame ();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setVisible(true);
f.setSize(500, 500);
您没有将KeyListener
添加到此JFrame实例中。因此,KeyListener只会在Test
实例可见并且处于焦点时才会响应。
我建议这样做:
public class Test extends JFrame implements KeyListener {
JFrame f; // Remove this.
public Test () {
super();
addKeyListener (this);
setFocusable (true);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setVisible(true);
setSize(500, 500);
}
}
要绘制图标,您还需要修改BulletAnimator
代码:
public void actionPerformed( ActionEvent e ) {
repaint();
revalidate(); // new line
}
并在f.add(s)
方法中将add(s)
更改为keyPressed
,以将图标添加到测试框架。
免责声明:正如其他人所指出的那样,有更好的解决方案来处理按键。我上面的建议仅确定了上面发布的原始代码的问题。