使用 GridBagLayout 调整 JPanel 和 JTable 的 JFrame 大小问题

问题描述 投票:0回答:1

我正在测试在同一框架中组合 JPanel(控件)和 JTable(数据)的过程,并且在尝试调整包含它们的 JFrame 的大小时遇到了问题。

我遇到的第一个问题是

frame.setMinimumSize(new Dimension (frame.getSize()))
在Windows 10下不起作用。它允许用户将框架大小调整为该尺寸的一半。 (取消注释该行代码以查看行为)。然后我尝试实现我自己的,并且
checkSize();
方法可以设置正确的最小尺寸。但是,我无法选择“调整大小结束”事件来发出
checkSize()
,并且最终得到的最小尺寸窗口不正确。我尝试过
ComponentListener
HierarchyBoundsListener
MouseListener
,但都不起作用。释放鼠标似乎总是会覆盖最后的尺寸
checkSize()
设置。有没有办法克服这个问题?

我不是最有经验的 Java Swing 程序员,我遇到的第二个问题是尝试在增加框架大小时调整 JTable 和 JPanel 的大小。当我用鼠标增加框架大小时,JTable 和 JPanel 在框架中心保持相同的大小。我希望控件 JPanel 保持锚定在左上角并仅水平增长或根本不增长,而 JTable 则水平和垂直增长并填充框架的其余部分。我如何实现这一目标?

下面的测试代码。

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ComponentEvent;
import java.awt.event.ComponentListener;
import java.awt.event.HierarchyBoundsListener;
import java.awt.event.HierarchyEvent;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.SwingUtilities;


public class Table extends JPanel
{
    private JTextField DCFileName = new JTextField (10);
    public JTextField DChours = new JTextField (5);
    JFrame frame = new JFrame();
    Dimension d;

    public Table()
    {
        super(new GridBagLayout());

        //setLayout(new BorderLayout());
        //headers for the table
        String[] columns = new String[] {
                "Id", "Name", "Hourly Rate", "Part Time"
        };

        //actual data for the table in a 2d array
        Object[][] data = new Object[30][5];
        for ( int i=0;i<30;i++) {
            data[i][0] = i;
            data[i][1] = "user"+i;
            data[i][2] = String.format("%.3f", Math.random() * 10.0);
            data[i][3] = Math.random() >0.5?true:false;
        }
        //create table with data
        JTable table = new JTable(data, columns);

        //add the table to the frame
        GridBagConstraints gbc = new GridBagConstraints();
        gbc.gridx = 0;
        gbc.gridy = 0;
        gbc.anchor = GridBagConstraints.WEST;
        //Add the control row
        add(setupControl(), gbc);
        //add(setupControl());
        gbc.gridy = 1;
        gbc.weighty = 1;
        //Add the table below
        add(new JScrollPane(table), gbc);
        frame.setTitle("Table Example");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);       
        frame.add(this);
        frame.addComponentListener(new FrameListen());
        // frame.addMouseListener(new MouseListen());
        frame.pack();
        // frame.setMinimumSize(new Dimension (frame.getSize()));
        d = frame.getSize();
        /*frame.getContentPane().addHierarchyBoundsListener(new HierarchyBoundsListener(){

            @Override
            public void ancestorMoved(HierarchyEvent e) {
                checkSize();
            }

            @Override
            public void ancestorResized(HierarchyEvent e) {
            }
        }); */
        System.out.println("Size " + d.getWidth() + " " + d.getHeight());
        frame.setVisible(true);
    }

    private JPanel setupControl() {
        JPanel control = new JPanel(new GridBagLayout());
        GridBagConstraints gbc = new GridBagConstraints();
        gbc.gridx = 0;
        gbc.gridy = 0;
        gbc.weightx = 0;
        gbc.fill = GridBagConstraints.HORIZONTAL;
        control.add(MakeTextField (" Rows of Data to Send", JTextField.LEFT) ,gbc);
        gbc.gridy = 1;
        control.add(DChours, gbc);
        DChours.setEditable(true);
        DChours.setText("10");
        gbc.gridy = 0;
        gbc.gridx = 1;
        control.add(MakeTextField (" Data input file", JTextField.LEFT) ,gbc);
        gbc.gridy = 1;
        DCFileName.setEditable(false);
        control.add(DCFileName, gbc);
        DCFileName.setText("Input file");
        return control;

    }

    private JTextField MakeTextField(String label, int alignment) {
        return MakeTextField ( label, label.length(), alignment );
    }

    private JTextField MakeTextField(String label, int length, int alignment) {
        length = (int) (length * 0.8);
        JTextField tf = new JTextField(length);
        tf.setText(label);
        tf.setEditable(false);
        tf.setHorizontalAlignment(alignment);
        tf.setBorder(javax.swing.BorderFactory.createEmptyBorder());
        return tf;
    } 

    private class MouseListen implements MouseListener{

        @Override
        public void mouseClicked(MouseEvent e) {
            // TODO Auto-generated method stub
            System.out.println("Mouse clicked" );

        }
        @Override
        public void mousePressed(MouseEvent e) {
            System.out.println("Mouse pressed" );

        }
        @Override
        public void mouseReleased(MouseEvent e) {
            System.out.println("Mouse released" );
            checkSize();

        }
        @Override
        public void mouseEntered(MouseEvent e) {
            System.out.println("Mouse enter" );

        }
        @Override
        public void mouseExited(MouseEvent e) {
            System.out.println("Mouse exit" );

        }

    }

    private class FrameListen implements ComponentListener{

        @Override
        public void componentResized(ComponentEvent e) {
            checkSize();
        }
        @Override
        public void componentMoved(ComponentEvent e) {
            // TODO Auto-generated method stub

        }
        @Override
        public void componentShown(ComponentEvent e) {
            // TODO Auto-generated method stub

        }
        @Override
        public void componentHidden(ComponentEvent e) {
            // TODO Auto-generated method stub

        }
    }

    private void checkSize() {
        Dimension d2 = frame.getSize();
        boolean resize = false;
        if (d2.getWidth() < d.getWidth()) {
            d2.setSize(d.getWidth(), d2.getHeight());
            resize = true;
        }
        if (d2.getHeight() < d.getHeight()) {
            d2.setSize(d2.getWidth(), d.getHeight());
            resize = true;
        }
        if ( resize ) frame.setSize(d2);
        System.out.println("Size " + d2.getWidth() + " " + d2.getHeight() + " " + resize);
        return;

    }

    public static void main(String[] args)
    {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                new Table();
            }
        });
    }   
}


 
java swing jframe jtable gridbaglayout
1个回答
0
投票

您不应根据当前尺寸设置最小尺寸,而应根据固定尺寸进行设置,以确保框架的尺寸不会调整为小于您想要的尺寸。以下是调整方法

frame.setMinimumSize(new Dimension(800, 600));

© www.soinside.com 2019 - 2024. All rights reserved.