因此,我正在开发一个游戏,在该游戏中,用户在网格中移动了演员,并且如果用户试图将演员移动到某种类型的空间,则可以将演员移动到该空间。网格由我知道的称为PGrid的类组成,因此网格由PGrid组成。问题是keyListener根本不起作用,甚至没有打印出“ hi”。下面是PGame和moveGrid的代码,其中PGame处理moveGrid内容,但moveGrid绘制网格(因为它是JPanel)。我尝试将keylistener从PGame移到moveGrid,但没有用。
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JFrame;
//where all the different classes are put together
public class PGame implements KeyListener{ //may want to move the listener to moveGrid
private static moveGrid panel = new moveGrid(8,8); //taking something from moveGrid
private static PActor pguy = new PActor("Bill", 2, 2);
private boolean shallmove = false;
private int newx, newy;
public static void main(String[] args){
//create a new frame
JFrame frame = new JFrame("PGame");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//moveGrid panel = new moveGrid(8,8); //taking something from moveGrid
frame.getContentPane().add(panel);
frame.pack();
frame.setVisible(true);
panel.requestFocus();
//creating a "path" of places able to move to
moveGrid.pgrids.get(0).changeType(1);
moveGrid.pgrids.get(1).changeType(1);
moveGrid.pgrids.get(2).changeType(1);
moveGrid.pgrids.get(3).changeType(1);
moveGrid.pgrids.get(10).changeType(1);
moveGrid.pgrids.get(11).changeType(1);
moveGrid.pgrids.get(19).changeType(1);
moveGrid.pgrids.get(27).changeType(1);
//moveGrid.pgrids.get(4).changeType(2);
//start our pguy out in a position
PGrid pguystart = new PGrid(2,0,0);
moveGrid.pgrids.set(0,pguystart);
panel.repaint();
}
public void keyPressed(KeyEvent e) {
//here test if the grid can be updated
//Test:
pguy.canMove(3,3);
pguy.Move(4,3,3);
if(e.getKeyCode() == KeyEvent.VK_UP){
newx = pguy.getx();
newy = pguy.gety() - 1;
shallmove = pguy.canMove(newx,newy);
System.out.println("Hi");
}else if(e.getKeyCode() == KeyEvent.VK_DOWN){
newx = pguy.getx();
newy = pguy.gety() + 1;
shallmove = pguy.canMove(newx,newy);
} else if(e.getKeyCode() == KeyEvent.VK_LEFT){
newx = pguy.getx() - 1;
newy = pguy.gety();
shallmove = pguy.canMove(newx,newy);
}else if(e.getKeyCode() == KeyEvent.VK_RIGHT){
newx = pguy.getx() + 1;
newy = pguy.gety();
shallmove = pguy.canMove(newx,newy);
}
}
public void keyReleased(KeyEvent e) {
System.out.println("Hi");
//update the grid if it can here
//somewhere in here add this:
//moveGrid.repaint(); //tell movegrid to repaint
if(shallmove = true){
//change a certain spot to the actor
PGrid temp = new PGrid(2,newx,newy);
moveGrid.pgrids.set(pguy.getplace(),temp);
//need to also change to old space to be back to what it was....
//*here*
pguy.Move(pguy.newPos,newx, newy);
panel.repaint();
}
}
public void keyTyped(KeyEvent e) { }
}
moveGrid:
//a grid in which stuff can move
import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
import javax.swing.*;
public class moveGrid extends JPanel {
private int height;
private int width;
private int newx, newy;
private static PActor pguy = new PActor("Bill", 2, 2);
private boolean shallmove = false;
public static ArrayList<PGrid> pgrids = new ArrayList<PGrid>(); //an array full of grid boxes with type PGrid
public moveGrid(int height, int width){
this.height = height;
this.width = width;
setPreferredSize(new Dimension(800, 800));
//make all the values in pgrids equal to "Water" and give them locations
int i = 0;
for(int y = 0; y < height; y++){
for(int x = 0; x < width; x++){
PGrid pnull = new PGrid(0, x, y);
pgrids.add(i, pnull);
i++;
}
}
//drawGrid();
}
/*public void drawGrid(Graphics g){
g.drawRect(x,y,20,20);
} */
public void addNotify() {
super.addNotify();
requestFocus();
}
public void paintComponent(Graphics g){
//PGrid curLoc = new PGrid(height, height, height);
//go through and draw out the grid
int q = 0;
int midx = 0; //need to make these somehow so the squares get drawn at the center
int midy = 0;
for(int qh = 0; qh < height; qh++){
for(int qw = 0; qw < width; qw++){
PGrid pcur = pgrids.get(q); //
int p = pcur.getType();
if(p == 0){
//may want to import a water looking image
g.setColor(Color.BLUE);
g.fillRect((40*qw)+midx,(40*qh)+midy,40,40);
g.setColor(Color.BLACK);
g.drawRect((40*qw)+midx,(40*qh)+midy,40,40);
}else if(p == 1){
//may want to import a better image
g.setColor(Color.GREEN);
g.fillRect((40*qw)+midx,(40*qh)+midy,40,40);
}else if(p == 2){
//draws the "character"
g.setColor(Color.ORANGE);
g.fillRect((40*qw)+midx,(40*qh)+midy,40,40);
}
q++;
}
}
//here draw the character in the proper position
//so like multiply the x and y by 40
}
}
我也可能在PActor类中出错,该类可能是移动的Actor。
public class PActor {
private String name;
private int curx, cury;
int newPos;
public PActor(String name, int curx, int cury){
this.name = name;
this.curx = curx;
this.cury = cury;
}
public boolean canMove(int x, int y){
boolean abletomove = false;
//test if the space that the user is trying to moveto can be moved to
//use indexOf(a temp variable with values x and y also with type 1) to test
PGrid togo = new PGrid(1,x,y);
//now scan through pgrids in moveGrid to see the desired spot can be moved to
for(int s = 0; s <= moveGrid.pgrids.size(); s++){
PGrid temp = moveGrid.pgrids.get(s);
//test if the temp space is equal
if((togo.getType() == temp.getType()) && (togo.getx() == temp.getx()) && (togo.gety() == temp.gety())){
abletomove = true;
newPos = s;
break; //stop scanning, as it is now unnecessary
}
else{ //do nothing
}
}
//now test pgrids to see if there is a spot like such that is moveable
return abletomove;
}
public int getplace(){
return newPos;
}
public int getx(){
return curx;
}
public int gety(){
return cury;
}
public void Move(int pos, int x, int y){
PGrid temp = new PGrid(2,x,y);
moveGrid.pgrids.set(pos,temp);
}
public String toString(){
return name + " ";
}
}
最佳答案
意见建议:
同样,要使任何Java Swing侦听器正常工作,必须将侦听器添加到组件中。例如,要使KeyListener正常工作,您首先需要通过在该组件上调用addKeyListener(myKeyListener)
将其添加到您希望收听的组件中。
为了使KeyListener正常工作,被监听的组件必须具有键盘焦点。这意味着,如果您正在收听JPanel,则首先必须通过在JPanel上调用setFocusable(true)
使其具有焦点,然后需要请求焦点,例如在其上调用requestFocusInWindow()
。
如果以后有东西抢走了焦点,例如已按下的JButton或文本组件,则KeyListener将不再起作用。
为了解决这个问题,我们通常建议您使用Key Bindings代替KeyListeners,但是请注意,这些设置与KeyListeners完全不同,并且您需要将所有假设抛在一边,并继续学习本教程。首先使用这些。
如果仍然卡住,那么您将要创建并发布一个minimal example program,这是一个小程序,其代码比已发布的程序少得多,但可以为我们编译,运行,并且直接向我们显示您的问题。
链接:
KeyListener Tutorial
Key Bindings tutorial