Java GUI中:如何使用移动WASD键一球? [英] Java GUI : How to move a ball using WASD keys?

查看:1146
本文介绍了Java GUI中:如何使用移动WASD键一球?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想写一个程序中,用户可以通过pressing WASD键在窗口中移动球。然而,当用户presses的钥匙,没有任何反应。贝娄是$ C我的程序的$ CS,谁能告诉我什么是错的或我怎么能提高我的计划? (如果我删除的KeyListener,并把球可以移动super.x ++;在ball.move())

 进口java.awt.BorderLayout中;
进口java.awt.Color中;
进口java.awt.Graphics;
进口java.awt.Graphics2D中;
进口java.awt.RenderingHints中;
进口java.awt.event.KeyAdapter;
进口java.awt.event.KeyEvent中;
进口java.awt.event.KeyListener;
进口java.util.concurrent.ScheduledThreadPoolExecutor中;
进口java.util.concurrent.TimeUnit中;
进口javax.swing.JApplet中;
进口javax.swing.JComponent中;
导入的java.awt.geom *。
公共类MoveBall扩展JApplet的
{
    公众最终诠释宽度= 567;
    公众最终诠释身高= 567;
    公共静态PaintSurface帆布;
    公共无效的init()
    {
        帆布=新PaintSurface();
        this.setSize(宽度,高度);
        this.add(帆布,BorderLayout.CENTER);
        的ScheduledThreadPoolExecutor执行人=新的ScheduledThreadPoolExecutor(3);
        executor.scheduleAtFixedRate(新动作(),0L,10L,TimeUnit.MILLISECONDS);
    }
}
Action类实现Runnable
{
    公共无效的run()
    {
        MoveBall.canvas.repaint();
    }
}
类PaintSurface扩展JComponent的
{
    球球=新球(20);
    公共PaintSurface()
    {
        addKeyListener(新侦听器());
    }
    公共无效漆(图形G)
    {
        Graphics2D的G2 =(Graphics2D的)克;
        g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,RenderingHints.VALUE_ANTIALIAS_ON);
        ball.move();
        g2.setColor(Color.GREEN);
        g2.fill(球);
        g2.setColor(Color.BLACK);
        g2.drawString(W,A,S,D或箭头键移动,7,17);
    }
}
Ball类扩展Ellipse2D.Float
{
    公众诠释xspeed,yspeed;
    公共球(INT D)
    {
        超(370370,D,D);
    }
    公共无效移动()
    {
        如果(super.x> 567)
        super.x - = 567;
        如果(super.x℃,)
        super.x + = 567;
        如果(super.y> 567)
            super.y - = 567;
        如果(super.y℃,)
            super.y + = 567;
        super.x + = xspeed;
        super.y + = yspeed;
    }
}
监听器类实现的KeyListener
{
    公共无效键pressed(KeyEvent的EV)
    {
        如果(ev.getKey code()== KeyEvent.VK_W)
        {
            MoveBall.canvas.ball.xspeed = 0;
            MoveBall.canvas.ball.yspeed = -1;
        }
        如果(ev.getKey code()== KeyEvent.VK_A)
        {
            MoveBall.canvas.ball.xspeed = -1;
            MoveBall.canvas.ball.yspeed = 0;
        }
        如果(ev.getKey code()== KeyEvent.VK_S)
        {
            MoveBall.canvas.ball.xspeed = 0;
            MoveBall.canvas.ball.yspeed = 1;
        }
        如果(ev.getKey code()== KeyEvent.VK_D)
        {
            MoveBall.canvas.ball.xspeed = 1;
            MoveBall.canvas.ball.yspeed = 0;
        }    }
    公共无效的keyReleased(KeyEvent的为arg0){}
    公共无效的keyTyped(KeyEvent的为arg0){}
}


解决方案

  

然而,当用户preSS的钥匙,什么都不会发生。


不要使用的KeyListener。如果组件具有焦点的KeyListener才能正常运行,所以我会想你的组件没有焦点。

而是使用键绑定,那么键盘甚至会工作,如果该组件没有焦点。

请参阅运动使用键盘有关这两种方法的详细信息。除了工作code的两种方法。

