将JPanels动态添加到JScrollPane

时间:2013-04-03 10:43:24

标签: java swing jpanel jscrollpane layout-manager

我的GUI看起来如下: GUI 当我按下按钮addComponent时,会在scrollPane(1)中添加新的JPanel,添加JPanel但滚动窗格不滚动,会发生的情况是它添加新的JPanel并且jPanel的大小正在减小。

因此我的问题是面板被插入到JScrollPane中,并且这些面板的大小正在减少,但是没有滚动条。

这是我播种的代码:

    public class ContractForm extends JFrame {

    private JPanel contentPane;
    private JTextField txtContractID;
    private JScrollPane scrollPane; 
    private JButton btnAddComponent;
    private JButton btnOk;
    private JComboBox<Customer> comboBoxCustomer;
    private JButton btnCancel;
    private ArrayList<JPanel> rows;
    private JPanel panel;
    private Dimension size;


    /**
     * Create the frame.
     */
    public ContractForm() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setBounds(250, 250, 654, 476);
        contentPane = new JPanel();
        contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
        setContentPane(contentPane);
        contentPane.setLayout(null);

                rows = new ArrayList<JPanel>();

        JLabel lblContractid = new JLabel("ContractID");
        lblContractid.setBounds(50, 11, 78, 14);
        contentPane.add(lblContractid);

        txtContractID = new JTextField();
        txtContractID.setBounds(138, 8, 86, 20);
        contentPane.add(txtContractID);
        txtContractID.setColumns(10);

        JLabel lblNewLabel = new JLabel("Customer");
        lblNewLabel.setBounds(276, 11, 69, 14);
        contentPane.add(lblNewLabel);

        comboBoxCustomer = new JComboBox<Customer>();
        comboBoxCustomer.setBounds(355, 8, 235, 20);
        contentPane.add(comboBoxCustomer);

        JLabel lblYear = new JLabel("Year:");
        lblYear.setBounds(50, 37, 46, 14);
        contentPane.add(lblYear);

        JSpinner spinner = new JSpinner();
        spinner.setBounds(138, 31, 86, 20);
        contentPane.add(spinner);

        scrollPane = new JScrollPane(JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED, JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
        scrollPane.setBounds(0, 59, 628, 312);
        contentPane.add(scrollPane);

        panel = new JPanel();
        panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
        size = panel.getSize();
        scrollPane.setViewportView(panel);


        btnAddComponent = new JButton("addComponent");
        btnAddComponent.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent arg0) {
                ArrayList<JobDescription> jobs = Database.getInstance().getJobDescription();
                JobDescriptionContractRow row = new JobDescriptionContractRow(jobs);
                rows.add(row);
                panel.add(row);
                scrollPane.repaint();
                scrollPane.revalidate();

            }
        });
        btnAddComponent.setBounds(355, 30, 114, 23);
        contentPane.add(btnAddComponent);

        btnOk = new JButton("Ok");
        btnOk.setBounds(185, 382, 89, 23);
        contentPane.add(btnOk);

        btnCancel = new JButton("Cancel");
        btnCancel.setBounds(298, 382, 89, 23);
        contentPane.add(btnCancel);




    }
}

public class JobDescriptionContractRow extends JPanel {
    private JTextField textField;
    private JButton btnRemove;

    /**
     * Create the panel.
     */
    public JobDescriptionContractRow(ArrayList<JobDescription> jobs) {
        setLayout(null);

        JLabel lblJobdescription = new JLabel("Job description");
        lblJobdescription.setBounds(10, 14, 94, 14);
        add(lblJobdescription);

        JComboBox<JobDescription> comboBox = new JComboBox<JobDescription>();
        comboBox.setBounds(102, 11, 149, 20);
        for(JobDescription job : jobs){
            comboBox.addItem(job);
        }
        comboBox.setSelectedItem(null);
        add(comboBox);

        textField = new JTextField();
        textField.setBounds(365, 11, 86, 20);
        add(textField);
        textField.setColumns(10);

        JLabel lblNewLabel = new JLabel("Contract price");
        lblNewLabel.setBounds(277, 14, 78, 14);
        add(lblNewLabel);

        JButton btnRemove = new JButton("remove");
        btnRemove.setBounds(469, 10, 89, 23);
        add(btnRemove);


    }
}

2 个答案:

答案 0 :(得分:3)

JPanel(您的JScrollPane视图组件)默认使用FlowLayout,它尊重组件的首选大小。您可以覆盖已添加的JPanels的{​​{3}}以正确调整其大小。如果不这样做,JScrollPane会计算出适合ViewPortView的所有尺寸。

旁注:避免使用绝对定位(null布局)并使用getPreferredSize

答案 1 :(得分:0)

您可以使用。

强制JScrollPane调整大小
JViewport v = new JViewport();
v.setSetViewSize(new Dimention(width,height));
scroll.setViewport(v);