主类中的Swing Timer不会重绘JFrame类

时间:2015-10-21 01:44:42

标签: java swing repaint

我有一个主类,它包含一个Array对象列表,并有一个Swing计时器,它重新绘制一个单独的JFrame类。尽管调用了重绘方法,但屏幕仍未更新。

应该发生什么: 按任意键时,将更新两个对象的x位置。每半秒滴答一次的摇摆计时器调用重绘方法。然后在更新的位置重绘图像。

据我所知,图像的位置正在更新,就像我最小化并重新打开JFrame窗口一样,图像已经移动。

我已经尝试更改计时器运行的时间间隔,将swing计时器移动到JFrame类,然后放置repaint();在一个线程中。但是我仍然不知道为什么重绘();没有更新屏幕。

这是我的代码草图: JFrame类

public class testingGround extends JPanel {
    private Image image;
    private qwq getter = new qwq();
    protected Keyboard keyboard = new Keyboard(); //KeyListener, imported from Keyboard class
    private JFrame frame = new JFrame(); //JFrame variable

public void createGUI(){
    testingGround panel = new testingGround(); // Creating a new JPanel, for objects to be drawn on
    JFrame frame = new JFrame("Game"); //Creating a new JFrame called frame 
    frame.setSize(600, 600); //Setting the size of the JFrame frame to be 600x600
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);// Setting so the frame exits on close
    frame.setVisible(true);
    frame.add(panel);// Adding the JPanel panel to the JFrame frame, so it's visible 
    frame.addKeyListener(keyboard); //Adding a KeyListener to detect users input in the JFrame frame
}   
public Frame getFrame() { //Constructor class to get JFrame in other classes
    return frame;
}

public void initComponents(){
    ImageIcon imageIcon = new ImageIcon("C:/Users/destr/workspace/GameWIP3/bin/A2.png");
    image =imageIcon.getImage();
}

protected void paintComponent (Graphics g){//Drawing
    super.paintComponent(g);
    initComponents();
    for (int i=0;i<getter.getFListSize();i++)
    {
    System.out.print("paint called");   
    g.drawImage(image, getter.getFighter(i).getFighterX(), getter.getFighter(i).getFighterY(), null);
    }
}
}

键盘类

public class Keyboard implements KeyListener {

private qwq getter = new qwq();

@Override
public void keyPressed(KeyEvent e) {
    getter.getFighter(0).setFighterX(500);;
    getter.getFighter(1).setFighterX(200);; 
    System.out.print("Updated the x value of two");
}

主类

public class qwq implements ActionListener {
private static ArrayList<Fighter> FighterList = new ArrayList<Fighter>(); // ArrayList                                                                          // of                                                               // Fighters
Timer timer = new Timer(500, this);
private static testingGround GUI = new testingGround();

public qwq() {
    timer.start();
}

public Fighter getFighter(int i) {
    return FighterList.get(i); // To retrieve a fighter from the Array List
}

public void addFighter(Fighter i) {
    FighterList.add(i); // To add a fighter to the Array list
}

public int getFListSize() {
    return FighterList.size();
}

public static void main(String[] args) {
    GUI.createGUI();
    GUI.getFrame();
    FighterList.add(new Fighter(0, 0));
    FighterList.add(new Fighter(20, 50));
}

@Override
public void actionPerformed(ActionEvent e) {
    if (e.getSource() == timer) {
        GUI.repaint();
    }
}
}

对象类

public class Fighter { 

    private int fighterX;
    private int fighterY;

public Fighter ( int fighterX, int fighterY) {
this.setFighterX(fighterX);
this.setFighterY (fighterY);
}

public int getFighterX (){
return fighterX; //method to get x coordinate of a fighter
}

public int getFighterY (){
return fighterY;//method to get y coordinate of a fighter
}

public void setFighterX(int fighterX) {
this.fighterX = fighterX; //method to set the x coordinate of a fighter
}

public void setFighterY(int fighterY) {
this.fighterY = fighterY; //method to set the y coordinate of a fighter
}
}

1 个答案:

答案 0 :(得分:3)

  • 您正在qwqtestingGround创建Keyboard的多个实例,这些实例彼此无关,只表示您现在正在创建新的Timer每次你创建一个新的实例
  • testingGround#createGUI中,您创建了testingGround的新实例,该实例会添加到JFrame的新实例中,因此qwq的引用必须testingGround 1}}与实际在屏幕上的实例无关!?此外,您在JFrame中创建了createGUI的新实例,该实例与您从JFrame返回的getFrame实例没有任何关系!?
OO是关于责任的,它负责什么。例如,你testingGround类不应该制作框架,这不是它的责任。它应该负责呈现游戏的当前状态。

例如......

import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.Timer;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class Qwq {

    public static void main(String[] args) {
        new Qwq();
    }

    public Qwq() {
        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 TestingGround());
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class Keyboard extends KeyAdapter {

        private List<Fighter> fighterList;

        public Keyboard(List<Fighter> fighterList) {
            this.fighterList = fighterList;
        }

        @Override
        public void keyPressed(KeyEvent e) {
            fighterList.get(0).setFighterX(500);
            fighterList.get(1).setFighterX(200);
            System.out.print("Updated the x value of two");
        }
    }

    public class TestingGround extends JPanel {

        private ArrayList<Fighter> fighterList = new ArrayList<>(); 

        private Image image;
        private Keyboard keyboard;

        public TestingGround() {
            loadImages();
            addKeyListener(new Keyboard(Collections.unmodifiableList(fighterList)));
            Timer timer = new Timer(500, new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    repaint();
                }
            });
            timer.start();
        }

        public void loadImages() {
            ImageIcon imageIcon = new ImageIcon("C:/Users/destr/workspace/GameWIP3/bin/A2.png");
            image = imageIcon.getImage();
        }

        protected void paintComponent(Graphics g) {//Drawing
            super.paintComponent(g);
            for (Fighter fighter : fighterList) {
                System.out.print("testing");
                g.drawImage(image, fighter.getFighterX(), fighter.getFighterY(), null);
            }
        }
    }

    public static class Fighter {

        private int fighterX;
        private int fighterY;

        public Fighter(int fighterX, int fighterY) {
            this.setFighterX(fighterX);
            this.setFighterY(fighterY);
        }

        public int getFighterX() {
            return fighterX; //method to get x coordinate of a fighter
        }

        public int getFighterY() {
            return fighterY;//method to get y coordinate of a fighter
        }

        public void setFighterX(int fighterX) {
            this.fighterX = fighterX; //method to set the x coordinate of a fighter
        }

        public void setFighterY(int fighterY) {
            this.fighterY = fighterY; //method to set the y coordinate of a fighter
        }
    }
}

现在,将Timer分开很容易,但我很懒惰