还有:


  1. 自定义涂装应通过覆盖的paintComponent(...)进行,而不是油漆(...)。你应该在开始调用super.paintComponent方法(...)。虽然在这种情况下,因为要扩展JComponent的背景将不会被自动清除,所以不是你需要画球前添加一个fillRect(...)语句绘制你的组件的背景。

  2. 请不要使用的ScheduledThreadPoolExecutor动画。更新GUI组件的状态应在事件指派线程来完成。你应该使用Swing的定时器。

看看在 Swing指南。有关于风俗画节如何使用Swing定时器来让你开始。

I want to write a program in which the user can move the ball on the window by pressing WASD keys. Yet, when the user presses the keys, nothing happens. Bellow are the codes of my program, can anyone tell me what's wrong or how can I improve my program? ( The ball can move if I delete the KeyListener and put super.x ++; in ball.move() )

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.concurrent.ScheduledThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import javax.swing.JApplet;
import javax.swing.JComponent;
import java.awt.geom.*;
public class MoveBall extends JApplet
{
    public final int Width =  567;
    public final int Height = 567;
    public static PaintSurface canvas;
    public void init()
    {
        canvas = new PaintSurface();
        this.setSize(Width, Height);
        this.add(canvas, BorderLayout.CENTER);
        ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(3);
        executor.scheduleAtFixedRate(new Action(), 0L, 10L, TimeUnit.MILLISECONDS);
    }
}
class Action implements Runnable
{
    public void run() 
    {
        MoveBall.canvas.repaint();  
    }   
}
class PaintSurface extends JComponent
{   
    Ball ball = new Ball(20);
    public PaintSurface()
    {
        addKeyListener(new Listener());
    }
    public void paint(Graphics g)
    {
        Graphics2D g2 = (Graphics2D)g;
        g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        ball.move();
        g2.setColor(Color.GREEN);
        g2.fill(ball);
        g2.setColor(Color.BLACK);
        g2.drawString("W,A,S,D or arrow keys to move", 7, 17);
    }
}
class Ball extends Ellipse2D.Float
{
    public int xspeed, yspeed;
    public Ball(int d)
    {
        super(370,370, d,d);
    }
    public void move()
    {
        if(super.x >567)
        super.x -=567;
        if(super.x <0)
        super.x +=567;
        if(super.y >567)
            super.y -=567;
        if(super.y < 0)
            super.y +=567;
        super.x += xspeed ;
        super.y += yspeed ;
    }
}
class Listener implements KeyListener
{
    public void keyPressed(KeyEvent ev) 
    {
        if(ev.getKeyCode() == KeyEvent.VK_W)
        {   
            MoveBall.canvas.ball.xspeed = 0 ;
            MoveBall.canvas.ball.yspeed = -1 ; 
        }   
        if(ev.getKeyCode() == KeyEvent.VK_A)
        {   
            MoveBall.canvas.ball.xspeed = -1 ;
            MoveBall.canvas.ball.yspeed = 0 ; 
        }   
        if(ev.getKeyCode() == KeyEvent.VK_S)
        {   
            MoveBall.canvas.ball.xspeed = 0 ;
            MoveBall.canvas.ball.yspeed = 1 ; 
        }   
        if(ev.getKeyCode() == KeyEvent.VK_D)
        {   
            MoveBall.canvas.ball.xspeed = 1 ;
            MoveBall.canvas.ball.yspeed = 0 ; 
        }   

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

解决方案

Yet, when the user press the keys, nothing happens.

Don't use a KeyListener. A KeyListener only works if the component has focus, so I would guess your component doesn't have focus.

Instead use Key Bindings, then the keyboard will work even if the component doesn't have focus.

See Motion Using the Keyboard for more information about both approaches. As well as working code for both approaches.

Also:

  1. Custom painting should be done by overriding paintComponent(...), not paint(...). You should invoke super.paintComponent(...) at the start. Although in this case because you are extending JComponent the background will not be cleared automatically, so instead you need to add a fillRect(...) statement to paint the background of your component before painting the ball.
  2. Don't use a ScheduledThreadPoolExecutor for animation. Updates to the state of GUI components should be done on the Event Dispatch Thread. You should be using a Swing Timer.

Take a look at the Swing Tutorial. There are sections on Custom Painting and How to Use Swing Timers to get you started.

这篇关于Java GUI中:如何使用移动WASD键一球?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