【问题标题】:GUI shows elements only after dragging windowGUI 仅在拖动窗口后显示元素
【发布时间】:2011-10-23 03:56:58
【问题描述】:
        frame_ref = new Frame("Login");
        mainPanel_ref = new Panel();
        buttonPanel_ref = new Panel();
        grid_ref = new GridLayout(4,2);
        frame_ref.setSize(300,120);
        frame_ref.setVisible(true);

        email_ref = new TextField();
        password_ref = new JPasswordField();

        mainPanel_ref.setLayout(grid_ref);
        mainPanel_ref.add(new Label("E-Mail"));
        mainPanel_ref.add(email_ref);
        mainPanel_ref.add(new Label("Passwort"));
        mainPanel_ref.add(password_ref);

        mainPanel_ref.add(submitLogin_ref);
        mainPanel_ref.add(fehlerMeldung_ref);

        frame_ref.add(mainPanel_ref);

我像上面一样在 Java 中设置了一个视图。窗口完全是空的,但是在我拖放它的大小之后,所有元素都出现了。有人知道如何解决这个问题吗?

【问题讨论】:

    标签: java swing user-interface layout


    【解决方案1】:

    添加组件后,请在JFrame 上调用pack()。这样做会导致框架采用显示组件所需的最小尺寸。最后致电 (setLocation()(4) &) setVisible(true)

    import java.awt.GridLayout;
    import javax.swing.*;
    import javax.swing.border.EmptyBorder;
    
    class FrameTest {
    
        public void init() {
            frame_ref = new JFrame("Login");
            frame_ref.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            mainPanel_ref = new JPanel(new GridLayout(4,2,6,3));
            mainPanel_ref.setBorder(new EmptyBorder(5,5,5,5));
    
            email_ref = new JTextField();
            password_ref = new JPasswordField();
            mainPanel_ref.add(new JLabel("E-Mail"));
            mainPanel_ref.add(email_ref);
            mainPanel_ref.add(new JLabel("Passwort"));
            mainPanel_ref.add(password_ref);
    
            mainPanel_ref.add(new JLabel(""));
            mainPanel_ref.add(new JLabel(""));
            mainPanel_ref.add(submitLogin_ref);
            mainPanel_ref.add(fehlerMeldung_ref);
    
            frame_ref.add(mainPanel_ref);
    
            //frame_ref.setSize(300,120);
            frame_ref.pack();
            frame_ref.setVisible(true);
        }
    
        public static void main(String[] args) {
            SwingUtilities.invokeLater(new Runnable() {
                public void run() {
                    new FrameTest().init();
                }
            });
        }
    
        private JFrame frame_ref;
        private JPanel mainPanel_ref;
        private JTextField email_ref;
        private JPasswordField password_ref;
        private JButton submitLogin_ref = new JButton("Submit Login");
        private JButton fehlerMeldung_ref = new JButton("Fehler Meldung");
    }
    

    其他提示:

    1. 不要将 Swing 与 AWT 混合使用。至少,不是组件,或者在面向 Java 7+ 之前不是。
    2. 登录组件通常更适合放入JDialogJOptionPane 而不是JFrame
    3. 这可能更适合嵌套布局或GridLayout 以外的其他布局
    4. setLocation() 可能被换成:
      • 如果登录有“父”组件,setLocationRelativeTo(Component)
      • 如果登录是显示的第一个屏幕,setLocationByPlatform(true) (1.6+)。
    5. 仔细检查来源以获取其他提示。
    6. 如需尽快获得更好的帮助,请发帖 SSCCE

    【讨论】:

    • @mKorbel 起初我想说“在这个千年不要使用 AWT 组件进行编码”。只有在制作 SSCCE 时,我才注意到JPasswordField! ;)
    【解决方案2】:

    frame_ref.add(mainPanel_ref); 之后调用frame_ref.setVisible(true);

    这里发生的是:您通过调用frame_ref.setVisible(true); 显示框架,然后在其中添加元素。所以你得到一个空框架。之后,当您拖动或调整大小时,它会重新绘制并且您可以看到元素。

    【讨论】:

    • 或者在添加mainPanel_ref后调用revalidate()和repaint()
    • @StanislavL:这不是正确的解决方案。你应该在完全添加东西之后而不是在它之前显示你的框架,然后添加东西然后调用 repaint()。
    • pack()validate() 应在 GUI 创建期间调用。 (此答案可能有效,但不是整个答案。)
    猜你喜欢
    • 1970-01-01
    • 2017-03-28
    • 1970-01-01
    • 2016-07-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-01-08
    相关资源
    最近更新 更多