创建 JTable 以显示数据时遇到问题

trouble with creating JTable to display data

我正在为学校做这个工资单项目。 这个想法是让用户从 ComboBox 输入员工的姓名、工作时间、小时费率和 select 部门。 将显示 3 个按钮,"Add More"、"Display Result" 和 "exit"。 "Add More" 按钮会将输入存储到多个 arryalist 中,并将文本字段设置为空白以允许更多输入。 "Display Result"会在底部的JPanel生成一个JTable,显示员工姓名、部门、​​周薪。

我 运行 遇到了点击 "Display Result" 按钮后没有任何显示的问题。也许我误解了按钮事件的目的,但我现在真的很困惑。请帮忙!

这是UI的photobucket directURL PrtSc,希望对您有所帮助。

import java.awt.event.*;
import java.awt.*;
import javax.swing.*;
import java.util.*;

public class PayrollFrame extends JFrame
{
    private JLabel nameMessageLabel, hourMessageLabel, rateMessageLabel, boxMessageLabel;
    private JTextField nameTextField, hourTextField, rateTextField;
    private JPanel inputPanel, buttonPanel, outputPanel, inputPanel1, inputPanel2, inputPanel3, inputPanel4;
    private JComboBox<String> departmentBox;
    private JButton addButton, displayButton, exitButton;
    private JTable resultTable;
    private String[] columnNames = {"Employee name", "Department", "Weekly Salary"};
    private Object[][] data;
    private int WINDOW_WIDTH = 400;
    private int WINDOW_HEIGHT = 500;

    ArrayList<String> name = new ArrayList<String>();
    ArrayList<String> hour = new ArrayList<String>();
    ArrayList<String> rate = new ArrayList<String>();
    ArrayList<String> department = new ArrayList<String>();
    ArrayList<String> salary = new ArrayList<String>();

    private String[] departments = {"IT", "Marketing", "Human Resource", "Sales", "Customer Service", "Financial"};

    /*default constructor*/
    public PayrollFrame()
    {
        super("Payroll");
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setSize(WINDOW_WIDTH, WINDOW_HEIGHT);
        setLayout(new GridLayout(3,1));
        buildInputPanel();
        buildButtonPanel();
        buildOutputPanel();

        add(inputPanel);
        add(buttonPanel);
        add(outputPanel);

        setVisible(true);
    }

    private void buildInputPanel()
    {
        nameMessageLabel = new JLabel("Employee Name: ");
        hourMessageLabel = new JLabel("Work Hour: ");
        rateMessageLabel = new JLabel("Hourly Rate: ");
        boxMessageLabel = new JLabel("Department: ");
        nameTextField = new JTextField(10);
        hourTextField = new JTextField(10);
        rateTextField = new JTextField(10);
        departmentBox = new JComboBox<String>(departments);

        inputPanel = new JPanel();
        inputPanel1 = new JPanel();
        inputPanel2 = new JPanel();
        inputPanel3 = new JPanel();
        inputPanel4 = new JPanel();

        inputPanel1.add(nameMessageLabel);
        inputPanel1.add(nameTextField);
        inputPanel2.add(hourMessageLabel);
        inputPanel2.add(hourTextField);
        inputPanel3.add(rateMessageLabel);
        inputPanel3.add(rateTextField);
        inputPanel4.add(boxMessageLabel);
        inputPanel4.add(departmentBox);

        inputPanel.add(inputPanel1);
        inputPanel.add(inputPanel2);
        inputPanel.add(inputPanel3);
        inputPanel.add(inputPanel4);
    }

    private void buildButtonPanel() 
    {
        addButton = new JButton("Add More");
        addButton.addActionListener(new ButtonAction());
        displayButton = new JButton("Display Result");
        displayButton.addActionListener(new ButtonAction());
        exitButton = new JButton("Exit");
        exitButton.addActionListener(new ButtonAction());

        buttonPanel = new JPanel();

        buttonPanel.add(addButton);
        buttonPanel.add(displayButton);
        buttonPanel.add(exitButton);
    }

    private void buildOutputPanel()
    {
        outputPanel = new JPanel();
    }

    /*Copy ArrayList into 2D array to display in JTable format*/
    private void printData() 
    {
        for(int i=0; i<name.size(); i++)
        {
            data[i][0]=name.get(i);
            data[i][2]=department.get(i);
            data[i][2]=salary.get(i);
        }
        resultTable = new JTable(data, columnNames);
        outputPanel = new JPanel();
        outputPanel.add(resultTable);
    }

