KeyListener完全不起作用,但是我的代码在我朋友的计算机上可以正常工作 [英] KeyListener doesn't work at all but my code worked fine on my friend's computer

查看:90
本文介绍了KeyListener完全不起作用,但是我的代码在我朋友的计算机上可以正常工作的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

KeyListener根本不起作用,就像它不在那儿一样,它显示带有桨的框架,但是当按下箭头键时它不会移动,但是我的代码在我的键盘上可以正常工作朋友的计算机,我删除并安装了JDK和eclipse的最新版本,并且没有任何更改,我什至用cmd对其进行了编译,但它不起作用
百分之一尝试它正常工作,然后下一次返回不工作 该代码是关于使用箭头键移动的桨的 Paddle类:

KeyListener doesn't work at all it's like it's not there, it shows the frame with the paddle but it doesn't move when arrowkey pressed , BUT my code worked properly on my friend's computer , i deleted and installed the last version of JDK and eclipse and nothing changed , i even compilated it with cmd and it doesn't work
edit : one in a 100 tries it works properly then the next time it returns to not working the code is about a paddle that moves with arrowkeys the Paddle class :

import java.awt.Color;
import java.awt.Graphics;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JPanel;

public class Paddle extends JPanel implements KeyListener{

    private int x=900,y=280 ;
    private int sx=20,sy=20 ;
    private int valY=0;

    public Paddle() {
        setFocusable(true);
        requestFocus();
        addKeyListener(this);
    }

    public void paintComponent(Graphics g) {
        draw(g);
        update();
        repaint();
    }

    public void draw(Graphics g) {
        g.setColor(Color.WHITE);
        g.fillRect(0, 0, 1000, 1000);
        g.setColor(Color.ORANGE);
        g.fillRect(x, y, sx, sy);
    }

    public void update() {
        this.y+=this.valY;
    }

    public void keyTyped(KeyEvent e) {
        System.out.println("typed");
    }

    public void keyPressed(KeyEvent e) {
        System.out.println("typed");
        int c=e.getKeyCode();
        if (c==KeyEvent.VK_UP){
            this.valY=-1;
        }
        if(c==KeyEvent.VK_DOWN){
            this.valY=1;
        }


    }

    public void keyReleased(KeyEvent e) {
        valY=0;
    }
}

推荐答案

您违反了自定义绘画的一些规则.它完全起作用的事实主要是运气.

You are violating some rules of custom painting. The fact that it worked at all was mostly luck.

首先,删除对repaint()的呼叫.这将导致再次调用paintComponent,这将调用repaint,这将调用paintComponent,这将调用repaint,等等.您正在创建一个非常快的无限循环,该循环将耗尽Swing的大部分资源.而是在更改图形所依赖的数据时调用repaint().

First, remove your call to repaint(). It is causing paintComponent to be called again, which calls repaint, which calls paintComponent, which calls repaint, etc. You are creating a very fast infinite loop which uses up most of Swing’s resources. Instead, call repaint() whenever you change the data on which your drawing relies.

第二,您不能解释绘画是出于多种原因的事实.您无法控制其中的大多数.当您移动窗口或调整窗口大小时,甚至当鼠标移到窗口上时,或由于其他多种原因,都可能会调用paintComponent.

Second, you are not accounting for the fact that painting occurs for many reasons. You don’t control most of them. paintComponent may be called when you move or resize the window, or even when the mouse moves over the window, or for a number of other reasons.

由于无法预测系统何时会请求您的类绘制其内容,因此您不得在paintComponent中更改对象的状态.您不得直接或间接从paintComponent调用update()方法.

Since it is impossible to predict when the system will request that your class paint its contents, you must not change the state of your object in paintComponent. You must not call your update() method from paintComponent, either directly or indirectly.

定期更新状态的正确方法是从

The correct way to regularly update your state is to call your updating method from a Timer. For instance:

// Update every 250 milliseconds, that is, 4 times per second.
Timer timer = new Timer(250, e -> update());
timer.start();

最后,每当您覆盖paintComponent时,代码的第一行都必须是对super.paintComponent(g);的调用.如果不这样做,最终将看到奇怪的绘画文物. 执行自定义绘画教程中对此进行了讨论.

Finally, whenever you override paintComponent, the first line of code needs to be a call to super.paintComponent(g);. If you don’t do that, you will eventually see strange painting artifacts. This is discussed in the Performing Custom Painting tutorial.

这篇关于KeyListener完全不起作用,但是我的代码在我朋友的计算机上可以正常工作的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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