有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

eclipse在Java中使用EventHandler使形状前后移动

我认为我的头衔很好地概括了我的问题。我对编程非常陌生(使用Head First Java进行了大约2-3周的自学),我正在尝试使用Action Listener在屏幕上来回移动一个方块,直到用户终止程序。我的问题是,我有一个计时器和两个类来实现Action Listener。我可以让它来回跑一次,但我只能让它这么做

package Animation;

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

import javax.swing.*;

public class Window extends JPanel implements ActionListener{
int x = 100;
Timer timer = new Timer(5, this);
int velX = 2;

public void paintComponent(Graphics  g){
    super.paintComponent(g);
    this.setBackground(Color.BLACK);
    g.setColor(Color.BLUE);
    g.fill3DRect(x, 150, 200, 200, true);
    timer.start();
    if(x >= 1000){
        timer.addActionListener(new HandlerClass());
            }//end if

    }//end paintComponent

public void actionPerformed(ActionEvent e){
    x += velX;
    repaint();
}//end actionP method

public class HandlerClass implements ActionListener{
    @Override
    public void actionPerformed(ActionEvent e) {
        if(x >= 100){
        x -= velX;
        repaint();
        }
    }//end actionP
}//end Handler

}//end Window

我见过一些问题,人们使用按钮来来回移动东西,或者移动东西一定次数,但我希望计时器能完成所有操作,直到用户退出。这样用户只需观看即可。我没有在main方法中包含这个类,因为它只是设置gui并调用这个类


共 (1) 个答案

  1. # 1 楼答案

    首先,看看Painting in AWT and SwingPerforming Custom Painting,了解有关Swing中绘画如何工作的更多细节

    基本上,Swing使用被动渲染算法,这意味着绘制周期可能在任何时候出于任何原因发生,大多数情况下无需直接干预

    永远不要在任何绘制方法中更改组件的状态,绘制方法应该绘制,仅此而已

    有一些小问题,首先,您将Window类和HandlerClass作为ActionListener添加到Timer中,这意味着您可能会陷入这样的境地:这两个侦听器在对象移动的方向上相互竞争。最好将动作逻辑放在一个方法中,例如:

    import java.awt.Color;
    import java.awt.Dimension;
    import java.awt.EventQueue;
    import java.awt.Graphics;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import javax.swing.JFrame;
    import javax.swing.JPanel;
    import javax.swing.Timer;
    import javax.swing.UIManager;
    import javax.swing.UnsupportedLookAndFeelException;
    
    public class Window extends JPanel {
    
        int x = 100;
        Timer timer = new Timer(5, new HandlerClass());
        int velX = 2;
    
        public Window() {
            this.setBackground(Color.BLACK);
            timer.start();
        }
    
        @Override
        public Dimension getPreferredSize() {
            return new Dimension(400, 400);
        }
    
        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
            g.setColor(Color.BLUE);
            g.fill3DRect(x, 150, 200, 200, true);
    
        }//end paintComponent
    
        public class HandlerClass implements ActionListener {
    
            @Override
            public void actionPerformed(ActionEvent e) {
                x += velX;
                if (x + 200 >= getWidth()) {
                    x = getWidth() - 200;
                    velX *= -1;
                } else if (x < 0) {
                    x = 0;
                    velX *= -1;
                }
                repaint();
            }//end actionP
        }//end Handler
    
        public static void main(String[] args) {
            EventQueue.invokeLater(new Runnable() {
                @Override
                public void run() {
                    try {
                        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                    } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                        ex.printStackTrace();
                    }
    
                    JFrame frame = new JFrame("Testing");
                    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                    frame.add(new Window());
                    frame.pack();
                    frame.setLocationRelativeTo(null);
                    frame.setVisible(true);
                }
            });
        }
    
    }//end Window