    /*Function of 3 buttons*/
    private class ButtonAction implements ActionListener
    {
        @Override
        public void actionPerformed(ActionEvent e) 
        {
            if(e.getActionCommand()=="Add More")
            {
                name.add(nameTextField.getText());
                hour.add(hourTextField.getText());
                rate.add(rateTextField.getText());
                department.add((String) departmentBox.getSelectedItem());
                calculateSalary(hourTextField.getText(), rateTextField.getText());
                nameTextField.setText("");
                hourTextField.setText("");
                rateTextField.setText("");
            }
            else if(e.getActionCommand()=="Display Result")
            {

                printData();

            }
            else if(e.getActionCommand()=="Exit")
            {
                System.exit(0);
            }
        }

        /*Calculate the weekly salary*/
        private void calculateSalary(String hourString, String rateString) 
        {
            int tempHour = Integer.parseInt(hourString);
            double tempRate = Double.parseDouble(rateString);
            if(tempHour<=40)
            {
                salary.add(Double.toString(tempHour * tempRate));
            }
            else
            {
                salary.add(Double.toString(40 * tempRate + (tempHour - 40) * (tempRate * 1.5))); //all hour after 40 will pay 1.5
            }
        }
    }
}

让我们从……开始吧

if (e.getActionCommand() == "Add More") {

不是你在 Java 中比较 String 的方式,你需要使用 equals 方法来代替,比如...

if ("Add More".equals(e.getActionCommand())) {

例如

接下来你做...

add(inputPanel);
add(buttonPanel);
add(outputPanel);

其中,当使用BorderLayout时,将每个组件添加到BorderLayout内的默认位置,需要为每个组件提供位置约束,否则奇怪的事情开始发生,例如...

add(inputPanel, BorderLayout.NORTH);
add(buttonPanel, BorderLayout.CENTER);
add(outputPanel, BorderLayout.SOUTH);

我刚刚发现你用的是 GridLayout,就我个人而言,我认为 BorderLayout 你会得到更好的结果,但那是我

然后您创建了 resultTableoutputPanel 的新实例,但您从未将 outputPanel 添加到任何内容...

/*Copy ArrayList into 2D array to display in JTable format*/
private void printData() 
{
    for(int i=0; i<name.size(); i++)
    {
        data[i][0]=name.get(i);
        data[i][1]=department.get(i);
        data[i][2]=salary.get(i);
    }
    resultTable = new JTable(data, columnNames);
    outputPanel = new JPanel();
    outputPanel.add(resultTable);
}

更好的办法是创建 resultTable,将其包裹在 JScrollPane 中并将其添加到您的屏幕。

当你想要"print"数据时,创建一个新的TableModel并将其应用到JTable

例如...

private void buildOutputPanel() {
    outputPanel = new JPanel(new BorderLayout());
    resultTable = new JTable();
    outputPanel.add(new JScrollPane(resultTable));
}

/*Copy ArrayList into 2D array to display in JTable format*/
private void printData() {
    for (int i = 0; i < name.size(); i++) {
        data[i][0] = name.get(i);
        data[i][2] = department.get(i);
        data[i][2] = salary.get(i);
    }
    DefaultTableModel model = new DefaultTableModel(data, columnNames);
    resultTable.setModel(model);
}

查看 How to Use Tables and How to Use Scroll Panes 了解更多详情

例子

import java.awt.BorderLayout;
import java.awt.EventQueue;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableModel;

public class PayrollFrame extends JFrame {

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                PayrollFrame frame = new PayrollFrame();
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    private JLabel nameMessageLabel, hourMessageLabel, rateMessageLabel, boxMessageLabel;
    private JTextField nameTextField, hourTextField, rateTextField;
    private JPanel inputPanel, buttonPanel, outputPanel, inputPanel1, inputPanel2, inputPanel3, inputPanel4;
    private JComboBox<String> departmentBox;
    private JButton addButton, displayButton, exitButton;
    private JTable resultTable;
    private String[] columnNames = {"Employee name", "Department", "Weekly Salary"};
    private Object[][] data;
    private int WINDOW_WIDTH = 400;
    private int WINDOW_HEIGHT = 500;

    ArrayList<String> name = new ArrayList<String>();
    ArrayList<String> hour = new ArrayList<String>();
    ArrayList<String> rate = new ArrayList<String>();
    ArrayList<String> department = new ArrayList<String>();
    ArrayList<String> salary = new ArrayList<String>();

    private String[] departments = {"IT", "Marketing", "Human Resource", "Sales", "Customer Service", "Financial"};

    /*default constructor*/
    public PayrollFrame() {
        super("Payroll");
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setLayout(new BorderLayout());
        buildInputPanel();
        buildButtonPanel();
        buildOutputPanel();

        add(inputPanel, BorderLayout.NORTH);
        add(buttonPanel);
        add(outputPanel, BorderLayout.SOUTH);

        setVisible(true);
    }

    private void buildInputPanel() {
        nameMessageLabel = new JLabel("Employee Name: ");
        hourMessageLabel = new JLabel("Work Hour: ");
        rateMessageLabel = new JLabel("Hourly Rate: ");
        boxMessageLabel = new JLabel("Department: ");
        nameTextField = new JTextField(10);
        hourTextField = new JTextField(10);
        rateTextField = new JTextField(10);
        departmentBox = new JComboBox<String>(departments);

        inputPanel = new JPanel();
        inputPanel1 = new JPanel();
        inputPanel2 = new JPanel();
        inputPanel3 = new JPanel();
        inputPanel4 = new JPanel();

        inputPanel1.add(nameMessageLabel);
        inputPanel1.add(nameTextField);
        inputPanel2.add(hourMessageLabel);
        inputPanel2.add(hourTextField);
        inputPanel3.add(rateMessageLabel);
        inputPanel3.add(rateTextField);
        inputPanel4.add(boxMessageLabel);
        inputPanel4.add(departmentBox);

        inputPanel.add(inputPanel1);
        inputPanel.add(inputPanel2);
        inputPanel.add(inputPanel3);
        inputPanel.add(inputPanel4);
    }

    private void buildButtonPanel() {
        addButton = new JButton("Add More");
        addButton.addActionListener(new ButtonAction());
        displayButton = new JButton("Display Result");
        displayButton.addActionListener(new ButtonAction());
        exitButton = new JButton("Exit");
        exitButton.addActionListener(new ButtonAction());

        buttonPanel = new JPanel();

        buttonPanel.add(addButton);
        buttonPanel.add(displayButton);
        buttonPanel.add(exitButton);
    }

    private void buildOutputPanel() {
        outputPanel = new JPanel(new BorderLayout());
        resultTable = new JTable();
        outputPanel.add(new JScrollPane(resultTable));      
    }

    /*Copy ArrayList into 2D array to display in JTable format*/
    private void printData() {
        for (int i = 0; i < name.size(); i++) {
            data[i][0] = name.get(i);
            data[i][2] = department.get(i);
            data[i][2] = salary.get(i);
        }
        TableModel model = new DefaultTableModel(data, columnNames);
        resultTable.setModel(model);
    }

    /*Function of 3 buttons*/
    private class ButtonAction implements ActionListener {

        @Override
        public void actionPerformed(ActionEvent e) {
            if ("Add More".equals(e.getActionCommand())) {
                name.add(nameTextField.getText());
                hour.add(hourTextField.getText());
                rate.add(rateTextField.getText());
                department.add((String) departmentBox.getSelectedItem());
                calculateSalary(hourTextField.getText(), rateTextField.getText());
                nameTextField.setText("");
                hourTextField.setText("");
                rateTextField.setText("");
            } else if ("Display Result".equals(e.getActionCommand())) {

                printData();

            } else if ("Exit".equals(e.getActionCommand())) {
                System.exit(0);
            }
        }

        /*Calculate the weekly salary*/
        private void calculateSalary(String hourString, String rateString) {
            int tempHour = Integer.parseInt(hourString);
            double tempRate = Double.parseDouble(rateString);
            if (tempHour <= 40) {
                salary.add(Double.toString(tempHour * tempRate));
            } else {
                salary.add(Double.toString(40 * tempRate + (tempHour - 40) * (tempRate * 1.5))); //all hour after 40 will pay 1.5
            }
        }
    }
}

感谢@MadProgrammer 的帮助!他的回复帮助我解决了我遇到的许多问题,并且真的试图向我解释事情。在咨询了我的导师后,我通过编辑 printData 方法成功地编译并 运行 我的程序。

private void printData() 
    {
        DefaultTableModel model = new DefaultTableModel(columnNames,name.size());
        resultTable.setModel(model);  
        for(int i=0; i<name.size(); i++)
        {
            resultTable.setValueAt(name.get(i),i,0);
            resultTable.setValueAt(department.get(i),i,1);
            resultTable.setValueAt(salary.get(i),i,2);
        }
    }