JTable构造函数的替代方案

时间:2014-08-13 15:41:05

标签: java swing jtable

在花了无数个小时与Swing合作并努力学习之后,我遇到了这个问题。在回答确切问题之前,我想简要介绍一下情况。如果您立即发现问题,请随意跳过此处。

我在过去的3天里一直在使用JTables (或至少尝试)。我对JTable构造函数有几个问题:

JTable(Object[][] rowData, Object[] columnNames)

在阅读并重新阅读oracle documentation之后,我偶然发现了一些关于JTable构造函数的点(使用它的缺点):

  • 它们会自动使每个单元格都可编辑。

  • 它们将所有数据类型视为相同(作为字符串)。例如,如果表列具有布尔数据,则表可以在复选框中显示数据。但是,如果使用前面列出的两个JTable构造函数中的任何一个,则布尔数据将显示为字符串。您可以在上图的素食列中看到这种差异。

  • 它们要求您将所有表格的数据放在数组或向量中,这可能不适合某些数据。例如,如果要从数据库中实例化一组对象,则可能需要直接查询对象的值,而不是将所有值复制到数组或向量中。

第一点和第三点都给我提问,所以我想问几个问题:

  1. 如何使单个列宽静止,此时,所有列宽均匀并在调整大小时均匀缩放。这是一个问题,因为列" ID"显然不需要像列那样多的空间"电子邮件"

  2. 由于我的String [] columnNames传递给构造函数但框架上没有显示任何内容,我也因为某些奇怪的原因而显示列名时出现问题。


  3. JTable代码:

    private JTable addStudentsJTable(){
        String[] columnNames = {
                "Teacher ID",
                "Student ID",
                "Name",
                "Surname",
                "E-mail",
                "Date of Birth",
                "Telephone",
                "Course",
                "OOP",
                "Year of Membership",
                "Consent"};
    
        Object[][] data = {
                {1, 1, "Random", "Student", "Student@email.com", "1/1/1970", 9999999, "MC", true, 2014, true},
                {2, 2, "Student", "Surname", "RandomStudent@email.com", "1/1/1970", 11111111, "AIO", true, 2000, true}
        };
        studentsJTable = new JTable(data, columnNames);
    
        studentsJTable.setPreferredScrollableViewportSize(new Dimension(850,200));
        studentsJTable.setFillsViewportHeight(true);
    
        JScrollPane scrollPane = new JScrollPane(studentsJTable);
        add(scrollPane);
        return studentsJTable;
    }
    

    整个JFrame类:

    import javax.swing.*;
    import javax.swing.border.EmptyBorder;
    import javax.swing.table.TableModel;
    import java.awt.*;
    
    public class JDatabaseMainFrame extends JFrame {
        private JTable studentsJTable;
        private JPanel contentPane;
    
    public JDatabaseMainFrame(){
        JFrame frame = new JFrame("JDatabase");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    
        setTitle("JDatabase");
        setResizable(true);
        setMinimumSize(new Dimension(850,350));
    
        contentPane = new JPanel();
        contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
        setContentPane(contentPane);
        contentPane.setLayout(new CardLayout(0, 0));
    
        //Adding tabs
        JTabbedPane tabbedPane = new JTabbedPane(JTabbedPane.LEFT);
        contentPane.add(tabbedPane, "Tabs");
    
        //Adding Student's panel
        JPanel studentsPanel = new JPanel();
        tabbedPane.addTab("Students", null, studentsPanel, null);
        studentsPanel.setLayout(new BorderLayout(0, 0));
    
        //Adding JTable to Student's panel
        JTable studentsJTable = addStudentsJTable();
        studentsPanel.add(studentsJTable, BorderLayout.CENTER);
    
        //Adding Teacher's panel
        JPanel teachersPanel = new JPanel();
        tabbedPane.addTab("Teachers", null, teachersPanel, null);
    
        //Adding Outing's panel
        JPanel outingsPanel = new JPanel();
        tabbedPane.addTab("Outings", null, outingsPanel, null);
    
        setBounds(200,200,650,650);
        pack();
        setVisible(true);
    }
    
    private void printData(JTable jTable){
        int numberOfRows = jTable.getRowCount();
        int numberOfColumns = jTable.getColumnCount();
    
        TableModel model = jTable.getModel();
    
        for(int i = 0; i < numberOfRows; i++){
            System.out.println("Row: " + i + ":");
            for(int j = 0; j < numberOfColumns; j++){
                System.out.println("  " + model.getValueAt(i, j));
            }
            System.out.println();
        }
        System.out.println("-------------------------------");
    }
    
    private JTable addStudentsJTable(){
        String[] columnNames = {
                "Teacher ID",
                "Student ID",
                "Name",
                "Surname",
                "E-mail",
                "Date of Birth",
                "Telephone",
                "Course",
                "OOP",
                "Year of Membership",
                "Consent"};
    
        Object[][] data = {
                {1, 1, "Random", "Student", "Student@email.com", "1/1/1970", 9999999, "MC", true, 2014, true},
                {2, 2, "Student", "Surname", "RandomStudent@email.com", "1/1/1970", 11111111, "AIO", true, 2000, true}
        };
        studentsJTable = new JTable(data, columnNames);
    
        studentsJTable.setPreferredScrollableViewportSize(new Dimension(850,200));
        studentsJTable.setFillsViewportHeight(true);
    
        JScrollPane scrollPane = new JScrollPane(studentsJTable);
        add(scrollPane);
        return studentsJTable;
    }
    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                JDatabaseMainFrame frame = new JDatabaseMainFrame();
                frame.setVisible(true);
            }
        });
    }
    }
    

    随意编译它以查看当前结果!

1 个答案:

答案 0 :(得分:2)

您应该设置自定义TableModel,这样您就可以使用所需的任何数据结构而不是数组:http://docs.oracle.com/javase/tutorial/uiswing/components/table.html#data

这也允许您指定哪些单元格是可编辑的。

只需调用TableColumn类中的相应方法即可设置JTable列的宽度。更多信息:http://docs.oracle.com/javase/8/docs/api/javax/swing/table/TableColumn.html

JTable标头仅在JScrollPane中自动显示。你确实将你的JTable添加到JScrollPane,但是你不能对JScrollPane做任何事情。 JScrollPane本身必须位于某个JFrame中。