【问题标题】:Java JFrame rectangleJava JFrame 矩形
【发布时间】:2014-01-24 06:21:02
【问题描述】:

所以,我一直在学习 Java,但我还是个新手,所以请耐心等待。我最近的目标是图形程序,这是一个键盘控制测试。由于某种原因,该程序不会显示矩形。通常paint() 会自行运行,但由于某种原因它不是。我查看了我制作的其他程序以及网络上的其他程序,但我仍然无法弄清楚。

import java.awt.*;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JFrame;

public class App extends JFrame{

    public static int keyVal = 0;
    public static void main(String[] args) {
        new App();   
        while(true){
            System.out.println(keyVal);
            Wait.ms(50);
        }
    }

    public App(){
        JFrame f = new JFrame();

        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setTitle("Pong");
        f.setSize(300,400);

        f.setLocationRelativeTo(null);

        f.addKeyListener(new KeyListener(){
            public void keyPressed(KeyEvent e){
                keyVal = e.getKeyCode();
            }

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

            public void keyTyped(KeyEvent e){}
        });

        f.setVisible(true);
    }

    public void paint(Graphics g){
        g.setColor(Color.orange);
        while(true){
            g.drawRect(20, 20, 100, 60);
        }
    }

}

【问题讨论】:

  • 第 1 步 - 永远不要在你的 paint 函数中添加 while(true) - 它永远不会完成,你的 UI 会被锁定。
  • 感谢您的提示!虽然遗憾的是它仍然不起作用。 ://
  • 抱歉,没有时间进一步研究这个问题 - 我浏览了一下,发现了一个明显的问题,并认为我至少可以提供一点帮助,即使我没有解决问题。
  • This tutorial 将引导您创建一个示例 Swing 应用程序 - 您应该能够吸取经验教训并将其应用到您的应用程序中。我注意到的其他一些差异 - 覆盖 paintComponent 而不是 paint,并且不要在 main 函数中使用 Wait。如果其他人想在代码示例之后设计您的应用并将其发布为答案,请成为我的客人...

标签: java swing jframe paint


【解决方案1】:
  1. 不要在像JFrame 这样的顶级容器上绘画,因为它们已经承载了绘画组件的负载并且没有双缓冲。
  2. 改为使用自定义JPanel 绘制并覆盖其paintComponent 方法并调用super.paintCompoent。然后将该面板添加到框架中。

    public class MyPanel extends JPanel {
        @Override 
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
        }
    
        @Override
        public Dimension getPreferredSize() {
            return new Dimension(300, 300);
        }
    }
    
  3. 还要注意在上面的代码中,我覆盖了getPreferredSize() 方法。这就是您在JPanel 上绘画时想要做的事情。原因是没有设置首选大小,因此您需要设置它。也应该使用它,这样您就不必设置容纳它的框架的大小。相反,只需调用frame.pack()JPanel 的首选大小就会得到尊重。

  4. 不要将KeyListener 与 Swing 应用程序一起使用。而是使用Key Bindings,您可能会遇到焦点问题,其中包括使用KeyListener。您可以查看示例 Here,了解如何使用简单的键绑定。
  5. 您还应该像这样从 Event Dispatch Thread 运行您的 Swing 应用程序

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable(){
            @Override
            public void run() {
                new MyApp();
            }
        });
    }
    
  6. 不要在 paintComponent 方法中使用 while。你会遇到问题。如果你想重复绘制一些东西,比如动画,你会想要使用javax.swing.Timer。您可以查看示例 here 或任何数量的 SO 帖子,您只需简单搜索一下如何使用 Swing Timer。

  7. 另外,您的 App 类已经是 JFrame 子类。无需在构造函数中创建另一个 JFrame。只需将组件添加到它,就像这样

    public App() {
        add(new MyPanel(), BorderLayout.CENTER);
        add(new JButton("Button"), BorderLayout.SOUTH);
    }
    

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-06-15
    • 1970-01-01
    • 2012-03-31
    • 1970-01-01
    • 2013-07-11
    相关资源
    最近更新 更多