使用Graphics2D绘制图像

我正在尝试使用java的Graphics2D在屏幕上绘制图像。 这是我正在使用的代码。 我希望看到一个图像在屏幕上稳定移动。 目前我可以看到图像,但除非我调整窗口大小,否则它不会移动,在这种情况下它会移动。 我勾画了下面的课程。

public class Tester extends JFrame { private static final long serialVersionUID = -3179467003801103750L; private Component myComponent; public static final int ONE_SECOND = 1000; public static final int FRAMES_PER_SECOND = 20; private Timer myTimer; public Tester (Component component, String title) { super(title); myComponent = component; } public void start () { myTimer = new Timer(ONE_SECOND / FRAMES_PER_SECOND, new ActionListener() { @Override public void actionPerformed (ActionEvent e) { repaint(); } }); myTimer.start(); } @Override public void paint (Graphics pen) { if (myComponent != null) { myComponent.paint(pen); } } } 

传递给Tester的Component对象是以下类:

 public class LevelBoard extends Canvas implements ISavable { private static final long serialVersionUID = -3528519211577278934L; @Override public void paint (Graphics pen) { for (Sprite s : mySprites) { s.paint((Graphics2D) pen); } } protected void add (Sprite sprite) { mySprites.add(sprite); } 

我确保这个类只有一个我添加的精灵。 精灵类大致如下:

 public class Sprite { private Image myImage; private int myX, myY; public Sprite () { URL path = getClass().getResource("/images/Bowser.png"); ImageIcon img = new ImageIcon(path); myImage = img.getImage(); } public void update () { myX += 5; myY += 5; } public void paint (Graphics2D pen) { update(); pen.drawImage(myImage, myX, myY,null); } 

但是,我看到屏幕上只有一个静止的bowser图像。 除非调整窗口大小,否则他不会移动。 我知道Sprite类中的paint(Graphics2D pen)方法是以特定的间隔调用的(因为Tester类中的Timer)。 但是,即使x和y位置每次增加5。 精灵不动。 为什么不? 我如何解决它? 我只是试图测试我的程序的其他function,所以我真的只需要启动并运行。 我真的不在乎如何。

你的代码充满了问题:

  1. 不要覆盖JFrame.paint() ,特别是如果不调用super 。 设置ContentPane并覆盖其paintComponent() 。 虽然看起来很方便,但通常设计不好而且不必要。
  2. 不要覆盖JComponent.paint() ,而是覆盖JComponent.paintComponent() (并调用super
  3. 使用JLabel显示图像。 它简单得多。
  4. 不要混合使用AWT(Canvas)和Swing(JFrame)。 坚持swing。

这是一个简单的例子,显示了Bowser围绕框架移动。 (当你减小框架尺寸并用框架边框击中图像时很有趣;-))

 import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.net.MalformedURLException; import java.net.URL; import java.util.Random; import javax.swing.ImageIcon; import javax.swing.JFrame; import javax.swing.JLabel; import javax.swing.SwingUtilities; import javax.swing.Timer; import javax.swing.UnsupportedLookAndFeelException; public class TestAnimation2 { private static final int NB_OF_IMAGES_PER_SECOND = 50; private static final int WIDTH = 800; private static final int HEIGHT = 600; private Random random = new Random(); private double dx; private double dy; private double x = WIDTH / 2; private double y = HEIGHT / 2; protected void initUI() throws MalformedURLException { final JFrame frame = new JFrame(TestAnimation2.class.getSimpleName()); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setLayout(null); final JLabel label = new JLabel(new ImageIcon(new URL("http://sofzh.miximages.com/java/404"))); label.setSize(label.getPreferredSize()); frame.setMinimumSize(label.getPreferredSize()); frame.add(label); frame.setSize(WIDTH, HEIGHT); dx = getNextSpeed(); dy = getNextSpeed(); Timer t = new Timer(1000 / NB_OF_IMAGES_PER_SECOND, new ActionListener() { @Override public void actionPerformed(ActionEvent e) { x += dx; y += dy; if (x + label.getWidth() > frame.getContentPane().getWidth()) { x = frame.getContentPane().getWidth() - label.getWidth(); dx = -getNextSpeed(); } else if (x < 0) { x = 0; dx = getNextSpeed(); } if (y + label.getHeight() > frame.getContentPane().getHeight()) { y = frame.getContentPane().getHeight() - label.getHeight(); dy = -getNextSpeed(); } else if (y < 0) { y = 0; dy = getNextSpeed(); } label.setLocation((int) x, (int) y); } }); frame.setVisible(true); t.start(); } private double getNextSpeed() { return 2 * Math.PI * (0.5 + random.nextDouble()); } public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, UnsupportedLookAndFeelException { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { try { new TestAnimation2().initUI(); } catch (MalformedURLException e) { // TODO Auto-generated catch block e.printStackTrace(); } } }); } }